From b2ae1e1ddb128bd1eb9ddeb5947a08e444a031a1 Mon Sep 17 00:00:00 2001 From: HojouFotytu Date: Thu, 17 Oct 2019 22:53:00 +0900 Subject: [PATCH 1/7] Update README.md --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index 65e9f7c..b52f488 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,5 @@ # Profit Trailer Magic [Visit the wiki](https://github.com/PTMagicians/PT-Magic/wiki) to learn about this project. + +[Go here](https://github.com/PTMagicians/PTMagic/releases) to download the latest version. From 908fbb6719814b7a37485bca63770cf9cc8d64f0 Mon Sep 17 00:00:00 2001 From: HojouFotytu <36724681+HojouFotytu@users.noreply.github.com> Date: Thu, 17 Oct 2019 23:15:20 +0900 Subject: [PATCH 2/7] update _defaults folder --- .../Monitor/appsettings.json | 0 .../settings.analyzer.json | 326 ------------------ .../Monitor/appsettings.json | 9 - .../_default settings USDT/nlog.config | 28 -- .../settings.general.json | 48 --- .../nlog.config | 0 .../settings.analyzer.json | 31 +- .../settings.general.json | 0 8 files changed, 25 insertions(+), 417 deletions(-) rename PTMagic/_defaults/_default settings PT 2.x/{_default settings BTC or ETH => }/Monitor/appsettings.json (100%) delete mode 100644 PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/settings.analyzer.json delete mode 100644 PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/Monitor/appsettings.json delete mode 100644 PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/nlog.config delete mode 100644 PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/settings.general.json rename PTMagic/_defaults/_default settings PT 2.x/{_default settings BTC or ETH => }/nlog.config (100%) rename PTMagic/_defaults/_default settings PT 2.x/{_default settings USDT => }/settings.analyzer.json (92%) rename PTMagic/_defaults/_default settings PT 2.x/{_default settings BTC or ETH => }/settings.general.json (100%) diff --git a/PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/Monitor/appsettings.json b/PTMagic/_defaults/_default settings PT 2.x/Monitor/appsettings.json similarity index 100% rename from PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/Monitor/appsettings.json rename to PTMagic/_defaults/_default settings PT 2.x/Monitor/appsettings.json diff --git a/PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/settings.analyzer.json b/PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/settings.analyzer.json deleted file mode 100644 index 124697b..0000000 --- a/PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/settings.analyzer.json +++ /dev/null @@ -1,326 +0,0 @@ -// -// The settings below offer a basic example of some of the options available when using PTMagic. -// You should take your time and adjust these settings according to your own personal preferences. -// Always test your PTMagic settings by running a Profit Trailer bot in TESTMODE, to make sure -// it is performing as you expect. -// -// For more information on these settings, see the wiki at: https://github.com/PTMagicians/PTMagic/wiki/settings.analyzer - - -{ - "AnalyzerSettings": { - "MarketAnalyzer": { - "StoreDataMaxHours": 48, // Number of hours to store market data - "IntervalMinutes": 2, // Interval in minutes for PTMagic to check market trends and triggers - "ExcludeMainCurrency": true, // Excludes the main currency (for example BTC) from market trend analysis - "MarketTrends": [ - { - "Name": "15m", // UNIQUE market trend name (to be referenced by your triggers below) - "Platform": "Exchange", // Platform to grab prices from (Allowed values are: CoinMarketCap, Exchange) - "MaxMarkets": 50, // Number of markets/pairs to analyze sorted by 24h volume - "TrendMinutes": 15, // Number of minutes to build a trend (1440 = 24h, 720 = 12h, 60 = 1h) - "TrendCurrency": "Market", // Trend Currency to build the trend against. If set to "Fiat", the trend will - // take the USD value of your main currency into account to build the trend. - // (Allowed values are: Fiat, Market) - "DisplayGraph": false, // Use this trend in the graph on the PTM Monitor dashboard and market analyzer - "DisplayOnMarketAnalyzerList": false // Disply this trend for all coins on the PTM Monitor market analyzer - }, - { - "Name": "1h", - "Platform": "Exchange", - "MaxMarkets": 50, - "TrendMinutes": 60, - "TrendCurrency": "Market", - "DisplayGraph": true, - "DisplayOnMarketAnalyzerList": true - }, - { - "Name": "6h", - "Platform": "Exchange", - "MaxMarkets": 50, - "TrendMinutes": 360, - "TrendCurrency": "Market", - "DisplayGraph": true, - "DisplayOnMarketAnalyzerList": true - }, - { - "Name": "12h", - "Platform": "Exchange", - "MaxMarkets": 50, - "TrendMinutes": 720, - "TrendCurrency": "Market", - "DisplayGraph": true, - "DisplayOnMarketAnalyzerList": true - }, - { - "Name": "24h", - "Platform": "Exchange", - "MaxMarkets": 50, - "TrendMinutes": 1440, - "TrendCurrency": "Market", - "DisplayGraph": true, - "DisplayOnMarketAnalyzerList": true - } - ] - }, - // ================================ GLOBAL SETTINGS ================================ - // - "GlobalSettings": [ // Global settings for Profit Trailer properties - // - // ----------------------------- - { - "SettingName": "EndOfTheWorld", // ANY UNIQUE name of your setting - "TriggerConnection": "AND", // Define if triggers will be connected by AND or OR - "Triggers": [ // Your triggers for this setting. You can use any of your defined trends from above - { - "MarketTrendName": "1h", // Reference to the market trend specified above - "MaxChange": 0 // The maximum value for this trigger to be true. (Any value below "0" will trigger this) - }, - { - "MarketTrendName": "12h", - "MaxChange": -2 - }, - { - "MarketTrendName": "24h", - "MaxChange": -5 - } - ], - "PairsProperties": { // Properties for PAIRS.PROPERTIES - // Any valid setting from https://wiki.profittrailer.com/doku.php?id=pairs.properties can be used here. - // You can use a specific value, or apply a discrete OFFSET or OFFSETPERCENT to the value in your default PAIRS setting. - "DEFAULT_sell_only_mode_enabled": true, - "DEFAULT_trailing_profit_OFFSETPERCENT": -50 - }, - "DCAProperties": { // Properties for DCA.PROPERTIES - "DEFAULT_DCA_trailing_profit_OFFSETPERCENT": -75 - } - }, - // ----------------------------- - { - "SettingName": "TankingDown", - "TriggerConnection": "AND", - "Triggers": [ - { - "MarketTrendName": "15m", - "MaxChange": 0 - }, - { - "MarketTrendName": "1h", - "MaxChange": 0 - }, - { - "MarketTrendName": "12h", - "MaxChange": 0 - }, - { - "MarketTrendName": "24h", // Any value between -5 and -3 will make this trigger true. - "MaxChange": -3, - "MinChange": -5 // The minimum value for this trigger to be true. (Any value above "-5" will trigger this) - } - ], - "PairsProperties": { - "max_trading_pairs_OFFSET": -2, - "DEFAULT_min_buy_volume_OFFSETPERCENT": 100, - //"DEFAULT_initial_cost_OFFSETPERCENT": -50, - //"DEFAULT_initial_cost_percentage_OFFSETPERCENT": -50, - "DEFAULT_trailing_buy_OFFSETPERCENT": 25, - "DEFAULT_trailing_profit_OFFSETPERCENT": -25 - }, - "DCAProperties": { - //"DEFAULT_DCA_rebuy_timeout_OFFSETPERCENT": 100, - "DEFAULT_DCA_trailing_buy_OFFSETPERCENT": 25, - "DEFAULT_DCA_trailing_profit_OFFSETPERCENT": -50 - }, - "IndicatorsProperties": { - } - }, - // ----------------------------- - { - "SettingName": "BearSighted", - "TriggerConnection": "AND", - "Triggers": [ - { - "MarketTrendName": "1h", - "MaxChange": 1 - }, - { - "MarketTrendName": "12h", - "MaxChange": 0 - }, - { - "MarketTrendName": "24h", - "MaxChange": -1, - "MinChange": -3 - } - ], - "PairsProperties": { - "max_trading_pairs_OFFSET": -1, - //"DEFAULT_initial_cost_OFFSETPERCENT": -25, - //"DEFAULT_initial_cost_percentage_OFFSETPERCENT": -25, - "DEFAULT_trailing_buy_OFFSETPERCENT": 10, - "DEFAULT_trailing_profit_OFFSETPERCENT": -10 - }, - "DCAProperties": { - "DEFAULT_DCA_trailing_buy_OFFSETPERCENT": 10, - "DEFAULT_DCA_trailing_profit_OFFSETPERCENT": -10, - }, - "IndicatorsProperties": { - } - }, - // ----------------------------- - { - "SettingName": "ReadyForLiftOff", - "TriggerConnection": "AND", - "Triggers": [ - { - "MarketTrendName": "1h", - "MinChange": 0 - }, - { - "MarketTrendName": "12h", - "MinChange": 0 - }, - { - "MarketTrendName": "24h", - "MinChange": 1, - "MaxChange": 3 - } - ], - "PairsProperties": { - "max_trading_pairs_OFFSET": 1, - //"DEFAULT_initial_cost_OFFSETPERCENT": 10, - //"DEFAULT_initial_cost_percentage_OFFSETPERCENT": 10, - "DEFAULT_trailing_buy_OFFSETPERCENT": -10, - "DEFAULT_A_sell_value_OFFSETPERCENT": 10 - }, - "DCAProperties": { - "DEFAULT_DCA_trailing_buy_OFFSETPERCENT": -10, - "DEFAULT_DCA_trailing_profit_OFFSETPERCENT": 10, - }, - "IndicatorsProperties": { - } - }, - // ----------------------------- - { - "SettingName": "ToTheMoon", - "TriggerConnection": "AND", - "Triggers": [ - { - "MarketTrendName": "1h", - "MinChange": 1 - }, - { - "MarketTrendName": "12h", - "MinChange": 1 - }, - { - "MarketTrendName": "24h", - "MinChange": 3 - } - ], - "PairsProperties": { - "max_trading_pairs_OFFSET": 2, - //"DEFAULT_initial_cost_OFFSETPERCENT": 20, - //"DEFAULT_initial_cost_percentage_OFFSETPERCENT": 20, - "DEFAULT_trailing_buy_OFFSETPERCENT": -10, - "DEFAULT_A_sell_value_OFFSETPERCENT": 20 - }, - "DCAProperties": { - "DEFAULT_DCA_trailing_buy_OFFSETPERCENT": -20, - "DEFAULT_DCA_trailing_profit_OFFSETPERCENT": 20, - }, - "IndicatorsProperties": { - } - }, - // ----------------------------- - { - "SettingName": "Default", - "PairsProperties": { - "File": "PAIRS.properties" - }, - "DCAProperties": { - "File": "DCA.properties" - }, - "IndicatorsProperties": { - "File": "INDICATORS.properties" - } - } - ], - // ================================ COIN-SPECIFIC SETTINGS ================================ - // - "SingleMarketSettings": [ // Single market/pair settings for Profit Trailer properties - // Any setting from https://wiki.profittrailer.com/doku.php?id=pairs.properties - // marked as CS (coin-specific) can be used here. - // Only coins that meet the triggered conditions will have the settings applied. - { - "SettingName": "BlacklistCoins", - "StopProcessWhenTriggered": true, - "Triggers": [ - { - "AgeDaysLowerThan": 21 - } - ], - "PairsProperties": { - "DEFAULT_trading_enabled": false, - "DEFAULT_sell_only_mode_enabled": true, - "DEFAULT_DCA_enabled": false - } - }, - // ----------------------------- - { - "SettingName": "PumpNDumpProtection", - "TriggerConnection": "OR", - "Triggers": [ - { - "MarketTrendName": "1h", - "MarketTrendRelation": "Relative", // The relation of the single market trend. Relative = Single market - // trend compared relative to the market trend - // Absolute = Single market trend viewed on its own - "MinChange": 8 - }, - { - "MarketTrendName": "12h", - "MarketTrendRelation": "Relative", - "MinChange": 10 - }, - { - "MarketTrendName": "24h", - "MarketTrendRelation": "Relative", - "MinChange": 12 - } - ], - "OffTriggers": [ - { - "HoursSinceTriggered": 3 // Any coin that triggers this setting, will remain under this setting - // for 3 hours, since the last time it triggered. - } - ], - "PairsProperties": { - "DEFAULT_sell_only_mode_enabled": true, - "DEFAULT_DCA_enabled": false - } - }, - // ----------------------------- - { - "SettingName": "FreefallBlock", - "TriggerConnection": "OR", - "Triggers": [ - { - "MarketTrendName": "1h", - "MarketTrendRelation": "Absolute", - "MaxChange": -5 - } - ], - "OffTriggers": [ - { - "HoursSinceTriggered": 1 - } - ], - "PairsProperties": { - "DEFAULT_sell_only_mode_enabled": true, - "DEFAULT_DCA_enabled": false - } - } - ] - } -} \ No newline at end of file diff --git a/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/Monitor/appsettings.json b/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/Monitor/appsettings.json deleted file mode 100644 index 0c38f1b..0000000 --- a/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/Monitor/appsettings.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "PTMagicBasePath": "YOUR PT MAGIC PATH", // Path to your Profit Trailer Magic main directory (use double backslashes for windows like C:\\PTMagic\\) - "Logging": { - "IncludeScopes": false, - "LogLevel": { - "Default": "Warning" - } - } -} diff --git a/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/nlog.config b/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/nlog.config deleted file mode 100644 index adb7382..0000000 --- a/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/nlog.config +++ /dev/null @@ -1,28 +0,0 @@ - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/settings.general.json b/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/settings.general.json deleted file mode 100644 index 05e044d..0000000 --- a/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/settings.general.json +++ /dev/null @@ -1,48 +0,0 @@ -{ - "GeneralSettings": { - "Application": { - "IsEnabled": true, // Enables the PTMagic bot (needs restart to take effect) - "TestMode": false, // If TestMode is active, no properties files will be changed - "ProfitTrailerPath": "YOUR PROFIT TRAILER PATH", // Path to your Profit Trailer main directory (use double backslashes for windows like C:\\ProfitTrailer\\) - "ProfitTrailerLicense": "YOUR PROFIT TRAILER LICENSE KEY", // Your Profit Trailer license key (needed to change your settings for PT 2.0 and above) - "ProfitTrailerServerAPIToken": "", //Your Profit Trailer Server API Token - "ProfitTrailerMonitorURL": "http://localhost:8081/", // The URL to your profit trailer monitor (needed to change your settings for PT 2.0 and above) - "ProfitTrailerDefaultSettingName": "default", // Your Profit Trailer default setting name (needed to change your settings for PT 2.0 and above) - "Exchange": "Bittrex", // The exchange your are running Profit Trailer on - "StartBalance": 0, // The balance you had in your wallet when you started working with Profit Trailer - "TimezoneOffset": "+0:00", // Your timezone offset from UTC time - "MainFiatCurrency": "USD", // Your main fiat currency that will be used in the monitor - "FloodProtectionMinutes": 0, // If a price trend is just zig-zagging around its trigger, you may want to protect your settings from getting switched back and forth every minute - "InstanceName": "PT Magic", // The name of the instance of this bot. This will be used in your monitor and your Telegram messages. In case you are running more than one bot, you may set different names to separate them - "CoinMarketCapAPIKey": "", //CoinMarketCap Api - "FreeCurrencyConverterAPIKey": "" // If "MainFiatCurrency" above is anything other than USD, you must obtain an API key from https://free.currencyconverterapi.com/free-api-key - }, - "Monitor": { - "IsPasswordProtected": true, // Defines if your monitor will be asking to setup a password on its first start - "OpenBrowserOnStart": false, // If active, a browser window will open as soon as you start the monitor - "Port": 5000, // The port you want to run your monitor on - "RootUrl": "/", // The root Url of your monitor - "GraphIntervalMinutes": 60, // The interval for the monitor market trend graph to draw points - "GraphMaxTimeframeHours": 24, // This will enable you to define the timeframe that your graph for market trends covers - "RefreshSeconds": 30, // The refresh interval of your monitor main page - "LinkPlatform": "TradingView", // The platform to which the pair name will link if you click on it - "MaxTopMarkets": 20, // The amount of top markets being shown in your Sales Analyzer - "MaxDailySummaries": 10, // The amount of "Last Days" being shown in your Sales Analyzer - "MaxMonthlySummaries": 10, // The amount of "Last Months" being shown in your Sales Analyzer - "TvStudyA": "BB@tv-basicstudies", // See available STUDIES at https://www.tradingview.com/wiki/Widget:TradingView_Widget - "TvStudyB": "", - "TvStudyC": "", - "TvStudyD": "" - }, - "Backup": { - "IsEnabled": true, // Enables a backup procedure for your properties files. Before every switch PTMagic will backup the current properties - "MaxHours": 12 // Max number of hours to keep backup files - }, - "Telegram": { - "IsEnabled": false, // Enables PT Magic to send Telegram messages - "BotToken": "", // Your Telegram bot token - "ChatId": 0, // Your Telegram Chat ID - "SilentMode": false // If SilentMode is active, no notification sound or vibration will happen when the bot sends a Telegram message - } - } -} \ No newline at end of file diff --git a/PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/nlog.config b/PTMagic/_defaults/_default settings PT 2.x/nlog.config similarity index 100% rename from PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/nlog.config rename to PTMagic/_defaults/_default settings PT 2.x/nlog.config diff --git a/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/settings.analyzer.json b/PTMagic/_defaults/_default settings PT 2.x/settings.analyzer.json similarity index 92% rename from PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/settings.analyzer.json rename to PTMagic/_defaults/_default settings PT 2.x/settings.analyzer.json index 124697b..2b54862 100644 --- a/PTMagic/_defaults/_default settings PT 2.x/_default settings USDT/settings.analyzer.json +++ b/PTMagic/_defaults/_default settings PT 2.x/settings.analyzer.json @@ -1,7 +1,8 @@ // -// The settings below offer a basic example of some of the options available when using PTMagic. +// The settings below offer a simple example of some of the options available when using PTMagic. // You should take your time and adjust these settings according to your own personal preferences. -// Always test your PTMagic settings by running a Profit Trailer bot in TESTMODE, to make sure +// +// ALWAYS test your PTMagic settings by running a Profit Trailer bot in TESTMODE, to make sure // it is performing as you expect. // // For more information on these settings, see the wiki at: https://github.com/PTMagicians/PTMagic/wiki/settings.analyzer @@ -30,6 +31,15 @@ "Platform": "Exchange", "MaxMarkets": 50, "TrendMinutes": 60, + "TrendCurrency": "Market", + "DisplayGraph": false, + "DisplayOnMarketAnalyzerList": true + }, + { + "Name": "3h", + "Platform": "Exchange", + "MaxMarkets": 50, + "TrendMinutes": 180, "TrendCurrency": "Market", "DisplayGraph": true, "DisplayOnMarketAnalyzerList": true @@ -58,7 +68,16 @@ "MaxMarkets": 50, "TrendMinutes": 1440, "TrendCurrency": "Market", - "DisplayGraph": true, + "DisplayGraph": false, + "DisplayOnMarketAnalyzerList": true + }, + { + "Name": "3d", + "Platform": "Exchange", + "MaxMarkets": 50, + "TrendMinutes": 4320, + "TrendCurrency": "Market", + "DisplayGraph": false, "DisplayOnMarketAnalyzerList": true } ] @@ -86,7 +105,7 @@ } ], "PairsProperties": { // Properties for PAIRS.PROPERTIES - // Any valid setting from https://wiki.profittrailer.com/doku.php?id=pairs.properties can be used here. + // Any valid setting from https://wiki.profittrailer.com/doku.php?id=pairs_config can be used here. // You can use a specific value, or apply a discrete OFFSET or OFFSETPERCENT to the value in your default PAIRS setting. "DEFAULT_sell_only_mode_enabled": true, "DEFAULT_trailing_profit_OFFSETPERCENT": -50 @@ -249,7 +268,7 @@ // ================================ COIN-SPECIFIC SETTINGS ================================ // "SingleMarketSettings": [ // Single market/pair settings for Profit Trailer properties - // Any setting from https://wiki.profittrailer.com/doku.php?id=pairs.properties + // Any setting from https://wiki.profittrailer.com/doku.php?id=pairs_config // marked as CS (coin-specific) can be used here. // Only coins that meet the triggered conditions will have the settings applied. { @@ -292,7 +311,7 @@ "OffTriggers": [ { "HoursSinceTriggered": 3 // Any coin that triggers this setting, will remain under this setting - // for 3 hours, since the last time it triggered. + // for 3 hours even if the trends are no longer true. } ], "PairsProperties": { diff --git a/PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/settings.general.json b/PTMagic/_defaults/_default settings PT 2.x/settings.general.json similarity index 100% rename from PTMagic/_defaults/_default settings PT 2.x/_default settings BTC or ETH/settings.general.json rename to PTMagic/_defaults/_default settings PT 2.x/settings.general.json From 3ffe830015e9f37bb753dbab29d3409aec8ce769 Mon Sep 17 00:00:00 2001 From: HojouFotytu <36724681+HojouFotytu@users.noreply.github.com> Date: Sat, 19 Oct 2019 11:42:45 +0900 Subject: [PATCH 3/7] Fix for issue #151 --- Core/ProfitTrailer/SettingsHandler.cs | 19 +++++++++++++++++-- 1 file changed, 17 insertions(+), 2 deletions(-) diff --git a/Core/ProfitTrailer/SettingsHandler.cs b/Core/ProfitTrailer/SettingsHandler.cs index c46db4c..71bac93 100644 --- a/Core/ProfitTrailer/SettingsHandler.cs +++ b/Core/ProfitTrailer/SettingsHandler.cs @@ -59,8 +59,16 @@ namespace Core.ProfitTrailer double offsetValue = SystemHelper.TextToDouble(newValueString, 0, "en-US"); if (offsetValue != 0) { + bool ContainsPercent = false; + if (oldValueString.Contains("%")) { + ContainsPercent = true; + oldValueString = oldValueString.Substring(0, oldValueString.Length - 1); + } double oldValue = SystemHelper.TextToDouble(oldValueString, 0, "en-US"); result = Math.Round((oldValue + offsetValue), 8).ToString(new System.Globalization.CultureInfo("en-US")); + if (ContainsPercent){ + result = result +"%"; + } } break; @@ -69,11 +77,16 @@ namespace Core.ProfitTrailer double offsetValuePercent = SystemHelper.TextToDouble(newValueString, 0, "en-US"); if (offsetValuePercent != 0) { + bool ContainsPercent = false; + if (oldValueString.Contains("%")) { + ContainsPercent = true; + oldValueString = oldValueString.Substring(0, oldValueString.Length - 1); + } double oldValue = SystemHelper.TextToDouble(oldValueString, 0, "en-US"); if (oldValue < 0) offsetValuePercent = offsetValuePercent * -1; double oldValueOffset = (oldValue * (offsetValuePercent / 100)); - // Use integers for timeout and pairs properties, otherwise double + // Ensure integers for timeout and pairs properties, otherwise double if (configPropertyKey.Contains("timeout", StringComparison.InvariantCultureIgnoreCase) || configPropertyKey.Contains("trading_pairs", StringComparison.InvariantCultureIgnoreCase) || configPropertyKey.Contains("buy_volume", StringComparison.InvariantCultureIgnoreCase) @@ -82,7 +95,6 @@ namespace Core.ProfitTrailer || configPropertyKey.Contains("rebuy_count", StringComparison.InvariantCultureIgnoreCase) || configPropertyKey.Contains("buy_volume", StringComparison.InvariantCultureIgnoreCase)) { - // Ensure some values are rounded up to integers for PT comaptability result = ((int)(Math.Round((oldValue + oldValueOffset), MidpointRounding.AwayFromZero) + .5)).ToString(new System.Globalization.CultureInfo("en-US")); } else @@ -90,6 +102,9 @@ namespace Core.ProfitTrailer // Use double to calculate result = Math.Round((oldValue + oldValueOffset), 8).ToString(new System.Globalization.CultureInfo("en-US")); } + if (ContainsPercent){ + result = result +"%"; + } } break; default: From e081fa62334b079947586ffaffc481f3dc60fd84 Mon Sep 17 00:00:00 2001 From: HojouFotytu <36724681+HojouFotytu@users.noreply.github.com> Date: Sat, 19 Oct 2019 12:33:38 +0900 Subject: [PATCH 4/7] update version number 2.2.8 --- PTMagic/Program.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/PTMagic/Program.cs b/PTMagic/Program.cs index 885fb28..fd73b60 100644 --- a/PTMagic/Program.cs +++ b/PTMagic/Program.cs @@ -7,7 +7,7 @@ using Core.Helper; using Core.Main.DataObjects.PTMagicData; using Microsoft.Extensions.DependencyInjection; -[assembly: AssemblyVersion("2.2.7")] +[assembly: AssemblyVersion("2.2.8")] [assembly: AssemblyProduct("PT Magic")] namespace PTMagic From 6195eae171a8676f589ec0daa46c6f4c8189f01d Mon Sep 17 00:00:00 2001 From: djbadders <34887832+djbadders@users.noreply.github.com> Date: Sat, 19 Oct 2019 11:14:40 +0100 Subject: [PATCH 5/7] Fix for sales data not refreshing --- Core/DataObjects/ProfitTrailerData.cs | 52 +++++++++++++++++---------- 1 file changed, 34 insertions(+), 18 deletions(-) diff --git a/Core/DataObjects/ProfitTrailerData.cs b/Core/DataObjects/ProfitTrailerData.cs index e951049..b34fca4 100644 --- a/Core/DataObjects/ProfitTrailerData.cs +++ b/Core/DataObjects/ProfitTrailerData.cs @@ -21,17 +21,38 @@ namespace Core.Main.DataObjects private string _ptmBasePath = ""; private PTMagicConfiguration _systemConfiguration = null; private TransactionData _transactionData = null; - private DateTimeOffset _dateTimeNow = Constants.confMinDate; private DateTime _buyLogRefresh = DateTime.UtcNow, _sellLogRefresh = DateTime.UtcNow, _dcaLogRefresh = DateTime.UtcNow, _summaryRefresh = DateTime.UtcNow; private volatile object _buyLock = new object(), _sellLock = new object(), _dcaLock = new object(), _summaryLock = new object(); + private TimeSpan? _offsetTimeSpan = null; + // Constructor public ProfitTrailerData(PTMagicConfiguration systemConfiguration) { _systemConfiguration = systemConfiguration; + } - // Convert local offset time to UTC - TimeSpan offsetTimeSpan = TimeSpan.Parse(systemConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", "")); - _dateTimeNow = DateTimeOffset.UtcNow.ToOffset(offsetTimeSpan); + // Get a time span for the UTC offset from the settings + private TimeSpan OffsetTimeSpan + { + get + { + if (!_offsetTimeSpan.HasValue) + { + // Get offset for settings. + _offsetTimeSpan = TimeSpan.Parse(_systemConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", "")); + } + + return _offsetTimeSpan.Value; + } + } + + // Get the time with the settings UTC offset applied + private DateTimeOffset LocalizedTime + { + get + { + return DateTimeOffset.UtcNow.ToOffset(OffsetTimeSpan); + } } public SummaryData Summary @@ -80,7 +101,7 @@ namespace Core.Main.DataObjects { get { - return SellLog.FindAll(sl => sl.SoldDate.Date == _dateTimeNow.DateTime.Date); + return SellLog.FindAll(sl => sl.SoldDate.Date == LocalizedTime.DateTime.Date); } } @@ -88,7 +109,7 @@ namespace Core.Main.DataObjects { get { - return SellLog.FindAll(sl => sl.SoldDate.Date == _dateTimeNow.DateTime.AddDays(-1).Date); + return SellLog.FindAll(sl => sl.SoldDate.Date == LocalizedTime.DateTime.AddDays(-1).Date); } } @@ -96,7 +117,7 @@ namespace Core.Main.DataObjects { get { - return SellLog.FindAll(sl => sl.SoldDate.Date >= _dateTimeNow.DateTime.AddDays(-7).Date); + return SellLog.FindAll(sl => sl.SoldDate.Date >= LocalizedTime.DateTime.AddDays(-7).Date); } } @@ -104,7 +125,7 @@ namespace Core.Main.DataObjects { get { - return SellLog.FindAll(sl => sl.SoldDate.Date >= _dateTimeNow.DateTime.AddDays(-30).Date); + return SellLog.FindAll(sl => sl.SoldDate.Date >= LocalizedTime.DateTime.AddDays(-30).Date); } } @@ -296,8 +317,7 @@ namespace Core.Main.DataObjects DateTimeOffset ptSoldDate = DateTimeOffset.Parse(dtDateTime.Year.ToString() + "-" + dtDateTime.Month.ToString("00") + "-" + dtDateTime.Day.ToString("00") + "T" + dtDateTime.Hour.ToString("00") + ":" + dtDateTime.Minute.ToString("00") + ":" + dtDateTime.Second.ToString("00"), CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal); // Convert UTC sales time to local offset time - TimeSpan offsetTimeSpan = TimeSpan.Parse(_systemConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", "")); - ptSoldDate = ptSoldDate.ToOffset(offsetTimeSpan); + ptSoldDate = ptSoldDate.ToOffset(OffsetTimeSpan); sellLogData.SoldDate = ptSoldDate.DateTime; @@ -387,8 +407,7 @@ namespace Core.Main.DataObjects DateTimeOffset ptFirstBoughtDate = DateTimeOffset.Parse(rdldDateTime.Year.ToString() + "-" + rdldDateTime.Month.ToString("00") + "-" + rdldDateTime.Day.ToString("00") + "T" + rdldDateTime.Hour.ToString("00") + ":" + rdldDateTime.Minute.ToString("00") + ":" + rdldDateTime.Second.ToString("00"), CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal); // Convert UTC bought time to local offset time - TimeSpan offsetTimeSpan = TimeSpan.Parse(_systemConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", "")); - ptFirstBoughtDate = ptFirstBoughtDate.ToOffset(offsetTimeSpan); + ptFirstBoughtDate = ptFirstBoughtDate.ToOffset(OffsetTimeSpan); dcaLogData.FirstBoughtDate = ptFirstBoughtDate.DateTime; } @@ -447,8 +466,7 @@ namespace Core.Main.DataObjects DateTimeOffset ptFirstBoughtDate = DateTimeOffset.Parse(rpldDateTime.Year.ToString() + "-" + rpldDateTime.Month.ToString("00") + "-" + rpldDateTime.Day.ToString("00") + "T" + rpldDateTime.Hour.ToString("00") + ":" + rpldDateTime.Minute.ToString("00") + ":" + rpldDateTime.Second.ToString("00"), CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal); // Convert UTC bought time to local offset time - TimeSpan offsetTimeSpan = TimeSpan.Parse(_systemConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", "")); - ptFirstBoughtDate = ptFirstBoughtDate.ToOffset(offsetTimeSpan); + ptFirstBoughtDate = ptFirstBoughtDate.ToOffset(OffsetTimeSpan); dcaLogData.FirstBoughtDate = ptFirstBoughtDate.DateTime; } @@ -507,8 +525,7 @@ namespace Core.Main.DataObjects DateTimeOffset ptFirstBoughtDate = DateTimeOffset.Parse(rpldDateTime.Year.ToString() + "-" + rpldDateTime.Month.ToString("00") + "-" + rpldDateTime.Day.ToString("00") + "T" + rpldDateTime.Hour.ToString("00") + ":" + rpldDateTime.Minute.ToString("00") + ":" + rpldDateTime.Second.ToString("00"), CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal); // Convert UTC bought time to local offset time - TimeSpan offsetTimeSpan = TimeSpan.Parse(_systemConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", "")); - ptFirstBoughtDate = ptFirstBoughtDate.ToOffset(offsetTimeSpan); + ptFirstBoughtDate = ptFirstBoughtDate.ToOffset(OffsetTimeSpan); dcaLogData.FirstBoughtDate = ptFirstBoughtDate.DateTime; } @@ -567,8 +584,7 @@ namespace Core.Main.DataObjects DateTimeOffset ptFirstBoughtDate = DateTimeOffset.Parse(rpldDateTime.Year.ToString() + "-" + rpldDateTime.Month.ToString("00") + "-" + rpldDateTime.Day.ToString("00") + "T" + rpldDateTime.Hour.ToString("00") + ":" + rpldDateTime.Minute.ToString("00") + ":" + rpldDateTime.Second.ToString("00"), CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal); // Convert UTC bought time to local offset time - TimeSpan offsetTimeSpan = TimeSpan.Parse(_systemConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", "")); - ptFirstBoughtDate = ptFirstBoughtDate.ToOffset(offsetTimeSpan); + ptFirstBoughtDate = ptFirstBoughtDate.ToOffset(OffsetTimeSpan); dcaLogData.FirstBoughtDate = ptFirstBoughtDate.DateTime; } From a4b000c72797341fb252f3100db6038b0ce0f94e Mon Sep 17 00:00:00 2001 From: djbadders <34887832+djbadders@users.noreply.github.com> Date: Sat, 19 Oct 2019 12:33:02 +0100 Subject: [PATCH 6/7] Fix for SMS tooltip not showing --- Monitor/Pages/_get/BagList.cshtml | 5 ++++- Monitor/wwwroot/assets/js/bootstrap.min.js | 6 +++--- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/Monitor/Pages/_get/BagList.cshtml b/Monitor/Pages/_get/BagList.cshtml index a77d81d..b1f7eb4 100644 --- a/Monitor/Pages/_get/BagList.cshtml +++ b/Monitor/Pages/_get/BagList.cshtml @@ -86,7 +86,10 @@ @if (mps != null && (mps.ActiveSingleSettings == null || mps.ActiveSingleSettings.Count == 0)) { @dcaLogEntry.Market } else { - @dcaLogEntry.Market + @dcaLogEntry.Market + + + } // Trend diff --git a/Monitor/wwwroot/assets/js/bootstrap.min.js b/Monitor/wwwroot/assets/js/bootstrap.min.js index c4c0d1f..9df6b6c 100644 --- a/Monitor/wwwroot/assets/js/bootstrap.min.js +++ b/Monitor/wwwroot/assets/js/bootstrap.min.js @@ -1,7 +1,7 @@ /*! - * Bootstrap v4.3.1 (https://getbootstrap.com/) - * Copyright 2011-2019 The Bootstrap Authors (https://github.com/twbs/bootstrap/graphs/contributors) + * Bootstrap v4.2.1 (https://getbootstrap.com/) + * Copyright 2011-2018 The Bootstrap Authors (https://github.com/twbs/bootstrap/graphs/contributors) * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE) */ -!function(t,e){"object"==typeof exports&&"undefined"!=typeof module?e(exports,require("jquery"),require("popper.js")):"function"==typeof define&&define.amd?define(["exports","jquery","popper.js"],e):e((t=t||self).bootstrap={},t.jQuery,t.Popper)}(this,function(t,g,u){"use strict";function i(t,e){for(var n=0;nthis._items.length-1||t<0))if(this._isSliding)g(this._element).one(Q.SLID,function(){return e.to(t)});else{if(n===t)return this.pause(),void this.cycle();var i=ndocument.documentElement.clientHeight;!this._isBodyOverflowing&&t&&(this._element.style.paddingLeft=this._scrollbarWidth+"px"),this._isBodyOverflowing&&!t&&(this._element.style.paddingRight=this._scrollbarWidth+"px")},t._resetAdjustments=function(){this._element.style.paddingLeft="",this._element.style.paddingRight=""},t._checkScrollbar=function(){var t=document.body.getBoundingClientRect();this._isBodyOverflowing=t.left+t.right
',trigger:"hover focus",title:"",delay:0,html:!1,selector:!1,placement:"top",offset:0,container:!1,fallbackPlacement:"flip",boundary:"scrollParent",sanitize:!0,sanitizeFn:null,whiteList:Ee},je="show",He="out",Re={HIDE:"hide"+De,HIDDEN:"hidden"+De,SHOW:"show"+De,SHOWN:"shown"+De,INSERTED:"inserted"+De,CLICK:"click"+De,FOCUSIN:"focusin"+De,FOCUSOUT:"focusout"+De,MOUSEENTER:"mouseenter"+De,MOUSELEAVE:"mouseleave"+De},xe="fade",Fe="show",Ue=".tooltip-inner",We=".arrow",qe="hover",Me="focus",Ke="click",Qe="manual",Be=function(){function i(t,e){if("undefined"==typeof u)throw new TypeError("Bootstrap's tooltips require Popper.js (https://popper.js.org/)");this._isEnabled=!0,this._timeout=0,this._hoverState="",this._activeTrigger={},this._popper=null,this.element=t,this.config=this._getConfig(e),this.tip=null,this._setListeners()}var t=i.prototype;return t.enable=function(){this._isEnabled=!0},t.disable=function(){this._isEnabled=!1},t.toggleEnabled=function(){this._isEnabled=!this._isEnabled},t.toggle=function(t){if(this._isEnabled)if(t){var e=this.constructor.DATA_KEY,n=g(t.currentTarget).data(e);n||(n=new this.constructor(t.currentTarget,this._getDelegateConfig()),g(t.currentTarget).data(e,n)),n._activeTrigger.click=!n._activeTrigger.click,n._isWithActiveTrigger()?n._enter(null,n):n._leave(null,n)}else{if(g(this.getTipElement()).hasClass(Fe))return void this._leave(null,this);this._enter(null,this)}},t.dispose=function(){clearTimeout(this._timeout),g.removeData(this.element,this.constructor.DATA_KEY),g(this.element).off(this.constructor.EVENT_KEY),g(this.element).closest(".modal").off("hide.bs.modal"),this.tip&&g(this.tip).remove(),this._isEnabled=null,this._timeout=null,this._hoverState=null,(this._activeTrigger=null)!==this._popper&&this._popper.destroy(),this._popper=null,this.element=null,this.config=null,this.tip=null},t.show=function(){var e=this;if("none"===g(this.element).css("display"))throw new Error("Please use show on visible elements");var t=g.Event(this.constructor.Event.SHOW);if(this.isWithContent()&&this._isEnabled){g(this.element).trigger(t);var n=_.findShadowRoot(this.element),i=g.contains(null!==n?n:this.element.ownerDocument.documentElement,this.element);if(t.isDefaultPrevented()||!i)return;var o=this.getTipElement(),r=_.getUID(this.constructor.NAME);o.setAttribute("id",r),this.element.setAttribute("aria-describedby",r),this.setContent(),this.config.animation&&g(o).addClass(xe);var s="function"==typeof this.config.placement?this.config.placement.call(this,o,this.element):this.config.placement,a=this._getAttachment(s);this.addAttachmentClass(a);var l=this._getContainer();g(o).data(this.constructor.DATA_KEY,this),g.contains(this.element.ownerDocument.documentElement,this.tip)||g(o).appendTo(l),g(this.element).trigger(this.constructor.Event.INSERTED),this._popper=new u(this.element,o,{placement:a,modifiers:{offset:this._getOffset(),flip:{behavior:this.config.fallbackPlacement},arrow:{element:We},preventOverflow:{boundariesElement:this.config.boundary}},onCreate:function(t){t.originalPlacement!==t.placement&&e._handlePopperPlacementChange(t)},onUpdate:function(t){return e._handlePopperPlacementChange(t)}}),g(o).addClass(Fe),"ontouchstart"in document.documentElement&&g(document.body).children().on("mouseover",null,g.noop);var c=function(){e.config.animation&&e._fixTransition();var t=e._hoverState;e._hoverState=null,g(e.element).trigger(e.constructor.Event.SHOWN),t===He&&e._leave(null,e)};if(g(this.tip).hasClass(xe)){var h=_.getTransitionDurationFromElement(this.tip);g(this.tip).one(_.TRANSITION_END,c).emulateTransitionEnd(h)}else c()}},t.hide=function(t){var e=this,n=this.getTipElement(),i=g.Event(this.constructor.Event.HIDE),o=function(){e._hoverState!==je&&n.parentNode&&n.parentNode.removeChild(n),e._cleanTipClass(),e.element.removeAttribute("aria-describedby"),g(e.element).trigger(e.constructor.Event.HIDDEN),null!==e._popper&&e._popper.destroy(),t&&t()};if(g(this.element).trigger(i),!i.isDefaultPrevented()){if(g(n).removeClass(Fe),"ontouchstart"in document.documentElement&&g(document.body).children().off("mouseover",null,g.noop),this._activeTrigger[Ke]=!1,this._activeTrigger[Me]=!1,this._activeTrigger[qe]=!1,g(this.tip).hasClass(xe)){var r=_.getTransitionDurationFromElement(n);g(n).one(_.TRANSITION_END,o).emulateTransitionEnd(r)}else o();this._hoverState=""}},t.update=function(){null!==this._popper&&this._popper.scheduleUpdate()},t.isWithContent=function(){return Boolean(this.getTitle())},t.addAttachmentClass=function(t){g(this.getTipElement()).addClass(Ae+"-"+t)},t.getTipElement=function(){return this.tip=this.tip||g(this.config.template)[0],this.tip},t.setContent=function(){var t=this.getTipElement();this.setElementContent(g(t.querySelectorAll(Ue)),this.getTitle()),g(t).removeClass(xe+" "+Fe)},t.setElementContent=function(t,e){"object"!=typeof e||!e.nodeType&&!e.jquery?this.config.html?(this.config.sanitize&&(e=Se(e,this.config.whiteList,this.config.sanitizeFn)),t.html(e)):t.text(e):this.config.html?g(e).parent().is(t)||t.empty().append(e):t.text(g(e).text())},t.getTitle=function(){var t=this.element.getAttribute("data-original-title");return t||(t="function"==typeof this.config.title?this.config.title.call(this.element):this.config.title),t},t._getOffset=function(){var e=this,t={};return"function"==typeof this.config.offset?t.fn=function(t){return t.offsets=l({},t.offsets,e.config.offset(t.offsets,e.element)||{}),t}:t.offset=this.config.offset,t},t._getContainer=function(){return!1===this.config.container?document.body:_.isElement(this.config.container)?g(this.config.container):g(document).find(this.config.container)},t._getAttachment=function(t){return Pe[t.toUpperCase()]},t._setListeners=function(){var i=this;this.config.trigger.split(" ").forEach(function(t){if("click"===t)g(i.element).on(i.constructor.Event.CLICK,i.config.selector,function(t){return i.toggle(t)});else if(t!==Qe){var e=t===qe?i.constructor.Event.MOUSEENTER:i.constructor.Event.FOCUSIN,n=t===qe?i.constructor.Event.MOUSELEAVE:i.constructor.Event.FOCUSOUT;g(i.element).on(e,i.config.selector,function(t){return i._enter(t)}).on(n,i.config.selector,function(t){return i._leave(t)})}}),g(this.element).closest(".modal").on("hide.bs.modal",function(){i.element&&i.hide()}),this.config.selector?this.config=l({},this.config,{trigger:"manual",selector:""}):this._fixTitle()},t._fixTitle=function(){var t=typeof this.element.getAttribute("data-original-title");(this.element.getAttribute("title")||"string"!==t)&&(this.element.setAttribute("data-original-title",this.element.getAttribute("title")||""),this.element.setAttribute("title",""))},t._enter=function(t,e){var n=this.constructor.DATA_KEY;(e=e||g(t.currentTarget).data(n))||(e=new this.constructor(t.currentTarget,this._getDelegateConfig()),g(t.currentTarget).data(n,e)),t&&(e._activeTrigger["focusin"===t.type?Me:qe]=!0),g(e.getTipElement()).hasClass(Fe)||e._hoverState===je?e._hoverState=je:(clearTimeout(e._timeout),e._hoverState=je,e.config.delay&&e.config.delay.show?e._timeout=setTimeout(function(){e._hoverState===je&&e.show()},e.config.delay.show):e.show())},t._leave=function(t,e){var n=this.constructor.DATA_KEY;(e=e||g(t.currentTarget).data(n))||(e=new this.constructor(t.currentTarget,this._getDelegateConfig()),g(t.currentTarget).data(n,e)),t&&(e._activeTrigger["focusout"===t.type?Me:qe]=!1),e._isWithActiveTrigger()||(clearTimeout(e._timeout),e._hoverState=He,e.config.delay&&e.config.delay.hide?e._timeout=setTimeout(function(){e._hoverState===He&&e.hide()},e.config.delay.hide):e.hide())},t._isWithActiveTrigger=function(){for(var t in this._activeTrigger)if(this._activeTrigger[t])return!0;return!1},t._getConfig=function(t){var e=g(this.element).data();return Object.keys(e).forEach(function(t){-1!==Oe.indexOf(t)&&delete e[t]}),"number"==typeof(t=l({},this.constructor.Default,e,"object"==typeof t&&t?t:{})).delay&&(t.delay={show:t.delay,hide:t.delay}),"number"==typeof t.title&&(t.title=t.title.toString()),"number"==typeof t.content&&(t.content=t.content.toString()),_.typeCheckConfig(be,t,this.constructor.DefaultType),t.sanitize&&(t.template=Se(t.template,t.whiteList,t.sanitizeFn)),t},t._getDelegateConfig=function(){var t={};if(this.config)for(var e in this.config)this.constructor.Default[e]!==this.config[e]&&(t[e]=this.config[e]);return t},t._cleanTipClass=function(){var t=g(this.getTipElement()),e=t.attr("class").match(Ne);null!==e&&e.length&&t.removeClass(e.join(""))},t._handlePopperPlacementChange=function(t){var e=t.instance;this.tip=e.popper,this._cleanTipClass(),this.addAttachmentClass(this._getAttachment(t.placement))},t._fixTransition=function(){var t=this.getTipElement(),e=this.config.animation;null===t.getAttribute("x-placement")&&(g(t).removeClass(xe),this.config.animation=!1,this.hide(),this.show(),this.config.animation=e)},i._jQueryInterface=function(n){return this.each(function(){var t=g(this).data(Ie),e="object"==typeof n&&n;if((t||!/dispose|hide/.test(n))&&(t||(t=new i(this,e),g(this).data(Ie,t)),"string"==typeof n)){if("undefined"==typeof t[n])throw new TypeError('No method named "'+n+'"');t[n]()}})},s(i,null,[{key:"VERSION",get:function(){return"4.3.1"}},{key:"Default",get:function(){return Le}},{key:"NAME",get:function(){return be}},{key:"DATA_KEY",get:function(){return Ie}},{key:"Event",get:function(){return Re}},{key:"EVENT_KEY",get:function(){return De}},{key:"DefaultType",get:function(){return ke}}]),i}();g.fn[be]=Be._jQueryInterface,g.fn[be].Constructor=Be,g.fn[be].noConflict=function(){return g.fn[be]=we,Be._jQueryInterface};var Ve="popover",Ye="bs.popover",ze="."+Ye,Xe=g.fn[Ve],$e="bs-popover",Ge=new RegExp("(^|\\s)"+$e+"\\S+","g"),Je=l({},Be.Default,{placement:"right",trigger:"click",content:"",template:''}),Ze=l({},Be.DefaultType,{content:"(string|element|function)"}),tn="fade",en="show",nn=".popover-header",on=".popover-body",rn={HIDE:"hide"+ze,HIDDEN:"hidden"+ze,SHOW:"show"+ze,SHOWN:"shown"+ze,INSERTED:"inserted"+ze,CLICK:"click"+ze,FOCUSIN:"focusin"+ze,FOCUSOUT:"focusout"+ze,MOUSEENTER:"mouseenter"+ze,MOUSELEAVE:"mouseleave"+ze},sn=function(t){var e,n;function i(){return t.apply(this,arguments)||this}n=t,(e=i).prototype=Object.create(n.prototype),(e.prototype.constructor=e).__proto__=n;var o=i.prototype;return o.isWithContent=function(){return this.getTitle()||this._getContent()},o.addAttachmentClass=function(t){g(this.getTipElement()).addClass($e+"-"+t)},o.getTipElement=function(){return this.tip=this.tip||g(this.config.template)[0],this.tip},o.setContent=function(){var t=g(this.getTipElement());this.setElementContent(t.find(nn),this.getTitle());var e=this._getContent();"function"==typeof e&&(e=e.call(this.element)),this.setElementContent(t.find(on),e),t.removeClass(tn+" "+en)},o._getContent=function(){return this.element.getAttribute("data-content")||this.config.content},o._cleanTipClass=function(){var t=g(this.getTipElement()),e=t.attr("class").match(Ge);null!==e&&0=this._offsets[o]&&("undefined"==typeof this._offsets[o+1]||tthis._items.length-1||t<0))if(this._isSliding)g(this._element).one(Q.SLID,function(){return e.to(t)});else{if(n===t)return this.pause(),void this.cycle();var i=ndocument.documentElement.clientHeight;!this._isBodyOverflowing&&t&&(this._element.style.paddingLeft=this._scrollbarWidth+"px"),this._isBodyOverflowing&&!t&&(this._element.style.paddingRight=this._scrollbarWidth+"px")},t._resetAdjustments=function(){this._element.style.paddingLeft="",this._element.style.paddingRight=""},t._checkScrollbar=function(){var t=document.body.getBoundingClientRect();this._isBodyOverflowing=t.left+t.right
',trigger:"hover focus",title:"",delay:0,html:!1,selector:!1,placement:"top",offset:0,container:!1,fallbackPlacement:"flip",boundary:"scrollParent"},De="show",we="out",Ae={HIDE:"hide"+Ee,HIDDEN:"hidden"+Ee,SHOW:"show"+Ee,SHOWN:"shown"+Ee,INSERTED:"inserted"+Ee,CLICK:"click"+Ee,FOCUSIN:"focusin"+Ee,FOCUSOUT:"focusout"+Ee,MOUSEENTER:"mouseenter"+Ee,MOUSELEAVE:"mouseleave"+Ee},Ne="fade",Oe="show",ke=".tooltip-inner",Pe=".arrow",Le="hover",je="focus",He="click",Re="manual",Ue=function(){function i(t,e){if("undefined"==typeof u)throw new TypeError("Bootstrap's tooltips require Popper.js (https://popper.js.org/)");this._isEnabled=!0,this._timeout=0,this._hoverState="",this._activeTrigger={},this._popper=null,this.element=t,this.config=this._getConfig(e),this.tip=null,this._setListeners()}var t=i.prototype;return t.enable=function(){this._isEnabled=!0},t.disable=function(){this._isEnabled=!1},t.toggleEnabled=function(){this._isEnabled=!this._isEnabled},t.toggle=function(t){if(this._isEnabled)if(t){var e=this.constructor.DATA_KEY,n=g(t.currentTarget).data(e);n||(n=new this.constructor(t.currentTarget,this._getDelegateConfig()),g(t.currentTarget).data(e,n)),n._activeTrigger.click=!n._activeTrigger.click,n._isWithActiveTrigger()?n._enter(null,n):n._leave(null,n)}else{if(g(this.getTipElement()).hasClass(Oe))return void this._leave(null,this);this._enter(null,this)}},t.dispose=function(){clearTimeout(this._timeout),g.removeData(this.element,this.constructor.DATA_KEY),g(this.element).off(this.constructor.EVENT_KEY),g(this.element).closest(".modal").off("hide.bs.modal"),this.tip&&g(this.tip).remove(),this._isEnabled=null,this._timeout=null,this._hoverState=null,(this._activeTrigger=null)!==this._popper&&this._popper.destroy(),this._popper=null,this.element=null,this.config=null,this.tip=null},t.show=function(){var e=this;if("none"===g(this.element).css("display"))throw new Error("Please use show on visible elements");var t=g.Event(this.constructor.Event.SHOW);if(this.isWithContent()&&this._isEnabled){g(this.element).trigger(t);var n=_.findShadowRoot(this.element),i=g.contains(null!==n?n:this.element.ownerDocument.documentElement,this.element);if(t.isDefaultPrevented()||!i)return;var o=this.getTipElement(),r=_.getUID(this.constructor.NAME);o.setAttribute("id",r),this.element.setAttribute("aria-describedby",r),this.setContent(),this.config.animation&&g(o).addClass(Ne);var s="function"==typeof this.config.placement?this.config.placement.call(this,o,this.element):this.config.placement,a=this._getAttachment(s);this.addAttachmentClass(a);var l=this._getContainer();g(o).data(this.constructor.DATA_KEY,this),g.contains(this.element.ownerDocument.documentElement,this.tip)||g(o).appendTo(l),g(this.element).trigger(this.constructor.Event.INSERTED),this._popper=new u(this.element,o,{placement:a,modifiers:{offset:{offset:this.config.offset},flip:{behavior:this.config.fallbackPlacement},arrow:{element:Pe},preventOverflow:{boundariesElement:this.config.boundary}},onCreate:function(t){t.originalPlacement!==t.placement&&e._handlePopperPlacementChange(t)},onUpdate:function(t){return e._handlePopperPlacementChange(t)}}),g(o).addClass(Oe),"ontouchstart"in document.documentElement&&g(document.body).children().on("mouseover",null,g.noop);var c=function(){e.config.animation&&e._fixTransition();var t=e._hoverState;e._hoverState=null,g(e.element).trigger(e.constructor.Event.SHOWN),t===we&&e._leave(null,e)};if(g(this.tip).hasClass(Ne)){var h=_.getTransitionDurationFromElement(this.tip);g(this.tip).one(_.TRANSITION_END,c).emulateTransitionEnd(h)}else c()}},t.hide=function(t){var e=this,n=this.getTipElement(),i=g.Event(this.constructor.Event.HIDE),o=function(){e._hoverState!==De&&n.parentNode&&n.parentNode.removeChild(n),e._cleanTipClass(),e.element.removeAttribute("aria-describedby"),g(e.element).trigger(e.constructor.Event.HIDDEN),null!==e._popper&&e._popper.destroy(),t&&t()};if(g(this.element).trigger(i),!i.isDefaultPrevented()){if(g(n).removeClass(Oe),"ontouchstart"in document.documentElement&&g(document.body).children().off("mouseover",null,g.noop),this._activeTrigger[He]=!1,this._activeTrigger[je]=!1,this._activeTrigger[Le]=!1,g(this.tip).hasClass(Ne)){var r=_.getTransitionDurationFromElement(n);g(n).one(_.TRANSITION_END,o).emulateTransitionEnd(r)}else o();this._hoverState=""}},t.update=function(){null!==this._popper&&this._popper.scheduleUpdate()},t.isWithContent=function(){return Boolean(this.getTitle())},t.addAttachmentClass=function(t){g(this.getTipElement()).addClass(Ce+"-"+t)},t.getTipElement=function(){return this.tip=this.tip||g(this.config.template)[0],this.tip},t.setContent=function(){var t=this.getTipElement();this.setElementContent(g(t.querySelectorAll(ke)),this.getTitle()),g(t).removeClass(Ne+" "+Oe)},t.setElementContent=function(t,e){var n=this.config.html;"object"==typeof e&&(e.nodeType||e.jquery)?n?g(e).parent().is(t)||t.empty().append(e):t.text(g(e).text()):t[n?"html":"text"](e)},t.getTitle=function(){var t=this.element.getAttribute("data-original-title");return t||(t="function"==typeof this.config.title?this.config.title.call(this.element):this.config.title),t},t._getContainer=function(){return!1===this.config.container?document.body:_.isElement(this.config.container)?g(this.config.container):g(document).find(this.config.container)},t._getAttachment=function(t){return be[t.toUpperCase()]},t._setListeners=function(){var i=this;this.config.trigger.split(" ").forEach(function(t){if("click"===t)g(i.element).on(i.constructor.Event.CLICK,i.config.selector,function(t){return i.toggle(t)});else if(t!==Re){var e=t===Le?i.constructor.Event.MOUSEENTER:i.constructor.Event.FOCUSIN,n=t===Le?i.constructor.Event.MOUSELEAVE:i.constructor.Event.FOCUSOUT;g(i.element).on(e,i.config.selector,function(t){return i._enter(t)}).on(n,i.config.selector,function(t){return i._leave(t)})}}),g(this.element).closest(".modal").on("hide.bs.modal",function(){i.element&&i.hide()}),this.config.selector?this.config=l({},this.config,{trigger:"manual",selector:""}):this._fixTitle()},t._fixTitle=function(){var t=typeof this.element.getAttribute("data-original-title");(this.element.getAttribute("title")||"string"!==t)&&(this.element.setAttribute("data-original-title",this.element.getAttribute("title")||""),this.element.setAttribute("title",""))},t._enter=function(t,e){var n=this.constructor.DATA_KEY;(e=e||g(t.currentTarget).data(n))||(e=new this.constructor(t.currentTarget,this._getDelegateConfig()),g(t.currentTarget).data(n,e)),t&&(e._activeTrigger["focusin"===t.type?je:Le]=!0),g(e.getTipElement()).hasClass(Oe)||e._hoverState===De?e._hoverState=De:(clearTimeout(e._timeout),e._hoverState=De,e.config.delay&&e.config.delay.show?e._timeout=setTimeout(function(){e._hoverState===De&&e.show()},e.config.delay.show):e.show())},t._leave=function(t,e){var n=this.constructor.DATA_KEY;(e=e||g(t.currentTarget).data(n))||(e=new this.constructor(t.currentTarget,this._getDelegateConfig()),g(t.currentTarget).data(n,e)),t&&(e._activeTrigger["focusout"===t.type?je:Le]=!1),e._isWithActiveTrigger()||(clearTimeout(e._timeout),e._hoverState=we,e.config.delay&&e.config.delay.hide?e._timeout=setTimeout(function(){e._hoverState===we&&e.hide()},e.config.delay.hide):e.hide())},t._isWithActiveTrigger=function(){for(var t in this._activeTrigger)if(this._activeTrigger[t])return!0;return!1},t._getConfig=function(t){return"number"==typeof(t=l({},this.constructor.Default,g(this.element).data(),"object"==typeof t&&t?t:{})).delay&&(t.delay={show:t.delay,hide:t.delay}),"number"==typeof t.title&&(t.title=t.title.toString()),"number"==typeof t.content&&(t.content=t.content.toString()),_.typeCheckConfig(pe,t,this.constructor.DefaultType),t},t._getDelegateConfig=function(){var t={};if(this.config)for(var e in this.config)this.constructor.Default[e]!==this.config[e]&&(t[e]=this.config[e]);return t},t._cleanTipClass=function(){var t=g(this.getTipElement()),e=t.attr("class").match(Te);null!==e&&e.length&&t.removeClass(e.join(""))},t._handlePopperPlacementChange=function(t){var e=t.instance;this.tip=e.popper,this._cleanTipClass(),this.addAttachmentClass(this._getAttachment(t.placement))},t._fixTransition=function(){var t=this.getTipElement(),e=this.config.animation;null===t.getAttribute("x-placement")&&(g(t).removeClass(Ne),this.config.animation=!1,this.hide(),this.show(),this.config.animation=e)},i._jQueryInterface=function(n){return this.each(function(){var t=g(this).data(ve),e="object"==typeof n&&n;if((t||!/dispose|hide/.test(n))&&(t||(t=new i(this,e),g(this).data(ve,t)),"string"==typeof n)){if("undefined"==typeof t[n])throw new TypeError('No method named "'+n+'"');t[n]()}})},s(i,null,[{key:"VERSION",get:function(){return"4.2.1"}},{key:"Default",get:function(){return Ie}},{key:"NAME",get:function(){return pe}},{key:"DATA_KEY",get:function(){return ve}},{key:"Event",get:function(){return Ae}},{key:"EVENT_KEY",get:function(){return Ee}},{key:"DefaultType",get:function(){return Se}}]),i}();g.fn[pe]=Ue._jQueryInterface,g.fn[pe].Constructor=Ue,g.fn[pe].noConflict=function(){return g.fn[pe]=ye,Ue._jQueryInterface};var We="popover",xe="bs.popover",Fe="."+xe,qe=g.fn[We],Me="bs-popover",Ke=new RegExp("(^|\\s)"+Me+"\\S+","g"),Qe=l({},Ue.Default,{placement:"right",trigger:"click",content:"",template:''}),Be=l({},Ue.DefaultType,{content:"(string|element|function)"}),Ve="fade",Ye="show",Xe=".popover-header",ze=".popover-body",Ge={HIDE:"hide"+Fe,HIDDEN:"hidden"+Fe,SHOW:"show"+Fe,SHOWN:"shown"+Fe,INSERTED:"inserted"+Fe,CLICK:"click"+Fe,FOCUSIN:"focusin"+Fe,FOCUSOUT:"focusout"+Fe,MOUSEENTER:"mouseenter"+Fe,MOUSELEAVE:"mouseleave"+Fe},Je=function(t){var e,n;function i(){return t.apply(this,arguments)||this}n=t,(e=i).prototype=Object.create(n.prototype),(e.prototype.constructor=e).__proto__=n;var o=i.prototype;return o.isWithContent=function(){return this.getTitle()||this._getContent()},o.addAttachmentClass=function(t){g(this.getTipElement()).addClass(Me+"-"+t)},o.getTipElement=function(){return this.tip=this.tip||g(this.config.template)[0],this.tip},o.setContent=function(){var t=g(this.getTipElement());this.setElementContent(t.find(Xe),this.getTitle());var e=this._getContent();"function"==typeof e&&(e=e.call(this.element)),this.setElementContent(t.find(ze),e),t.removeClass(Ve+" "+Ye)},o._getContent=function(){return this.element.getAttribute("data-content")||this.config.content},o._cleanTipClass=function(){var t=g(this.getTipElement()),e=t.attr("class").match(Ke);null!==e&&0=this._offsets[o]&&("undefined"==typeof this._offsets[o+1]||t Date: Sat, 19 Oct 2019 22:20:35 +0900 Subject: [PATCH 7/7] Fix for Issue #142 --- Monitor/Pages/SettingsGeneral.cshtml.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Monitor/Pages/SettingsGeneral.cshtml.cs b/Monitor/Pages/SettingsGeneral.cshtml.cs index 2b25ccf..a144b7b 100644 --- a/Monitor/Pages/SettingsGeneral.cshtml.cs +++ b/Monitor/Pages/SettingsGeneral.cshtml.cs @@ -67,12 +67,12 @@ namespace Monitor.Pages PTMagicConfiguration.GeneralSettings.Application.IsEnabled = HttpContext.Request.Form["Application_IsEnabled"].Equals("on"); PTMagicConfiguration.GeneralSettings.Application.TestMode = HttpContext.Request.Form["Application_TestMode"].Equals("on"); - PTMagicConfiguration.GeneralSettings.Application.Exchange = HttpContext.Request.Form["Application_Exchange"]; PTMagicConfiguration.GeneralSettings.Application.StartBalance = SystemHelper.TextToDouble(HttpContext.Request.Form["Application_StartBalance"], PTMagicConfiguration.GeneralSettings.Application.StartBalance, "en-US"); - PTMagicConfiguration.GeneralSettings.Application.TimezoneOffset = HttpContext.Request.Form["Application_TimezoneOffset"].ToString().Replace(" ", ""); + PTMagicConfiguration.GeneralSettings.Application.ProfitTrailerDefaultSettingName = HttpContext.Request.Form["Application_ProfitTrailerDefaultSettingName"]; PTMagicConfiguration.GeneralSettings.Application.FloodProtectionMinutes = SystemHelper.TextToInteger(HttpContext.Request.Form["Application_FloodProtectionMinutes"], PTMagicConfiguration.GeneralSettings.Application.FloodProtectionMinutes); PTMagicConfiguration.GeneralSettings.Application.InstanceName = HttpContext.Request.Form["Application_InstanceName"]; PTMagicConfiguration.GeneralSettings.Application.CoinMarketCapAPIKey = HttpContext.Request.Form["Application_CoinMarketCapAPIKey"]; + PTMagicConfiguration.GeneralSettings.Application.FreeCurrencyConverterAPIKey = HttpContext.Request.Form["Application_FreeCurrencyConverterAPIKey"]; PTMagicConfiguration.GeneralSettings.Monitor.IsPasswordProtected = HttpContext.Request.Form["Monitor_IsPasswordProtected"].Equals("on"); PTMagicConfiguration.GeneralSettings.Monitor.OpenBrowserOnStart = HttpContext.Request.Form["Monitor_OpenBrowserOnStart"].Equals("on");