From e23e2f2dfee009d4ff8bd87f7646916f68ccf827 Mon Sep 17 00:00:00 2001 From: EarnForex <48102957+EarnForex@users.noreply.github.com> Date: Thu, 20 Jul 2023 16:38:22 +0200 Subject: [PATCH] 3.04 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 1. Added a dark theme mode, which can be set via the DarkMode input parameter. 2. Added an option to display breakeven lines at levels where the Position Sizer will apply breakeven to existing positions. 3. Added the Entry line label to display the distance from the current price to the Entry level for pending orders. 4. Added input parameters (ShowMaxParametersOnTrading, ShowFusesOnTrading, and ShowCheckboxesOnTrading) to make the Trading tab more compact. 5. Added separate total and per-symbol fields to control volume, risk, and number of trades on the Trading tab. 6. Added an input parameter (SettingsFile) to let users load their own custom settings file with panel fields configured according to their needs. The EA won't delete custom settings files. 7. Added two new hotkeys — to set a stop-loss (SetStopLossHotKey) and a take-profit (SetTakeProfitHotKey) to the price level at the mouse pointer's current position. 8. Added an option to change the translation of the panel's interface in MetaTrader 5. Language files are currently only available for Ukrainian and Russian. Users can create and use their own translation files. 9. Changed the breakeven mechanism to take into account the size of the commission if UseCommissionToSetTPDistance is set to true. 10. Changed the additional TP fields to appear with some non-zero value if the main TP is non-zero. 11. Fixed a bug when switching the chart's symbol could result in line labels disappearing if SymbolChange was set to Keep panel as is. 12. Fixed a bug in the MT5 version that resulted in the trade type not resetting properly when SymbolChange was set to Reset to defaults on symbol change. 13. Fixed a bug that resulted in false warnings and incorrect position size calculation when the EA failed to get the symbol information at the first attempt. 14. Fixed a bug that resulted in some of the +/- buttons to remain on the chart when the panel was minimized. 15. Fixed a bug that resulted in the stop-loss not keeping its correct distance when SLDistanceInPoints was set to true. 16. Fixed a bug when the additional funds asterisk remained visible even when the panel was minimized. 17. Fixed a bug in the MT5 version that resulted in the risk field resetting to default when the user clicked on the position size field after setting it to a custom value. 18. Fixed a bug that resulted in the stop-loss line sometimes disappearing on a symbol change. 19. Fixed a bug in the MT5 version that resulted in the Stop Price line appearing after switching from Stop Limit to Instant and setting the DisableStopLimit input parameter to true. 20. Fixed a bug that would result in wrong value appearing in the account size field after clicking on it and then clicking outside if the value contained a thousands separator. 21. Fixed a bug in the MT5 version that caused a critical 'array out of range' error when clicking on the +/- buttons for a single take-profit field. 22. Fixed a bug in the MT4 version that caused a critical 'array out of range' error when switching the chart symbol to a one with more additional TPs saved in a settings file. 23. Fixed a bug that caused the risk to be calculated based on the percentage value instead of the money value when Custom Balance was updated even if the MoneyRisk parameter was greater than 0. 24. Fixed a bug with ATR timeframe button not working. 25. Fixed a bug with incorrect volume share allocation when adding a new TP. 26. Fixed a bug in the MT5 version that caused a critical 'stack overflow' error when the EA failed to convert a symbol's profit or margin currency. 27. Fixed a bug that would cause TP values set in points to shift when dragging doing some unrelated chart manipulations. --- MQL4/Experts/Position Sizer/Defines.mqh | 33 +- .../Position Sizer/EF-Icon-64x64px.ico | Bin 0 -> 2686 bytes .../Position Sizer/Position Sizer Trading.mqh | 156 +- .../Experts/Position Sizer/Position Sizer.mq4 | 263 ++- .../Experts/Position Sizer/Position Sizer.mqh | 792 ++++++--- MQL5/Experts/Position Sizer/Defines.mqh | 31 +- .../Position Sizer/EF-Icon-64x64px.ico | Bin 0 -> 2686 bytes .../Position Sizer/Position Sizer Trading.mqh | Bin 76412 -> 98358 bytes .../Experts/Position Sizer/Position Sizer.mq5 | 255 ++- .../Experts/Position Sizer/Position Sizer.mqh | 1432 ++++++++++------- .../Position Sizer/Translations/English.mqh | 303 ++++ .../Position Sizer/Translations/Russian.mqh | 298 ++++ .../Position Sizer/Translations/Ukrainian.mqh | 300 ++++ 13 files changed, 2878 insertions(+), 985 deletions(-) create mode 100644 MQL4/Experts/Position Sizer/EF-Icon-64x64px.ico create mode 100644 MQL5/Experts/Position Sizer/EF-Icon-64x64px.ico create mode 100644 MQL5/Experts/Position Sizer/Translations/English.mqh create mode 100644 MQL5/Experts/Position Sizer/Translations/Russian.mqh create mode 100644 MQL5/Experts/Position Sizer/Translations/Ukrainian.mqh diff --git a/MQL4/Experts/Position Sizer/Defines.mqh b/MQL4/Experts/Position Sizer/Defines.mqh index 4a5e668..8dcd479 100644 --- a/MQL4/Experts/Position Sizer/Defines.mqh +++ b/MQL4/Experts/Position Sizer/Defines.mqh @@ -9,11 +9,19 @@ #include #include -#define CONTROLS_EDIT_COLOR_ENABLE C'255,255,255' -#define CONTROLS_EDIT_COLOR_DISABLE C'221,221,211' +color CONTROLS_EDIT_COLOR_ENABLE = C'255,255,255'; +color CONTROLS_EDIT_COLOR_DISABLE = C'221,221,211'; -#define CONTROLS_BUTTON_COLOR_ENABLE C'200,200,200' -#define CONTROLS_BUTTON_COLOR_DISABLE C'224,224,224' +color CONTROLS_BUTTON_COLOR_ENABLE = C'200,200,200'; +color CONTROLS_BUTTON_COLOR_DISABLE = C'224,224,224'; + +color DARKMODE_BG_DARK_COLOR = 0x444444; +color DARKMODE_CONTROL_BRODER_COLOR = 0x888888; +color DARKMODE_MAIN_AREA_BORDER_COLOR = 0x333333; +color DARKMODE_MAIN_AREA_BG_COLOR = 0x666666; +color DARKMODE_EDIT_BG_COLOR = 0xAAAAAA; +color DARKMODE_BUTTON_BG_COLOR = 0xA19999; +color DARKMODE_TEXT_COLOR = 0x000000;; enum ENTRY_TYPE { @@ -82,6 +90,13 @@ enum COMMISSION_TYPE COMMISSION_PERCENT, // Percentage }; +enum CALCULATE_RISK_FOR_TRADING_TAB +{ + CALCULATE_RISK_FOR_TRADING_TAB_NO, // Normal calculation + CALCULATE_RISK_FOR_TRADING_TAB_TOTAL, // For Trading tab - total + CALCULATE_RISK_FOR_TRADING_TAB_PER_SYMBOL // For Trading tab - per symbol +}; + struct Settings { ENTRY_TYPE EntryType; @@ -116,7 +131,6 @@ struct Settings int MaxSpread; int MaxEntrySLDistance; int MinEntrySLDistance; - double MaxPositionSize; // For SL/TP distance modes: int StopLoss; int TakeProfit; @@ -131,9 +145,12 @@ struct Settings bool CommentAutoSuffix; int TrailingStopPoints; int BreakEvenPoints; - int MaxNumberOfTrades; - bool AllSymbols; - double MaxTotalRisk; + int MaxNumberOfTradesTotal; + int MaxNumberOfTradesPerSymbol; + double MaxPositionSizeTotal; + double MaxPositionSizePerSymbol; + double MaxRiskTotal; + double MaxRiskPerSymbol; // For ATR: int ATRPeriod; double ATRMultiplierSL; diff --git a/MQL4/Experts/Position Sizer/EF-Icon-64x64px.ico b/MQL4/Experts/Position Sizer/EF-Icon-64x64px.ico new file mode 100644 index 0000000000000000000000000000000000000000..30c9d729d1b7cafcb9c1b272402220fd54da61d1 GIT binary patch literal 2686 zcmZQzU<5)32LT|-!jQqmz#zuJz@P!d4nW)h#2|58pstI9;pjzwT+*ZB!zBa+u>-jG zuuBV$%0okd*5LyWXfOkA8>%pzH!2Se0eFa@GDr^}xDHeX+*nj$IB!%Q8UpYTL1j=a ieBcIw8E{Kbh2gwWd1wg0Lj;vU>+nIfZIm}`LjVArAv>u6 literal 0 HcmV?d00001 diff --git a/MQL4/Experts/Position Sizer/Position Sizer Trading.mqh b/MQL4/Experts/Position Sizer/Position Sizer Trading.mqh index 341a3a0..7101c41 100644 --- a/MQL4/Experts/Position Sizer/Position Sizer Trading.mqh +++ b/MQL4/Experts/Position Sizer/Position Sizer Trading.mqh @@ -98,34 +98,39 @@ void Trade() } } - if (sets.MaxNumberOfTrades > 0) + if ((sets.MaxNumberOfTradesTotal > 0) || (sets.MaxNumberOfTradesPerSymbol > 0)) { int total = OrdersTotal(); - int cnt = 0; + int cnt = 0, persymbol_cnt = 0; for (int i = 0; i < total; i++) { if (!OrderSelect(i, SELECT_BY_POS)) continue; if ((sets.MagicNumber != 0) && (OrderMagicNumber() != sets.MagicNumber)) continue; - if ((!sets.AllSymbols) && (OrderSymbol() != Symbol())) continue; + if (OrderSymbol() == Symbol()) persymbol_cnt++; cnt++; } - if (cnt >= sets.MaxNumberOfTrades) + if ((cnt + sets.TakeProfitsNumber > sets.MaxNumberOfTradesTotal) && (sets.MaxNumberOfTradesTotal > 0)) { - Alert("Not taking a trade - current # of traes (", cnt, ") >= maximum number of trades (", sets.MaxNumberOfTrades, ")."); + Alert("Not taking a trade - current total # of trades (", cnt, ") + number of trades in execution (", sets.TakeProfitsNumber, ") > maximum total number of trades allowed (", sets.MaxNumberOfTradesTotal, ")."); + return; + } + if ((persymbol_cnt + sets.TakeProfitsNumber > sets.MaxNumberOfTradesPerSymbol) && (sets.MaxNumberOfTradesPerSymbol > 0)) + { + Alert("Not taking a trade - current # of trades per symbol (", persymbol_cnt, ") + number of trades in execution (", sets.TakeProfitsNumber, ") > maximum number of trades per symbol allowed (", sets.MaxNumberOfTradesPerSymbol, ")."); return; } } - if (sets.MaxTotalRisk > 0) + if (sets.MaxRiskTotal > 0) { - CalculatePortfolioRisk(true); + CalculatePortfolioRisk(CALCULATE_RISK_FOR_TRADING_TAB_TOTAL); double risk; if (PortfolioLossMoney != DBL_MAX) { risk = (PortfolioLossMoney + OutputRiskMoney) / AccSize * 100; - if (risk > sets.MaxTotalRisk) + if (risk > sets.MaxRiskTotal) { - Alert("Not taking a trade - total potential risk (", DoubleToString(risk, 2), ") >= maximum risk (", DoubleToString(sets.MaxTotalRisk, 2), ")."); + Alert("Not taking a trade - total potential risk (", DoubleToString(risk, 2), ") >= maximum total risk allowed (", DoubleToString(sets.MaxRiskTotal, 2), ")."); return; } } @@ -135,6 +140,25 @@ void Trade() return; } } + if (sets.MaxRiskPerSymbol > 0) + { + CalculatePortfolioRisk(CALCULATE_RISK_FOR_TRADING_TAB_PER_SYMBOL); + double risk; + if (PortfolioLossMoney != DBL_MAX) + { + risk = (PortfolioLossMoney + OutputRiskMoney) / AccSize * 100; + if (risk > sets.MaxRiskPerSymbol) + { + Alert("Not taking a trade - potential risk per symbol (", DoubleToString(risk, 2), ") >= maximum risk per symbol allowed (", DoubleToString(sets.MaxRiskPerSymbol, 2), ")."); + return; + } + } + else + { + Alert("Not taking a trade - infinite potential risk per symbol."); + return; + } + } ENUM_SYMBOL_TRADE_EXECUTION Execution_Mode = (ENUM_SYMBOL_TRADE_EXECUTION)SymbolInfoInteger(Symbol(), SYMBOL_TRADE_EXEMODE); string warning_suffix = ""; @@ -189,20 +213,25 @@ void Trade() } } - if (sets.MaxPositionSize > 0) + if ((sets.MaxPositionSizeTotal > 0) && (sets.MaxPositionSizePerSymbol > 0)) { int total = OrdersTotal(); - double volume = 0; + double volume = 0, volume_persymbol = 0; for (int i = 0; i < total; i++) { if (!OrderSelect(i, SELECT_BY_POS)) continue; if ((sets.MagicNumber != 0) && (OrderMagicNumber() != sets.MagicNumber)) continue; - if ((!sets.AllSymbols) && (OrderSymbol() != Symbol())) continue; + if (OrderSymbol() == Symbol()) volume_persymbol += OrderLots(); volume += OrderLots(); } - if (volume + PositionSize > sets.MaxPositionSize) + if ((volume + PositionSize > sets.MaxPositionSizeTotal) && (sets.MaxPositionSizeTotal > 0)) { - Alert("Not taking a trade - current total volume (", DoubleToString(volume, LotStep_digits), ") + new position volume (", DoubleToString(PositionSize, LotStep_digits), ") >= maximum total volume (", sets.MaxPositionSize, ")."); + Alert("Not taking a trade - current total volume (", DoubleToString(volume, LotStep_digits), ") + new position volume (", DoubleToString(PositionSize, LotStep_digits), ") >= maximum total volume allowed (", DoubleToString(sets.MaxPositionSizeTotal, LotStep_digits), ")."); + return; + } + if ((volume_persymbol + PositionSize > sets.MaxPositionSizePerSymbol) && (sets.MaxPositionSizePerSymbol > 0)) + { + Alert("Not taking a trade - current volume per symbol (", DoubleToString(volume_persymbol, LotStep_digits), ") + new position volume (", DoubleToString(PositionSize, LotStep_digits), ") >= maximum volume per symbol allowed (", DoubleToString(sets.MaxPositionSizePerSymbol, LotStep_digits), ")."); return; } } @@ -480,7 +509,38 @@ void DoTrailingStop() // Sets SL to breakeven based on the Magic number and symbol. void DoBreakEven() { - if ((!TerminalInfoInteger(TERMINAL_TRADE_ALLOWED)) || (!TerminalInfoInteger(TERMINAL_CONNECTED)) || (!MQLInfoInteger(MQL_TRADE_ALLOWED))) return; + if (!TerminalInfoInteger(TERMINAL_CONNECTED)) return; + + // Delete old BE lines if necessary. + if (be_line_color != clrNONE) + { + int obj_total = ObjectsTotal(ChartID(), -1, OBJ_HLINE); + for (int i = obj_total - 1; i >= 0; i--) + { + string obj_name = ObjectName(ChartID(), i, -1, OBJ_HLINE); + if (StringFind(obj_name, ObjectPrefix + "BE") == -1) continue; // Skip all other horizontal lines. + int ticket = (int)StringToInteger(StringSubstr(obj_name, StringLen(ObjectPrefix + "BE"))); + if (!OrderSelect(ticket, SELECT_BY_TICKET)) // No longer exists. + { + ObjectDelete(ChartID(), obj_name); // Delete the line. + if (ShowLineLabels) ObjectDelete(ChartID(), ObjectPrefix + "BEL" + IntegerToString(ticket)); // Delete the label. + } + else // Check if already triggered. Order selected. + { + double be_price = NormalizeDouble(StringToDouble(ObjectGetString(ChartID(), obj_name, OBJPROP_TOOLTIP)), _Digits); + if (((OrderType() == OP_BUY) && (OrderStopLoss() >= be_price)) // Already triggered. + || ((OrderType() == OP_SELL) && (OrderStopLoss() <= be_price) && (OrderStopLoss() != 0))) + { + ObjectDelete(ChartID(), obj_name); // Delete the line. + if (ShowLineLabels) ObjectDelete(ChartID(), ObjectPrefix + "BEL" + IntegerToString(ticket)); // Delete the label. + } + } + } + } + + if (sets.BreakEvenPoints <= 0) return; + + if ((!TerminalInfoInteger(TERMINAL_TRADE_ALLOWED)) || (!MQLInfoInteger(MQL_TRADE_ALLOWED))) return; for (int i = 0; i < OrdersTotal(); i++) { @@ -489,13 +549,30 @@ void DoBreakEven() else { if ((OrderSymbol() != Symbol()) || (OrderMagicNumber() != sets.MagicNumber)) continue; + + // Based on the commission if UseCommissionToSetTPDistance is set to true. + double extra_be_distance = 0; + if ((UseCommissionToSetTPDistance) && (sets.CommissionPerLot != 0)) + { + // Calculate real commission in currency units. + double commission = CalculateCommission(); + + // Extra BE Distance = Commission Size / Point_value. + // Commission Size = Commission * 2. + // Extra BE Distance = Commission * 2 / Point_value. + if ((UnitCost_reward != 0) && (TickSize != 0)) + extra_be_distance = commission * 2 / (UnitCost_reward / TickSize); + } + if (OrderType() == OP_BUY) { - double BE = NormalizeDouble(OrderOpenPrice() + sets.BreakEvenPoints * _Point, _Digits); - if ((Bid >= BE) && (OrderOpenPrice() > OrderStopLoss())) // Only move to breakeven if the current stop-loss is lower. + double BE_threshold = NormalizeDouble(OrderOpenPrice() + sets.BreakEvenPoints * _Point, _Digits); + double BE_price = NormalizeDouble(OrderOpenPrice() + extra_be_distance, _Digits); + if ((be_line_color != clrNONE) && (BE_price > OrderStopLoss())) DrawBELine(OrderTicket(), BE_threshold, BE_price); // Only draw if not triggered yet. + if ((Bid >= BE_threshold) && (Bid >= BE_price) && (BE_price > OrderStopLoss())) // Only move to BE if the price reached the necessary threshold, the price is above the calculated BE price, and the current stop-loss is lower. { // Write Open price to the SL field. - if (!OrderModify(OrderTicket(), OrderOpenPrice(), OrderOpenPrice(), OrderTakeProfit(), OrderExpiration())) + if (!OrderModify(OrderTicket(), OrderOpenPrice(), BE_price, OrderTakeProfit(), OrderExpiration())) Print("OrderModify Buy BE failed " + ErrorDescription(GetLastError()) + "."); else Print("Breakeven was applied to position - " + Symbol() + " BUY-order #" + IntegerToString(OrderTicket()) + " Lotsize = " + DoubleToString(OrderLots(), LotStep_digits) + ", OpenPrice = " + DoubleToString(OrderOpenPrice(), _Digits) + ", Stop-Loss was moved from " + DoubleToString(OrderStopLoss(), _Digits) + "."); @@ -503,11 +580,13 @@ void DoBreakEven() } else if (OrderType() == OP_SELL) { - double BE = NormalizeDouble(OrderOpenPrice() - sets.BreakEvenPoints * _Point, _Digits); - if ((Ask <= BE) && ((OrderOpenPrice() < OrderStopLoss()) || (OrderStopLoss() == 0))) // Only move to breakeven if the current stop-loss is higher (or zero). + double BE_threshold = NormalizeDouble(OrderOpenPrice() - sets.BreakEvenPoints * _Point, _Digits); + double BE_price = NormalizeDouble(OrderOpenPrice() - extra_be_distance, _Digits); + if ((be_line_color != clrNONE) && ((BE_price < OrderStopLoss()) || (OrderStopLoss() == 0))) DrawBELine(OrderTicket(), BE_threshold, BE_price); + if ((Ask <= BE_threshold) && (Ask <= BE_price) && ((BE_price < OrderStopLoss()) || (OrderStopLoss() == 0))) // Only move to BE if the price reached the necessary threshold, the price below the calculated BE price, and the current stop-loss is higher (or zero). { // Write Open price to the SL field. - if (!OrderModify(OrderTicket(), OrderOpenPrice(), OrderOpenPrice(), OrderTakeProfit(), OrderExpiration())) + if (!OrderModify(OrderTicket(), OrderOpenPrice(), BE_price, OrderTakeProfit(), OrderExpiration())) Print("OrderModify Sell BE failed " + ErrorDescription(GetLastError()) + "."); else Print("Breakeven was applied to position - " + Symbol() + " SELL-order #" + IntegerToString(OrderTicket()) + " Lotsize = " + DoubleToString(OrderLots(), LotStep_digits) + ", OpenPrice = " + DoubleToString(OrderOpenPrice(), _Digits) + ", Stop-Loss was moved from " + DoubleToString(OrderStopLoss(), _Digits) + "."); @@ -516,4 +595,39 @@ void DoBreakEven() } } } + +void DrawBELine(int ticket, double be_threshold, double be_price) +{ + string obj_name = ObjectPrefix + "BE" + IntegerToString(ticket); // Line. + ObjectCreate(ChartID(), obj_name, OBJ_HLINE, 0, TimeCurrent(), be_threshold); + ObjectSetDouble(ChartID(), obj_name, OBJPROP_PRICE, be_threshold); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_STYLE, be_line_style); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_COLOR, be_line_color); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_WIDTH, be_line_width); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_SELECTABLE, false); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BACK, true); + ObjectSetString(ChartID(), obj_name, OBJPROP_TOOLTIP, DoubleToString(be_price, _Digits)); // Store BE price in the tooltip. + + if (sets.ShowLines) ObjectSetInteger(ChartID(), obj_name, OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), obj_name, OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + + if (ShowLineLabels) + { + obj_name = ObjectPrefix + "BEL" + IntegerToString(ticket); // Label. + ObjectCreate(ChartID(), obj_name, OBJ_LABEL, 0, 0, 0); + if (sets.ShowLines) ObjectSetInteger(ChartID(), obj_name, OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), obj_name, OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_COLOR, clrNONE); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_SELECTABLE, false); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_HIDDEN, false); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_CORNER, CORNER_LEFT_UPPER); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BACK, DrawTextAsBackground); + ObjectSetString(ChartID(), obj_name, OBJPROP_TOOLTIP, ""); + string text = "BE for "; + if (OrderType() == OP_BUY) text += "Buy"; + else if (OrderType() == OP_SELL) text += "Sell"; + text += " #" + IntegerToString(ticket); + DrawLineLabel(obj_name, text, be_threshold, be_line_color, false, -6); + } +} //+------------------------------------------------------------------+ \ No newline at end of file diff --git a/MQL4/Experts/Position Sizer/Position Sizer.mq4 b/MQL4/Experts/Position Sizer/Position Sizer.mq4 index 1212aad..0795e0f 100644 --- a/MQL4/Experts/Position Sizer/Position Sizer.mq4 +++ b/MQL4/Experts/Position Sizer/Position Sizer.mq4 @@ -5,8 +5,9 @@ //+------------------------------------------------------------------+ #property copyright "EarnForex.com" #property link "https://www.earnforex.com/metatrader-expert-advisors/Position-Sizer/" -#property version "3.03" -string Version = "3.03"; +#property icon "EF-Icon-64x64px.ico" +#property version "3.04" +string Version = "3.04"; #property strict #property description "Calculates risk-based position size for your account." @@ -28,10 +29,14 @@ input bool ShowPointValue = false; // ShowPointValue: Show point value? input bool ShowMaxPSButton = false; // ShowMaxPSButton: Show Max Position Size button? input bool StartPanelMinimized = false; // StartPanelMinimized: Start the panel minimized? input bool ShowATROptions = false; // ShowATROptions: If true, SL and TP can be set via ATR. +input bool ShowMaxParametersOnTrading = true; // Show max parameters on Trading tab? +input bool ShowFusesOnTrading = true; // Show trading "fuses" on Trading tab? +input bool ShowCheckboxesOnTrading = true; // Show checkboxes on Trading tab? input group "Fonts" input string ____Fonts = ""; input color sl_label_font_color = clrLime; // SL Label Color input color tp_label_font_color = clrYellow; // TP Label Font Color +input color entry_label_font_color = clrBlue; // Entry Label Font Color input uint font_size = 13; // Labels Font Size input string font_face = "Courier"; // Labels Font Face input group "Lines" @@ -39,12 +44,15 @@ input string ____Lines = ""; input color entry_line_color = clrBlue; // Entry Line Color input color stoploss_line_color = clrLime; // Stop-Loss Line Color input color takeprofit_line_color = clrYellow; // Take-Profit Line Color +input color be_line_color = clrNONE; // BE Line Color input ENUM_LINE_STYLE entry_line_style = STYLE_SOLID; // Entry Line Style input ENUM_LINE_STYLE stoploss_line_style = STYLE_SOLID; // Stop-Loss Line Style input ENUM_LINE_STYLE takeprofit_line_style = STYLE_SOLID; // Take-Profit Line Style +input ENUM_LINE_STYLE be_line_style = STYLE_DOT; // BE Line Style input uint entry_line_width = 1; // Entry Line Width input uint stoploss_line_width = 1; // Stop-Loss Line Width input uint takeprofit_line_width = 1; // Take-Profit Line Width +input uint be_line_width = 1; // BE Line Width input group "Defaults" input string ____Defaults = ""; input TRADE_DIRECTION DefaultTradeDirection = Long; // TradeDirection: Default trade direction. @@ -79,7 +87,8 @@ input int DefaultMaxSlippage = 0; // MaxSlippage: Maximum slippage for Trading t input int DefaultMaxSpread = 0; // MaxSpread: Maximum spread for Trading tab. input int DefaultMaxEntrySLDistance = 0; // MaxEntrySLDistance: Maximum entry/SL distance for Trading tab. input int DefaultMinEntrySLDistance = 0; // MinEntrySLDistance: Minimum entry/SL distance for Trading tab. -input double DefaultMaxPositionSize = 0; // MaxPositionSize: Maximum position size for Trading tab. +input double DefaultMaxPositionSizeTotal = 0; // Maximum position size total for Trading tab. +input double DefaultMaxPositionSizePerSymbol = 0; // Maximum position size per symbol for Trading tab. input bool DefaultSubtractOPV = false; // SubtractOPV: Subtract open positions volume (Trading tab). input bool DefaultSubtractPOV = false; // SubtractPOV: Subtract pending orders volume (Trading tab). input bool DefaultDoNotApplyStopLoss = false; // DoNotApplyStopLoss: Don't apply SL for Trading tab. @@ -91,15 +100,18 @@ input ENUM_BASE_CORNER DefaultPanelPositionCorner = CORNER_LEFT_UPPER; // PanelP input bool DefaultTPLockedOnSL = false; // TPLockedOnSL: Lock TP to (multiplied) SL distance. input int DefaultTrailingStop = 0; // TrailingStop: For the Trading tab. input int DefaultBreakEven = 0; // BreakEven: For the Trading tab. -input int DefaultMaxNumberOfTrades = 0; // MaxNumberOfTrades: For the Trading tab. 0 - no limit. -input double DefaultMaxTotalRisk = 0; // MaxTotalRisk: For the Trading tab. 0 - no limit. -input bool DefaultAllSymbols = true; // AllSymbols: For Trading tab, true - count trades in all symbols. +input int DefaultMaxNumberOfTradesTotal = 0; // MaxNumberOfTradesTotal: For the Trading tab. 0 - no limit. +input int DefaultMaxNumberOfTradesPerSymbol = 0; // MaxNumberOfTradesPerSymbol: For the Trading tab. 0 - no limit. +input double DefaultMaxRiskTotal = 0; // MaxRiskTotal: For the Trading tab. 0 - no limit. +input double DefaultMaxRiskPerSymbol = 0; // MaxRiskPerSymbol: For the Trading tab. 0 - no limit. input group "Keyboard shortcuts" input string ____Keyboard_Shortcuts = "Case-insensitive hotkey. Supports Ctrl, Shift."; input string TradeHotKey = "T"; // TradeHotKey: Execute a trade. input string SwitchOrderTypeHotKey = "O"; // SwitchOrderTypeHotKey: Switch order type. input string SwitchEntryDirectionHotKey = "TAB"; // SwitchEntryDirectionHotKey: Switch entry direction. input string SwitchHideShowLinesHotKey = "H"; // SwitchHideShowLinesHotKey: Switch Hide/Show lines. +input string SetStopLossHotKey = "S"; // SetStopLossHotKey: Set SL to where mouse pointer is. +input string SetTakeProfitHotKey = "P"; // SetTakeProfitHotKey: Set TP to where mouse pointer is. input group "Miscellaneous" input string ____Miscellaneous = ""; input double TP_Multiplier = 1; // TP Multiplier for SL value, appears in Take-profit button. @@ -120,6 +132,8 @@ input SYMBOL_CHART_CHANGE_REACTION SymbolChange = SYMBOL_CHART_CHANGE_EACH_OWN; input bool DisableTradingSounds = false; // DisableTradingSounds: If true, sound will be off for trading actions. input bool IgnoreMarketExecutionMode = true; // IgnoreMarketExecutionMode: If true, ignore Market execution. input bool MarketModeApplySLTPAfterAllTradesExecuted = false; // Market Mode - Apply SL/TP After All Trades Executed +input bool DarkMode = false; // DarkMode: Enable dark mode for a less bright panel. +input string SettingsFile = ""; // SettingsFile: Load custom panel settings from \Files\ folder. CPositionSizeCalculator* ExtDialog; @@ -127,18 +141,34 @@ CPositionSizeCalculator* ExtDialog; bool Dont_Move_the_Panel_to_Default_Corner_X_Y; uint LastRecalculationTime = 0; bool StopLossLineIsBeingMoved = false; -bool TakeProfitLineIsBeingMoved = false; -uchar MainKey_TradeHotKey = 0, MainKey_SwitchOrderTypeHotKey = 0, MainKey_SwitchEntryDirectionHotKey = 0, MainKey_SwitchHideShowLinesHotKey = 0; -bool CtrlRequired_TradeHotKey = false, CtrlRequired_SwitchOrderTypeHotKey = false, CtrlRequired_SwitchEntryDirectionHotKey = false, CtrlRequired_SwitchHideShowLinesHotKey = false; -bool ShiftRequired_TradeHotKey = false, ShiftRequired_SwitchOrderTypeHotKey = false, ShiftRequired_SwitchEntryDirectionHotKey = false, ShiftRequired_SwitchHideShowLinesHotKey = false; +bool TakeProfitLineIsBeingMoved[]; // Separate for each TP. +uchar MainKey_TradeHotKey = 0, MainKey_SwitchOrderTypeHotKey = 0, MainKey_SwitchEntryDirectionHotKey = 0, MainKey_SwitchHideShowLinesHotKey = 0, MainKey_SetStopLossHotKey = 0, MainKey_SetTakeProfitHotKey = 0; +bool CtrlRequired_TradeHotKey = false, CtrlRequired_SwitchOrderTypeHotKey = false, CtrlRequired_SwitchEntryDirectionHotKey = false, CtrlRequired_SwitchHideShowLinesHotKey = false, CtrlRequired_SetStopLossHotKey = false, CtrlRequired_SetTakeProfitHotKey = false; +bool ShiftRequired_TradeHotKey = false, ShiftRequired_SwitchOrderTypeHotKey = false, ShiftRequired_SwitchEntryDirectionHotKey = false, ShiftRequired_SwitchHideShowLinesHotKey = false, ShiftRequired_SetStopLossHotKey = false, ShiftRequired_SetTakeProfitHotKey = false; bool NeedToCheckToggleScaleOffOn; int PrevChartWidth = -1; int DeinitializationReason = -1; string OldSymbol = ""; int OldTakeProfitsNumber = -1; +int Mouse_Last_X = 0, Mouse_Last_Y = 0; // For SL/TP hotkeys. int OnInit() { + if (DarkMode) + { + CONTROLS_EDIT_COLOR_ENABLE = DARKMODE_EDIT_BG_COLOR; + CONTROLS_EDIT_COLOR_DISABLE = 0x999999; + CONTROLS_BUTTON_COLOR_ENABLE = DARKMODE_BUTTON_BG_COLOR; + CONTROLS_BUTTON_COLOR_DISABLE = 0x919999; + } + else + { + CONTROLS_EDIT_COLOR_ENABLE = C'255,255,255'; + CONTROLS_EDIT_COLOR_DISABLE = C'221,221,211'; + CONTROLS_BUTTON_COLOR_ENABLE = C'200,200,200'; + CONTROLS_BUTTON_COLOR_DISABLE = C'224,224,224'; + } + TickSize = -1; if (DeinitializationReason != REASON_CHARTCHANGE) ExtDialog = new CPositionSizeCalculator; // Create the panel only if it is not a symbol/timeframe change. @@ -148,6 +178,11 @@ int OnInit() MathSrand(GetTickCount() + 293029); // Used by CreateInstanceId() in Dialog.mqh (standard library). Keep the second number unique across other panel indicators/EAs. + if (SettingsFile != "") // Load a custom settings file if given via input parameters. + { + ExtDialog.SetFileName(SettingsFile); + } + Dont_Move_the_Panel_to_Default_Corner_X_Y = true; PanelCaptionBase = "Position Sizer (ver. " + Version + ")"; @@ -155,7 +190,7 @@ int OnInit() // Symbol changed. if ((DeinitializationReason == REASON_CHARTCHANGE) && (OldSymbol != _Symbol)) { - ObjectsDeleteAll(0, ObjectPrefix); // All lines should be deleted, so that they could be recreated at new sets. values. + ObjectsDeleteAll(0, ObjectPrefix, -1, OBJ_HLINE); // All lines should be deleted, so that they could be recreated at new sets. values. if (SymbolChange == SYMBOL_CHART_CHANGE_EACH_OWN) { ExtDialog.SaveSettingsOnDisk(OldSymbol); // Save old symbol's settings. @@ -168,6 +203,7 @@ int OnInit() OutputSwapsYearlyLongLot = "?"; OutputSwapsYearlyShortLot = "?"; OutputSwapsYearlyLongPS = "?"; OutputSwapsYearlyShortPS = "?"; OutputSwapsCurrencyDailyLot = ""; OutputSwapsCurrencyDailyPS = ""; OutputSwapsCurrencyYearlyLot = ""; OutputSwapsCurrencyYearlyPS = ""; ReferenceSymbol = NULL; SwapConversionSymbol = ""; AdditionalReferenceSymbol = NULL; + WarnedAboutZeroUnitCost = 0; NeedToCheckToggleScaleOffOn = true; @@ -178,7 +214,6 @@ int OnInit() else LinesSelectedStatus = 2; // Flip lines to unselected. } } - // Normal attempt to load settings fails (attempted in not chart change case and in chart case with 'each pair own settings' case if ((((DeinitializationReason != REASON_CHARTCHANGE) || ((DeinitializationReason == REASON_CHARTCHANGE) && (OldSymbol != _Symbol) && (SymbolChange == SYMBOL_CHART_CHANGE_EACH_OWN))) && (!ExtDialog.LoadSettingsFromDisk())) // OR chart change with hard_reset configured and with symbol change. @@ -192,6 +227,7 @@ int OnInit() if (sets.TakeProfitsNumber < 1) sets.TakeProfitsNumber = 1; // At least one TP. ArrayResize(sets.TP, sets.TakeProfitsNumber); ArrayResize(sets.TPShare, sets.TakeProfitsNumber); + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); ArrayInitialize(sets.TP, 0); ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); ArrayResize(sets.WasSelectedAdditionalTakeProfitLine, sets.TakeProfitsNumber - 1); // -1 because the flag for the main TP is saved elsewhere. @@ -239,7 +275,9 @@ int OnInit() sets.MaxSpread = DefaultMaxSpread; sets.MaxEntrySLDistance = DefaultMaxEntrySLDistance; sets.MinEntrySLDistance = DefaultMinEntrySLDistance; - sets.MaxPositionSize = DefaultMaxPositionSize; + sets.MaxPositionSizeTotal = DefaultMaxPositionSizeTotal; + sets.MaxPositionSizePerSymbol = DefaultMaxPositionSizePerSymbol; + if ((sets.MaxPositionSizeTotal < sets.MaxPositionSizePerSymbol) && (sets.MaxPositionSizeTotal != 0)) sets.MaxPositionSizeTotal = sets.MaxPositionSizePerSymbol; sets.StopLoss = 0; sets.TakeProfit = 0; sets.SubtractPendingOrders = DefaultSubtractPOV; @@ -254,14 +292,16 @@ int OnInit() sets.TPLockedOnSL = DefaultTPLockedOnSL; sets.TrailingStopPoints = DefaultTrailingStop; sets.BreakEvenPoints = DefaultBreakEven; - sets.MaxNumberOfTrades = DefaultMaxNumberOfTrades; - sets.MaxTotalRisk = DefaultMaxTotalRisk; - sets.AllSymbols = DefaultAllSymbols; - sets.ShareVolumeMode = Equal; + sets.MaxNumberOfTradesTotal = DefaultMaxNumberOfTradesTotal; + sets.MaxNumberOfTradesPerSymbol = DefaultMaxNumberOfTradesPerSymbol; + if ((sets.MaxNumberOfTradesTotal < sets.MaxNumberOfTradesPerSymbol) && (sets.MaxNumberOfTradesTotal != 0)) sets.MaxNumberOfTradesTotal = sets.MaxNumberOfTradesPerSymbol; + sets.MaxRiskTotal = DefaultMaxRiskTotal; + sets.MaxRiskPerSymbol = DefaultMaxRiskPerSymbol; + if ((sets.MaxRiskTotal < sets.MaxRiskPerSymbol) && (sets.MaxRiskTotal != 0)) sets.MaxRiskTotal = sets.MaxRiskPerSymbol; + sets.ShareVolumeMode = Decreasing; sets.TemplateChanged = false; } if (sets.TakeProfitsNumber < 1) sets.TakeProfitsNumber = 1; // At least one TP. - if (DeinitializationReason != REASON_CHARTCHANGE) { if (!ExtDialog.Create(0, "Position Sizer (ver. " + Version + ")", 0, DefaultPanelPositionX, DefaultPanelPositionY)) return INIT_FAILED; @@ -279,6 +319,8 @@ int OnInit() if (SwitchEntryDirectionHotKey != "") DissectHotKeyCombination(SwitchEntryDirectionHotKey, ShiftRequired_SwitchEntryDirectionHotKey, CtrlRequired_SwitchEntryDirectionHotKey, MainKey_SwitchEntryDirectionHotKey); if (SwitchOrderTypeHotKey != "") DissectHotKeyCombination(SwitchOrderTypeHotKey, ShiftRequired_SwitchOrderTypeHotKey, CtrlRequired_SwitchOrderTypeHotKey, MainKey_SwitchOrderTypeHotKey); if (SwitchHideShowLinesHotKey != "") DissectHotKeyCombination(SwitchHideShowLinesHotKey, ShiftRequired_SwitchHideShowLinesHotKey, CtrlRequired_SwitchHideShowLinesHotKey, MainKey_SwitchHideShowLinesHotKey); + if (SetStopLossHotKey != "") DissectHotKeyCombination(SetStopLossHotKey, ShiftRequired_SetStopLossHotKey, CtrlRequired_SetStopLossHotKey, MainKey_SetStopLossHotKey); + if (SetTakeProfitHotKey != "") DissectHotKeyCombination(SetTakeProfitHotKey, ShiftRequired_SetTakeProfitHotKey, CtrlRequired_SetTakeProfitHotKey, MainKey_SetTakeProfitHotKey); } else if (OldSymbol != _Symbol) { @@ -295,21 +337,16 @@ int OnInit() } Dont_Move_the_Panel_to_Default_Corner_X_Y = false; } - else if (SymbolChange == SYMBOL_CHART_CHANGE_EACH_OWN) // Load the INI file if it was a symbol change and a each symbol has its own settings. - { - ExtDialog.IniFileLoad(); - } - } - + } // Avoid re-initialization on timeframe change and on symbol change with the 'keep panel' setting. if ((DeinitializationReason != REASON_CHARTCHANGE) || ((DeinitializationReason == REASON_CHARTCHANGE) && (OldSymbol != _Symbol) && ((SymbolChange == SYMBOL_CHART_CHANGE_HARD_RESET) || (SymbolChange == SYMBOL_CHART_CHANGE_EACH_OWN)))) { - Initialization(); if (DeinitializationReason == REASON_CHARTCHANGE) // Do not run if it is not the symbol change because 'CPositionSizeCalculator::Create()' takes care of that in other cases. { // Remove extra empty space on the panel when going from a panel with more TPs to a panel with fewer TPs. if (sets.TakeProfitsNumber < OldTakeProfitsNumber) { + Initialization(); int NewTakeProfitsNumber = sets.TakeProfitsNumber; sets.TakeProfitsNumber = OldTakeProfitsNumber; // Used and decremented inside OnClickBtnTakeProfitsNumberRemove(). while (sets.TakeProfitsNumber > NewTakeProfitsNumber) @@ -326,12 +363,15 @@ int OnInit() { ExtDialog.OnClickBtnTakeProfitsNumberAdd(); } + // Theese three should be executed only after all TP arrays are properly resized. + Initialization(); + ExtDialog.IniFileLoad(); // InitObjects(); is skipped because it will be done after adding all the TP chart objects. } } - + else Initialization(); // Brings panel on top of other objects without actual maximization of the panel. ExtDialog.HideShowMaximize(); - } + } if (!Dont_Move_the_Panel_to_Default_Corner_X_Y) { @@ -373,9 +413,57 @@ int OnInit() // Call the chart event processing function. ExtDialog.ChartEvent(CHARTEVENT_CHART_CHANGE, lparam, dparam, sparam); } - + if (!EventSetTimer(1)) Print("Error setting timer: ", GetLastError()); + if (DarkMode) + { + int total = ObjectsTotal(ChartID()); + for (int i = 0; i < total; i++) + { + string obj_name = ObjectName(ChartID(), i); + if (StringSubstr(obj_name, 0, StringLen(ExtDialog.Name())) != ExtDialog.Name()) continue; // Skip non-panel objects. + //if (ObjectType(obj_name) != OBJ_RECTANGLE_LABEL) continue; + if (obj_name == ExtDialog.Name() + "Back") + { + + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BGCOLOR, DARKMODE_BG_DARK_COLOR); + } + if (obj_name == ExtDialog.Name() + "Caption") + { + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BGCOLOR, DARKMODE_BG_DARK_COLOR); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_COLOR, DARKMODE_CONTROL_BRODER_COLOR); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BORDER_COLOR, DARKMODE_BG_DARK_COLOR); + } + else if (obj_name == ExtDialog.Name() + "ClientBack") + { + ObjectSetInteger(ChartID(), obj_name, OBJPROP_COLOR, DARKMODE_MAIN_AREA_BORDER_COLOR); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BGCOLOR, DARKMODE_MAIN_AREA_BG_COLOR); + } + else if (StringSubstr(obj_name, 0, StringLen(ExtDialog.Name() + "m_Edt")) == ExtDialog.Name() + "m_Edt") + { + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BGCOLOR, DARKMODE_EDIT_BG_COLOR); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BORDER_COLOR, DARKMODE_CONTROL_BRODER_COLOR); + } + else if (StringSubstr(obj_name, 0, StringLen(ExtDialog.Name() + "m_Btn")) == ExtDialog.Name() + "m_Btn") + { + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BGCOLOR, DARKMODE_BUTTON_BG_COLOR); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BORDER_COLOR, DARKMODE_CONTROL_BRODER_COLOR); + } + else if (StringSubstr(obj_name, 0, StringLen(ExtDialog.Name() + "m_Chk")) == ExtDialog.Name() + "m_Chk") + { + ObjectSetInteger(ChartID(), obj_name, OBJPROP_COLOR, DARKMODE_TEXT_COLOR); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BGCOLOR, DARKMODE_MAIN_AREA_BG_COLOR); + ObjectSetInteger(ChartID(), obj_name, OBJPROP_BORDER_COLOR, DARKMODE_MAIN_AREA_BG_COLOR); + } + else + { + if (obj_name == ExtDialog.Name() + "m_LblURL") ObjectSetInteger(ChartID(), obj_name, OBJPROP_COLOR, 0x224400); + else ObjectSetInteger(ChartID(), obj_name, OBJPROP_COLOR, DARKMODE_TEXT_COLOR); + } + } + } + return INIT_SUCCEEDED; } @@ -392,7 +480,7 @@ void OnDeinit(const int reason) ObjectsDeleteAll(0, ObjectPrefix); // Delete all lines if platform was closed. if ((reason == REASON_REMOVE) || (reason == REASON_PROGRAM)) { - ExtDialog.DeleteSettingsFile(); + if (SettingsFile == "") ExtDialog.DeleteSettingsFile(); if (!FileDelete(ExtDialog.IniFileName() + ExtDialog.IniFileExt())) Print("Failed to delete the PS panel's .ini file: ", GetLastError()); } } @@ -414,12 +502,15 @@ void OnDeinit(const int reason) else { ObjectDelete(0, ObjectPrefix + "StopLossLabel"); + ObjectDelete(0, ObjectPrefix + "EntryLabel"); ObjectsDeleteAll(0, ObjectPrefix + "TakeProfitLabel", -1, OBJ_LABEL); ObjectsDeleteAll(0, ObjectPrefix + "TPAdditionalLabel", -1, OBJ_LABEL); ObjectDelete(0, ObjectPrefix + "SLAdditionalLabel"); ExtDialog.Destroy(); delete ExtDialog; } + + ObjectsDeleteAll(0, ObjectPrefix + "BE"); // Delete all BE lines and labels. } void OnTick() @@ -427,7 +518,6 @@ void OnTick() ExtDialog.RefreshValues(); if (sets.TrailingStopPoints > 0) DoTrailingStop(); - if (sets.BreakEvenPoints > 0) DoBreakEven(); } void OnChartEvent(const int id, @@ -435,32 +525,42 @@ void OnChartEvent(const int id, const double &dparam, const string &sparam) { - // Mouse move while left mouse button is down. - if ((id == CHARTEVENT_MOUSE_MOVE) && (((uint)sparam & 1) == 1)) + if (id == CHARTEVENT_MOUSE_MOVE) { - if ((SLDistanceInPoints) || ((ShowATROptions) && (sets.ATRMultiplierSL > 0))) + Mouse_Last_X = (int)lparam; + Mouse_Last_Y = (int)dparam; + if (((uint)sparam & 1) == 1) // While left mouse button is down. { - double current_line_price = ObjectGetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, 0); - if (current_line_price != tStopLossLevel) StopLossLineIsBeingMoved = true; - else StopLossLineIsBeingMoved = false; - } - if ((TPDistanceInPoints) || ((ShowATROptions) && (sets.ATRMultiplierTP > 0))) - { - TakeProfitLineIsBeingMoved = false; - double current_line_price = ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, 0); - if (current_line_price != tTakeProfitLevel) TakeProfitLineIsBeingMoved = true; - // Additional take-profits. - else + if ((SLDistanceInPoints) || ((ShowATROptions) && (sets.ATRMultiplierSL > 0))) + { + double current_line_price = NormalizeDouble(ObjectGetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, 0), _Digits); + if (MathAbs(current_line_price - tStopLossLevel) > _Point / 2.0) // != for doubles. + { + StopLossLineIsBeingMoved = true; + } + else StopLossLineIsBeingMoved = false; + } + if ((TPDistanceInPoints) || ((ShowATROptions) && (sets.ATRMultiplierTP > 0))) { - for (int i = 1; i < sets.TakeProfitsNumber; i++) // Will fire only if sets.TakeProfitsNumber > 1. + ArrayInitialize(TakeProfitLineIsBeingMoved, false); + double current_line_price = NormalizeDouble(ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, 0), _Digits); + if (MathAbs(current_line_price - tTakeProfitLevel) > _Point / 2.0) // != for doubles. + { + TakeProfitLineIsBeingMoved[0] = true; + } + // Additional take-profits. + else { - if (sets.TP[i] != 0) // With zero points TP, keep the TP lines at zero level - as with the main TP level. + for (int i = 1; i < sets.TakeProfitsNumber; i++) // Will fire only if sets.TakeProfitsNumber > 1. { - current_line_price = ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, 0); - if (current_line_price != sets.TP[i]) + if (sets.TP[i] != 0) // With zero points TP, keep the TP lines at zero level - as with the main TP level. { - TakeProfitLineIsBeingMoved = true; - break; + current_line_price = NormalizeDouble(ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, 0), _Digits); + if (MathAbs(current_line_price - sets.TP[i]) > _Point / 2.0) // != for doubles. + { + TakeProfitLineIsBeingMoved[i] = true; + break; + } } } } @@ -468,6 +568,12 @@ void OnChartEvent(const int id, } } + if (id == CHARTEVENT_CLICK) // Avoid "sticking" of xxxLineIsBeingMoved variables. + { + StopLossLineIsBeingMoved = false; + ArrayInitialize(TakeProfitLineIsBeingMoved, false); + } + // Remember the panel's location to have the same location for minimized and maximized states. if ((id == CHARTEVENT_CUSTOM + ON_DRAG_END) && (lparam == -1)) { @@ -481,9 +587,9 @@ void OnChartEvent(const int id, if (id == CHARTEVENT_CUSTOM + ON_END_EDIT) { // Additional take-profit field #N on Main tab. - if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "AdditionalTPEdits")) == ExtDialog.Name() + "AdditionalTPEdits") + if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "m_EdtAdditionalTPEdits")) == ExtDialog.Name() + "m_EdtAdditionalTPEdits") { - int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "AdditionalTPEdits"))) - 1; + int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "m_EdtAdditionalTPEdits"))) - 1; ExtDialog.UpdateAdditionalTPEdit(i); } // Take-profit field #N on Trading tab. @@ -502,15 +608,15 @@ void OnChartEvent(const int id, else if (id == CHARTEVENT_CUSTOM + ON_CLICK) { // Additional take-profit increase button #N on Main tab. - if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "AdditionalTPButtonsIncrease")) == ExtDialog.Name() + "AdditionalTPButtonsIncrease") + if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "m_BtnAdditionalTPButtonsIncrease")) == ExtDialog.Name() + "m_BtnAdditionalTPButtonsIncrease") { - int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "AdditionalTPButtonsIncrease"))) - 1; + int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "m_BtnAdditionalTPButtonsIncrease"))) - 1; ExtDialog.ProcessAdditionalTPButtonsIncrease(i); } // Additional take-profit decrease button #N on Main tab. - else if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "AdditionalTPButtonsDecrease")) == ExtDialog.Name() + "AdditionalTPButtonsDecrease") + else if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "m_BtnAdditionalTPButtonsDecrease")) == ExtDialog.Name() + "m_BtnAdditionalTPButtonsDecrease") { - int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "AdditionalTPButtonsDecrease"))) - 1; + int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "m_BtnAdditionalTPButtonsDecrease"))) - 1; ExtDialog.ProcessAdditionalTPButtonsDecrease(i); } // Because there is a bug that keeps a control's Id() = -1 if it is created after the panel is initialized. So, it cannot be processed with the panel's event processor. @@ -571,6 +677,49 @@ void OnChartEvent(const int id, Trade(); } } + // Set stop-loss: + else if ((MainKey_SetStopLossHotKey != 0) && (lparam == MainKey_SetStopLossHotKey)) + { + if (((!ShiftRequired_SetStopLossHotKey) || (TerminalInfoInteger(TERMINAL_KEYSTATE_SHIFT) < 0)) // Shift + && ((!CtrlRequired_SetStopLossHotKey) || (TerminalInfoInteger(TERMINAL_KEYSTATE_CONTROL) < 0))) // Control + { + // Capture point price location. + int subwindow; + double price; + datetime time; // Dummy. + ChartXYToTimePrice(ChartID(), Mouse_Last_X, Mouse_Last_Y, subwindow, time, price); + // If valid, move line SL there. + if ((subwindow == 0) && (price > 0)) + { + ObjectSetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, price); + if ((SLDistanceInPoints) || (ShowATROptions)) ExtDialog.UpdateFixedSL(); + ExtDialog.RefreshValues(); + } + } + } + // Set take-profit: + else if ((MainKey_SetTakeProfitHotKey != 0) && (lparam == MainKey_SetTakeProfitHotKey)) + { + if (((!ShiftRequired_SetTakeProfitHotKey) || (TerminalInfoInteger(TERMINAL_KEYSTATE_SHIFT) < 0)) // Shift + && ((!CtrlRequired_SetTakeProfitHotKey) || (TerminalInfoInteger(TERMINAL_KEYSTATE_CONTROL) < 0))) // Control + { + // Capture point price location. + int subwindow; + double price; + datetime time; // Dummy. + ChartXYToTimePrice(ChartID(), Mouse_Last_X, Mouse_Last_Y, subwindow, time, price); + // If valid, move line SL there. + if ((subwindow == 0) && (price > 0)) + { + ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, price); + if ((TPDistanceInPoints) || (ShowATROptions)) ExtDialog.UpdateFixedTP(); + ExtDialog.ShowTPRelatedEdits(); + ExtDialog.RefreshValues(); + ExtDialog.HideShowMaximize(); + ExtDialog.MoveAndResize(); + } + } + } } // Call Panel's event handler only if it is not a CHARTEVENT_CHART_CHANGE - workaround for minimization bug on chart switch. @@ -594,7 +743,7 @@ void OnChartEvent(const int id, } if (sparam == ObjectPrefix + "StopLossLine") StopLossLineIsBeingMoved = false; // In any case ending moving state for the stop-loss line. - if (StringFind(sparam, ObjectPrefix + "TakeProfitLine") != -1) TakeProfitLineIsBeingMoved = false; // In any case ending moving state for the take-profit line. + if (StringFind(sparam, ObjectPrefix + "TakeProfitLine") != -1) ArrayInitialize(TakeProfitLineIsBeingMoved, false); // In any case ending moving state for the take-profit line. if (id != CHARTEVENT_CHART_CHANGE) ExtDialog.RefreshValues(); diff --git a/MQL4/Experts/Position Sizer/Position Sizer.mqh b/MQL4/Experts/Position Sizer/Position Sizer.mqh index d8ea0f7..ddf1853 100644 --- a/MQL4/Experts/Position Sizer/Position Sizer.mqh +++ b/MQL4/Experts/Position Sizer/Position Sizer.mqh @@ -16,9 +16,9 @@ class CPositionSizeCalculator : public CAppDialog { private: CButton m_BtnTabMain, m_BtnTabRisk, m_BtnTabMargin, m_BtnTabSwaps, m_BtnTabTrading, m_BtnOrderType, m_BtnAccount, m_BtnLines, m_BtnStopLoss, m_BtnTakeProfit, m_BtnEntry, m_BtnATRTimeframe, m_BtnCommissionType, m_BtnMaxPS, m_BtnTrade, m_BtnTPsInward, m_BtnTPsOutward, m_BtnTradingTPShare, m_BtnQuickRisk1, m_BtnQuickRisk2, m_BtnEntryIncrease, m_BtnEntryDecrease, m_BtnStopLossIncrease, m_BtnStopLossDecrease, m_BtnTakeProfitIncrease, m_BtnTakeProfitDecrease, m_BtnTakeProfitsNumberAdd, m_BtnTakeProfitsNumberRemove; - CCheckBox m_ChkSpreadAdjustmentSL, m_ChkSpreadAdjustmentTP, m_ChkCountPendings, m_ChkIgnoreOrdersWithoutSL, m_ChkIgnoreOrdersWithoutTP, m_ChkIgnoreOtherSymbols, m_ChkDisableTradingWhenLinesAreHidden, m_ChkSubtractPositions, m_ChkSubtractPendingOrders, m_ChkDoNotApplyStopLoss, m_ChkDoNotApplyTakeProfit, m_ChkAskForConfirmation, m_ChkCommentAutoSuffix, m_ChkAllSymbols; - CEdit m_EdtEntryLevel, m_EdtSL, m_EdtTP, m_EdtAccount, m_EdtCommissionSize, m_EdtRiskPIn, m_EdtRiskPRes, m_EdtRiskMIn, m_EdtRiskMRes, m_EdtReward1, m_EdtReward2, m_EdtRR1, m_EdtRR2, m_EdtPosSize, m_EdtPointValue, m_EdtATRPeriod, m_EdtATRMultiplierSL, m_EdtATRMultiplierTP, m_EdtCurRiskM, m_EdtCurRiskP, m_EdtPotRiskM, m_EdtPotRiskP, m_EdtCurProfitM, m_EdtCurProfitP, m_EdtPotProfitM, m_EdtPotProfitP, m_EdtCurL, m_EdtPotL, m_EdtPosMargin, m_EdtUsedMargin, m_EdtFreeMargin, m_EdtCustomLeverage, m_EdtMaxPositionSizeByMargin, m_EdtSwapsType, m_EdtSwapsTripleDay, m_EdtSwapsNominalLong, m_EdtSwapsNominalShort, m_EdtSwapsDailyLongLot, m_EdtSwapsDailyShortLot, m_EdtSwapsDailyLongPS, m_EdtSwapsDailyShortPS, m_EdtSwapsYearlyLongLot, m_EdtSwapsYearlyShortLot, m_EdtSwapsYearlyLongPS, m_EdtSwapsYearlyShortPS, m_EdtMagicNumber, m_EdtCommentary, m_EdtMaxSlippage, m_EdtMaxSpread, m_EdtMaxEntrySLDistance, m_EdtMinEntrySLDistance, m_EdtMaxPositionSize, m_EdtTrailingStopPoints, m_EdtBreakEvenPoints, m_EdtMaxNumberOfTrades, m_EdtMaxTotalRisk; - CLabel m_LblEntryLevel, m_LblEntryWarning, m_LblSL, m_LblSLWarning, m_LblTPWarning, m_LblOrderType, m_LblCommissionSize, m_LblAdditionalFundsAsterisk, m_LblInput, m_LblResult, m_LblRisk, m_LblRiskM, m_LblReward, m_LblRR, m_LblPosSize, m_LblPointValue, m_LblATRPeriod, m_LblATRMultiplierSL, m_LblATRMultiplierTP, m_LblATRValue, m_LblATRTimeframe, m_LblCurrentRiskMoney, m_LblCurrentRiskPerc, m_LblCurrentProfitMoney, m_LblCurrentProfitPerc, m_LblPotentialRiskMoney, m_LblPotentialRiskPerc, m_LblPotentialProfitMoney, m_LblPotentialProfitPerc, m_LblCurrentLots, m_LblPotentialLots, m_LblCurrentPortfolio, m_LblPotentialPortfolio, m_LblPosMargin, m_LblUsedMargin, m_LblFreeMargin, m_LblCustomLeverage, m_LblAccLeverage, m_LblSymbolLeverage, m_LblMaxPositionSizeByMargin, m_LblSwapsType, m_LblSwapsTripleDay, m_LblSwapsLong, m_LblSwapsShort, m_LblSwapsNominal, m_LblSwapsDaily, m_LblSwapsYearly, m_LblSwapsPerLotDaily, m_LblSwapsPerPSDaily, m_LblSwapsPerLotYearly, m_LblSwapsPerPSYearly, m_LblMagicNumber, m_LblCommentary, m_LblTradingPoints, m_LblMaxSlippage, m_LblMaxSpread, m_LblMaxEntrySLDistance, m_LblMinEntrySLDistance, m_LblTradingLots, m_LblMaxPositionSize, m_LblURL, m_LblTradingTP, m_LblTrailingStop, m_LblBreakEven, m_LblMaxNumberOfTrades, m_LblMaxTotalRisk; + CCheckBox m_ChkSpreadAdjustmentSL, m_ChkSpreadAdjustmentTP, m_ChkCountPendings, m_ChkIgnoreOrdersWithoutSL, m_ChkIgnoreOrdersWithoutTP, m_ChkIgnoreOtherSymbols, m_ChkDisableTradingWhenLinesAreHidden, m_ChkSubtractPositions, m_ChkSubtractPendingOrders, m_ChkDoNotApplyStopLoss, m_ChkDoNotApplyTakeProfit, m_ChkAskForConfirmation, m_ChkCommentAutoSuffix; + CEdit m_EdtEntryLevel, m_EdtSL, m_EdtTP, m_EdtAccount, m_EdtCommissionSize, m_EdtRiskPIn, m_EdtRiskPRes, m_EdtRiskMIn, m_EdtRiskMRes, m_EdtReward1, m_EdtReward2, m_EdtRR1, m_EdtRR2, m_EdtPosSize, m_EdtPointValue, m_EdtATRPeriod, m_EdtATRMultiplierSL, m_EdtATRMultiplierTP, m_EdtCurRiskM, m_EdtCurRiskP, m_EdtPotRiskM, m_EdtPotRiskP, m_EdtCurProfitM, m_EdtCurProfitP, m_EdtPotProfitM, m_EdtPotProfitP, m_EdtCurL, m_EdtPotL, m_EdtPosMargin, m_EdtUsedMargin, m_EdtFreeMargin, m_EdtCustomLeverage, m_EdtMaxPositionSizeByMargin, m_EdtSwapsType, m_EdtSwapsTripleDay, m_EdtSwapsNominalLong, m_EdtSwapsNominalShort, m_EdtSwapsDailyLongLot, m_EdtSwapsDailyShortLot, m_EdtSwapsDailyLongPS, m_EdtSwapsDailyShortPS, m_EdtSwapsYearlyLongLot, m_EdtSwapsYearlyShortLot, m_EdtSwapsYearlyLongPS, m_EdtSwapsYearlyShortPS, m_EdtMagicNumber, m_EdtCommentary, m_EdtMaxSlippage, m_EdtMaxSpread, m_EdtMaxEntrySLDistance, m_EdtMinEntrySLDistance, m_EdtMaxPositionSize, m_EdtTrailingStopPoints, m_EdtBreakEvenPoints, m_EdtMaxNumberOfTradesTotal, m_EdtMaxNumberOfTradesPerSymbol, m_EdtMaxPositionSizeTotal, m_EdtMaxPositionSizePerSymbol, m_EdtMaxRiskTotal, m_EdtMaxRiskPerSymbol; + CLabel m_LblEntryLevel, m_LblEntryWarning, m_LblSL, m_LblSLWarning, m_LblTPWarning, m_LblOrderType, m_LblCommissionSize, m_LblAdditionalFundsAsterisk, m_LblInput, m_LblResult, m_LblRisk, m_LblRiskM, m_LblReward, m_LblRR, m_LblPosSize, m_LblPointValue, m_LblATRPeriod, m_LblATRMultiplierSL, m_LblATRMultiplierTP, m_LblATRValue, m_LblATRTimeframe, m_LblCurrentRiskMoney, m_LblCurrentRiskPerc, m_LblCurrentProfitMoney, m_LblCurrentProfitPerc, m_LblPotentialRiskMoney, m_LblPotentialRiskPerc, m_LblPotentialProfitMoney, m_LblPotentialProfitPerc, m_LblCurrentLots, m_LblPotentialLots, m_LblCurrentPortfolio, m_LblPotentialPortfolio, m_LblPosMargin, m_LblUsedMargin, m_LblFreeMargin, m_LblCustomLeverage, m_LblAccLeverage, m_LblSymbolLeverage, m_LblMaxPositionSizeByMargin, m_LblSwapsType, m_LblSwapsTripleDay, m_LblSwapsLong, m_LblSwapsShort, m_LblSwapsNominal, m_LblSwapsDaily, m_LblSwapsYearly, m_LblSwapsPerLotDaily, m_LblSwapsPerPSDaily, m_LblSwapsPerLotYearly, m_LblSwapsPerPSYearly, m_LblMagicNumber, m_LblCommentary, m_LblTradingPoints, m_LblMaxSlippage, m_LblMaxSpread, m_LblMaxEntrySLDistance, m_LblMinEntrySLDistance, m_LblTradingLots, m_LblURL, m_LblTradingTP, m_LblTrailingStop, m_LblBreakEven, m_LblMaxNumberOfTrades, m_LblMaxNumberOfTradesTotal, m_LblMaxNumberOfTradesPerSymbol, m_LblMaxPositionSize, m_LblMaxPositionSizeTotal, m_LblMaxPositionSizePerSymbol, m_LblMaxRisk, m_LblMaxRiskTotal, m_LblMaxRiskPerSymbol; string m_FileName; double m_DPIScale; bool NoPanelMaximization; // A crutch variable to prevent panel maximization when Maximize() is called at the indicator's initialization. @@ -52,6 +52,7 @@ public: virtual bool LoadSettingsFromDisk(); virtual bool DeleteSettingsFile(); virtual void HideShowMaximize(); + virtual void MoveAndResize(); virtual void UpdateFixedSL(); virtual void UpdateFixedTP(); virtual void UpdateAdditionalFixedTP(int i); @@ -69,7 +70,7 @@ public: virtual void CheckAndRestoreLines(); virtual void Minimize(); virtual bool IsMinimized() {return m_minimized;} - virtual void IniFileLoad() {CAppDialog::IniFileLoad(); InitObjects();} // Need to init objects after ini file load. + virtual void IniFileLoad() {CAppDialog::IniFileLoad();ExtDialog.InitObjects();} // Need to init objects after ini file load. void OnClickBtnTakeProfitsNumberRemove(); void OnClickBtnTPsInward(); void OnClickBtnTPsOutward(); @@ -79,6 +80,9 @@ public: int MaxTakeProfitsNumber; void OnClickBtnTakeProfitsNumberAdd(); + virtual bool InitObjects(); + void ShowTPRelatedEdits(); + void SetFileName(string file_name) {m_FileName = file_name;} // Remember the panel's location to have the same location for minimized and maximized states. int remember_top, remember_left; @@ -96,9 +100,7 @@ private: virtual void HideTrading(); virtual bool CreateObjects(); - virtual bool InitObjects(); // Arranges panel objects on the panel. - virtual void MoveAndResize(); virtual bool DisplayValues(); virtual void ProcessTPChange(const bool tp_button_click); @@ -144,12 +146,14 @@ private: void OnEndEditEdtMaxSpread(); void OnEndEditEdtMaxEntrySLDistance(); void OnEndEditEdtMinEntrySLDistance(); - void OnEndEditEdtMaxPositionSize(); + void OnEndEditEdtMaxPositionSizeTotal(); + void OnEndEditEdtMaxPositionSizePerSymbol(); void OnEndEditEdtTrailingStopPoints(); void OnEndEditEdtBreakEvenPoints(); - void OnEndEditEdtMaxNumberOfTrades(); - void OnEndEditEdtMaxTotalRisk(); - void OnChangeChkAllSymbols(); + void OnEndEditEdtMaxNumberOfTradesTotal(); + void OnEndEditEdtMaxNumberOfTradesPerSymbol(); + void OnEndEditEdtMaxRiskTotal(); + void OnEndEditEdtMaxRiskPerSymbol(); void OnChangeChkSubtractPositions(); void OnChangeChkSubtractPendingOrders(); void OnChangeChkDoNotApplyStopLoss(); @@ -209,12 +213,14 @@ ON_EVENT(ON_END_EDIT, m_EdtMaxSlippage, OnEndEditEdtMaxSlippage) ON_EVENT(ON_END_EDIT, m_EdtMaxSpread, OnEndEditEdtMaxSpread) ON_EVENT(ON_END_EDIT, m_EdtMaxEntrySLDistance, OnEndEditEdtMaxEntrySLDistance) ON_EVENT(ON_END_EDIT, m_EdtMinEntrySLDistance, OnEndEditEdtMinEntrySLDistance) -ON_EVENT(ON_END_EDIT, m_EdtMaxPositionSize, OnEndEditEdtMaxPositionSize) +ON_EVENT(ON_END_EDIT, m_EdtMaxPositionSizeTotal, OnEndEditEdtMaxPositionSizeTotal) +ON_EVENT(ON_END_EDIT, m_EdtMaxPositionSizePerSymbol, OnEndEditEdtMaxPositionSizePerSymbol) ON_EVENT(ON_END_EDIT, m_EdtTrailingStopPoints, OnEndEditEdtTrailingStopPoints) ON_EVENT(ON_END_EDIT, m_EdtBreakEvenPoints, OnEndEditEdtBreakEvenPoints) -ON_EVENT(ON_END_EDIT, m_EdtMaxNumberOfTrades, OnEndEditEdtMaxNumberOfTrades) -ON_EVENT(ON_END_EDIT, m_EdtMaxTotalRisk, OnEndEditEdtMaxTotalRisk) -ON_EVENT(ON_CHANGE, m_ChkAllSymbols, OnChangeChkAllSymbols) +ON_EVENT(ON_END_EDIT, m_EdtMaxNumberOfTradesTotal, OnEndEditEdtMaxNumberOfTradesTotal) +ON_EVENT(ON_END_EDIT, m_EdtMaxNumberOfTradesPerSymbol, OnEndEditEdtMaxNumberOfTradesPerSymbol) +ON_EVENT(ON_END_EDIT, m_EdtMaxRiskTotal, OnEndEditEdtMaxRiskTotal) +ON_EVENT(ON_END_EDIT, m_EdtMaxRiskPerSymbol, OnEndEditEdtMaxRiskPerSymbol) ON_EVENT(ON_CHANGE, m_ChkSubtractPositions, OnChangeChkSubtractPositions) ON_EVENT(ON_CHANGE, m_ChkSubtractPendingOrders, OnChangeChkSubtractPendingOrders) ON_EVENT(ON_CHANGE, m_ChkDoNotApplyStopLoss, OnChangeChkDoNotApplyStopLoss) @@ -229,7 +235,7 @@ ON_EVENT(ON_CLICK, m_BtnTabTrading, OnClickBtnTabTrading) ON_EVENT(ON_CLICK, m_BtnTakeProfit, OnClickBtnTakeProfit) if (DefaultSL > 0) ON_EVENT(ON_CLICK, m_BtnStopLoss, OnClickBtnStopLoss) ON_EVENT(ON_CLICK, m_BtnEntry, OnClickBtnEntry) -if (!ShowATROptions) ON_EVENT(ON_CLICK, m_BtnATRTimeframe, OnClickBtnATRTimeframe) +if (ShowATROptions) ON_EVENT(ON_CLICK, m_BtnATRTimeframe, OnClickBtnATRTimeframe) ON_EVENT(ON_CLICK, m_BtnTrade, OnClickBtnTrade) if (QuickRisk1 > 0) ON_EVENT(ON_CLICK, m_BtnQuickRisk1, OnClickBtnQuickRisk1) if (QuickRisk2 > 0) ON_EVENT(ON_CLICK, m_BtnQuickRisk2, OnClickBtnQuickRisk2) @@ -499,11 +505,11 @@ bool CPositionSizeCalculator::CreateObjects() // Because only one Remove button is needed. if (!ButtonCreate(MainTabList, m_BtnTakeProfitsNumberRemove, first_column_start, y, first_column_start + v_spacing * 4 - 1, y + element_height, "m_BtnTakeProfitsNumberRemove", "x", "Remove Take-profit")) return false; } - if (!LabelCreate(MainTabList, AdditionalTPLabels[i], first_column_start + v_spacing * 4, y, first_column_start + normal_label_width, y + element_height, "AdditionalTPLabels" + IntegerToString(i + 2), additional_tp_label_beginning + IntegerToString(i + 2) + additional_tp_label_end)) return false; - if (!EditCreate(MainTabList, AdditionalTPEdits[i], second_column_start, y, second_column_start + normal_edit_width, y + element_height, "AdditionalTPEdits" + IntegerToString(i + 2), "")) return false; - if (!ButtonCreate(MainTabList, AdditionalTPButtonsIncrease[i], second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "AdditionalTPButtonsIncrease" + IntegerToString(i + 2), "+", "Increase Take-profit #" + IntegerToString(i + 2) + " by 1 point")) return false; - if (!ButtonCreate(MainTabList, AdditionalTPButtonsDecrease[i], second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "AdditionalTPButtonsDecrease" + IntegerToString(i + 2), "-", "Decrease Take-profit #" + IntegerToString(i + 2) + " by 1 point")) return false; - if (!LabelCreate(MainTabList, AdditionalTPWarnings[i], third_column_start, y, third_column_start + narrow_label_width, y + element_height, "AdditionalTPWarnings" + IntegerToString(i + 2), " ")) return false; + if (!LabelCreate(MainTabList, AdditionalTPLabels[i], first_column_start + v_spacing * 4, y, first_column_start + normal_label_width, y + element_height, "m_LblAdditionalTPLabels" + IntegerToString(i + 2), additional_tp_label_beginning + IntegerToString(i + 2) + additional_tp_label_end)) return false; + if (!EditCreate(MainTabList, AdditionalTPEdits[i], second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtAdditionalTPEdits" + IntegerToString(i + 2), "")) return false; + if (!ButtonCreate(MainTabList, AdditionalTPButtonsIncrease[i], second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnAdditionalTPButtonsIncrease" + IntegerToString(i + 2), "+", "Increase Take-profit #" + IntegerToString(i + 2) + " by 1 point")) return false; + if (!ButtonCreate(MainTabList, AdditionalTPButtonsDecrease[i], second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnAdditionalTPButtonsDecrease" + IntegerToString(i + 2), "-", "Decrease Take-profit #" + IntegerToString(i + 2) + " by 1 point")) return false; + if (!LabelCreate(MainTabList, AdditionalTPWarnings[i], third_column_start, y, third_column_start + narrow_label_width, y + element_height, "m_LblAdditionalTPWarnings" + IntegerToString(i + 2), " ")) return false; } } @@ -745,7 +751,7 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; if (!LabelCreate(MarginTabList, m_LblCustomLeverage, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblCustomLeverage", "Custom leverage = 1:")) return false; - if (!EditCreate(MarginTabList, m_EdtCustomLeverage, second_margin_column_start - (int)MathRound(10 * m_DPIScale), y, second_margin_column_start + leverage_edit_width, y + element_height, "m_CustomLeverage", "")) return false; + if (!EditCreate(MarginTabList, m_EdtCustomLeverage, second_margin_column_start - (int)MathRound(10 * m_DPIScale), y, second_margin_column_start + leverage_edit_width, y + element_height, "m_EdtCustomLeverage", "")) return false; if (!LabelCreate(MarginTabList, m_LblAccLeverage, second_margin_column_start + leverage_edit_width + (int)MathRound(5 * m_DPIScale), y, second_margin_column_start + leverage_edit_width + (int)MathRound(5 * m_DPIScale) + wide_edit_width, y + element_height, "m_LblAccLeverage", "")) return false; y += element_height + v_spacing; @@ -857,22 +863,32 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(TradingTabList, m_LblMaxNumberOfTrades, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxNumberOfTrades", "Max # of trades:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxNumberOfTrades, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxNumberOfTrades", "", "With a given Magic number")) return false; - if (!CheckBoxCreate(TradingTabList, m_ChkAllSymbols, third_trading_column_start, y, third_trading_column_start + max_psc_edit_width, y + element_height, "m_ChkAllSymbols", "All symbols", "Count trades on all symbols?")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxPositionSize, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxPositionSize", "Max total volume:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxPositionSize, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxPositionSize", "")) return false; - if (!LabelCreate(TradingTabList, m_LblTradingLots, third_trading_column_start, y, third_trading_column_start + max_psc_edit_width, y + element_height, "m_LblTradingLots", " lots")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxTotalRisk, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxTotalRisk", "Max total risk, %:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxTotalRisk, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxTotalRisk", "")) return false; - - y += element_height + v_spacing; + if (ShowMaxParametersOnTrading) + { + if (!LabelCreate(TradingTabList, m_LblMaxNumberOfTrades, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxNumberOfTrades", "Max # of trades")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxNumberOfTradesTotal, first_column_start + narrow_label_width + element_height, y, multi_tp_column_start + tab_button_width, y + element_height, "m_LblMaxNumberOfTradesTotal", "Total:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxNumberOfTradesTotal, first_column_start + v_spacing * 2 + tab_button_width + normal_edit_width, y, first_column_start + v_spacing * 2 + tab_button_width * 2 + normal_edit_width, y + element_height, "m_EdtMaxNumberOfTradesTotal", "")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxNumberOfTradesPerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 2, y, multi_tp_button_start + leverage_edit_width + v_spacing * 6 + tab_button_width, y + element_height, "m_LblMaxNumberOfTradesPerSymbol", "Per symbol:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxNumberOfTradesPerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width, y, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width * 2, y + element_height, "m_EdtMaxNumberOfTradesPerSymbol", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMaxPositionSize, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxPositionSize", "Max volume")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxPositionSizeTotal, first_column_start + narrow_label_width + element_height, y, multi_tp_column_start + tab_button_width, y + element_height, "m_LblMaxPositionSizeTotal", "Total:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxPositionSizeTotal, first_column_start + v_spacing * 2 + tab_button_width + normal_edit_width, y, first_column_start + v_spacing * 2 + tab_button_width * 2 + normal_edit_width, y + element_height, "m_EdtMaxPositionSizeTotal", "")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxPositionSizePerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 2, y, multi_tp_button_start + leverage_edit_width + v_spacing * 6 + tab_button_width, y + element_height, "m_LblMaxPositionSizePerSymbol", "Per symbol:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxPositionSizePerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width, y, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width * 2, y + element_height, "m_EdtMaxPositionSizePerSymbol", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMaxRisk, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxRisk", "Max risk, %")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxRiskTotal, first_column_start + narrow_label_width + element_height, y, multi_tp_column_start + tab_button_width, y + element_height, "m_LblMaxRiskTotal", "Total:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxRiskTotal, first_column_start + v_spacing * 2 + tab_button_width + normal_edit_width, y, first_column_start + v_spacing * 2 + tab_button_width * 2 + normal_edit_width, y + element_height, "m_EdtMaxRiskTotal", "")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxRiskPerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 2, y, multi_tp_button_start + leverage_edit_width + v_spacing * 6 + tab_button_width, y + element_height, "m_LblMaxRiskPerSymbol", "Per symbol:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxRiskPerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width, y, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width * 2, y + element_height, "m_EdtMaxRiskPerSymbol", "")) return false; + + y += element_height + v_spacing; + } if (!CheckBoxCreate(TradingTabList, m_ChkDisableTradingWhenLinesAreHidden, first_column_start, y, panel_end, y + element_height, "m_ChkDisableTradingWhenLinesAreHidden", "Disable trading when lines are hidden")) return false; @@ -900,45 +916,51 @@ bool CPositionSizeCalculator::CreateObjects() } } - if (!LabelCreate(TradingTabList, m_LblTradingPoints, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_LblTradingPoints", "Points", "")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxSlippage, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxSlippage", "Max slippage:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxSlippage, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxSlippage", "")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxSpread, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxSpread", "Max spread:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxSpread, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxSpread", "")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxEntrySLDistance, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxEntrySLDistance", "Max Entry/SL distance:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxEntrySLDistance, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxEntrySLDistance", "")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMinEntrySLDistance, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMinEntrySLDistance", "Min Entry/SL distance:")) return false; - if (!EditCreate(TradingTabList, m_EdtMinEntrySLDistance, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMinEntrySLDistance", "")) return false; - - y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPositions, first_column_start, y, panel_end, y + element_height, "m_ChkSubtractPositions", "Subtract open positions volume", "The EA will subtract currently open trades' volume from the calculated position size before opening a trade.")) return false; - - y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPendingOrders, first_column_start, y, panel_end, y + element_height, "m_ChkSubtractPendingOrders", "Subtract pending orders volume", "The EA will subtract pending orders' volume from the calculated position size before opening a trade.")) return false; - - y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyStopLoss, first_column_start, y, panel_end, y + element_height, "m_ChkDoNotApplyStopLoss", "Do not apply stop-loss", "The EA won't apply stop-loss to the trade it opens.")) return false; - - y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyTakeProfit, first_column_start, y, panel_end, y + element_height, "m_ChkDoNotApplyTakeProfit", "Do not apply take-profit", "The EA won't apply take-prfoit to the trade it opens.")) return false; + if (ShowFusesOnTrading) + { + if (!LabelCreate(TradingTabList, m_LblTradingPoints, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_LblTradingPoints", "Points", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMaxSlippage, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxSlippage", "Max slippage:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxSlippage, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxSlippage", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMaxSpread, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxSpread", "Max spread:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxSpread, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxSpread", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMaxEntrySLDistance, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxEntrySLDistance", "Max Entry/SL distance:")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxEntrySLDistance, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxEntrySLDistance", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMinEntrySLDistance, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMinEntrySLDistance", "Min Entry/SL distance:")) return false; + if (!EditCreate(TradingTabList, m_EdtMinEntrySLDistance, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMinEntrySLDistance", "")) return false; + + y += element_height + v_spacing; + } - y += element_height + v_spacing; + if (ShowCheckboxesOnTrading) + { + if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPositions, first_column_start, y, panel_end, y + element_height, "m_ChkSubtractPositions", "Subtract open positions volume", "The EA will subtract currently open trades' volume from the calculated position size before opening a trade.")) return false; + + y += element_height + v_spacing; + + if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPendingOrders, first_column_start, y, panel_end, y + element_height, "m_ChkSubtractPendingOrders", "Subtract pending orders volume", "The EA will subtract pending orders' volume from the calculated position size before opening a trade.")) return false; + + y += element_height + v_spacing; + + if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyStopLoss, first_column_start, y, panel_end, y + element_height, "m_ChkDoNotApplyStopLoss", "Do not apply stop-loss", "The EA won't apply stop-loss to the trade it opens.")) return false; + + y += element_height + v_spacing; + + if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyTakeProfit, first_column_start, y, panel_end, y + element_height, "m_ChkDoNotApplyTakeProfit", "Do not apply take-profit", "The EA won't apply take-profit to the trade it opens.")) return false; + + y += element_height + v_spacing; + } if (!CheckBoxCreate(TradingTabList, m_ChkAskForConfirmation, first_column_start, y, panel_end, y + element_height, "m_ChkAskForConfirmation", "Ask for confirmation", "The EA will ask for confirmation before opening a trade.")) return false; @@ -1011,16 +1033,24 @@ bool CPositionSizeCalculator::InitObjects() if (!TradingTPShareEdits[i].TextAlign(align)) return false; } } - if (!m_EdtMaxSlippage.TextAlign(align)) return false; - if (!m_EdtMaxSpread.TextAlign(align)) return false; - if (!m_EdtMaxEntrySLDistance.TextAlign(align)) return false; - if (!m_EdtMinEntrySLDistance.TextAlign(align)) return false; - if (!m_EdtMaxPositionSize.TextAlign(align)) return false; + if (ShowFusesOnTrading) + { + if (!m_EdtMaxSlippage.TextAlign(align)) return false; + if (!m_EdtMaxSpread.TextAlign(align)) return false; + if (!m_EdtMaxEntrySLDistance.TextAlign(align)) return false; + if (!m_EdtMinEntrySLDistance.TextAlign(align)) return false; + } if (!m_EdtTrailingStopPoints.TextAlign(align)) return false; if (!m_EdtBreakEvenPoints.TextAlign(align)) return false; - if (!m_EdtMaxNumberOfTrades.TextAlign(align)) return false; - if (!m_EdtMaxTotalRisk.TextAlign(align)) return false; - + if (ShowMaxParametersOnTrading) + { + if (!m_EdtMaxNumberOfTradesTotal.TextAlign(align)) return false; + if (!m_EdtMaxNumberOfTradesPerSymbol.TextAlign(align)) return false; + if (!m_EdtMaxPositionSizeTotal.TextAlign(align)) return false; + if (!m_EdtMaxPositionSizePerSymbol.TextAlign(align)) return false; + if (!m_EdtMaxRiskTotal.TextAlign(align)) return false; + if (!m_EdtMaxRiskPerSymbol.TextAlign(align)) return false; + } if (sets.TPLockedOnSL) m_BtnTakeProfit.ColorBackground(CONTROLS_BUTTON_COLOR_ENABLE); else m_BtnTakeProfit.ColorBackground(CONTROLS_BUTTON_COLOR_BG); @@ -1165,18 +1195,30 @@ bool CPositionSizeCalculator::InitObjects() if (!m_EdtMagicNumber.Text(IntegerToString(sets.MagicNumber))) return false; if (!m_EdtCommentary.Text(sets.Commentary)) return false; if (!m_ChkCommentAutoSuffix.Checked(sets.CommentAutoSuffix)) return false; - if (!m_EdtMaxNumberOfTrades.Text(IntegerToString(sets.MaxNumberOfTrades))) return false; - if (!m_EdtMaxTotalRisk.Text(DoubleToString(sets.MaxTotalRisk, 2))) return false; - if (!m_ChkAllSymbols.Checked(sets.AllSymbols)) return false; + if (ShowMaxParametersOnTrading) + { + if (!m_EdtMaxNumberOfTradesTotal.Text(IntegerToString(sets.MaxNumberOfTradesTotal))) return false; + if (!m_EdtMaxNumberOfTradesPerSymbol.Text(IntegerToString(sets.MaxNumberOfTradesPerSymbol))) return false; + if (!m_EdtMaxPositionSizeTotal.Text(DoubleToString(sets.MaxPositionSizeTotal, 2))) return false; + if (!m_EdtMaxPositionSizePerSymbol.Text(DoubleToString(sets.MaxPositionSizeTotal, 2))) return false; + if (!m_EdtMaxRiskTotal.Text(DoubleToString(sets.MaxRiskTotal, 2))) return false; + if (!m_EdtMaxRiskPerSymbol.Text(DoubleToString(sets.MaxRiskPerSymbol, 2))) return false; + } if (!m_ChkDisableTradingWhenLinesAreHidden.Checked(sets.DisableTradingWhenLinesAreHidden)) return false; - if (!m_EdtMaxSlippage.Text(IntegerToString(sets.MaxSlippage))) return false; - if (!m_EdtMaxSpread.Text(IntegerToString(sets.MaxSpread))) return false; - if (!m_EdtMaxEntrySLDistance.Text(IntegerToString(sets.MaxEntrySLDistance))) return false; - if (!m_EdtMinEntrySLDistance.Text(IntegerToString(sets.MinEntrySLDistance))) return false; - if (!m_ChkSubtractPositions.Checked(sets.SubtractPositions)) return false; - if (!m_ChkSubtractPendingOrders.Checked(sets.SubtractPendingOrders)) return false; - if (!m_ChkDoNotApplyStopLoss.Checked(sets.DoNotApplyStopLoss)) return false; - if (!m_ChkDoNotApplyTakeProfit.Checked(sets.DoNotApplyTakeProfit)) return false; + if (ShowFusesOnTrading) + { + if (!m_EdtMaxSlippage.Text(IntegerToString(sets.MaxSlippage))) return false; + if (!m_EdtMaxSpread.Text(IntegerToString(sets.MaxSpread))) return false; + if (!m_EdtMaxEntrySLDistance.Text(IntegerToString(sets.MaxEntrySLDistance))) return false; + if (!m_EdtMinEntrySLDistance.Text(IntegerToString(sets.MinEntrySLDistance))) return false; + } + if (ShowCheckboxesOnTrading) + { + if (!m_ChkSubtractPositions.Checked(sets.SubtractPositions)) return false; + if (!m_ChkSubtractPendingOrders.Checked(sets.SubtractPendingOrders)) return false; + if (!m_ChkDoNotApplyStopLoss.Checked(sets.DoNotApplyStopLoss)) return false; + if (!m_ChkDoNotApplyTakeProfit.Checked(sets.DoNotApplyTakeProfit)) return false; + } if (!m_ChkAskForConfirmation.Checked(sets.AskForConfirmation)) return false; MoveAndResize(); @@ -1301,6 +1343,19 @@ bool CPositionSizeCalculator::DisplayValues() AdditionalTPWarnings[i - 1].Text(AdditionalWarningTP[i - 1]); } + /* Order type */ if (sets.EntryType == Instant) + { + m_BtnOrderType.Text("Instant"); + m_EdtEntryLevel.ReadOnly(true); + m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); + } + else if (sets.EntryType == Pending) + { + m_BtnOrderType.Text("Pending"); + m_EdtEntryLevel.ReadOnly(false); + m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_ENABLE); + } + /* Account Value */ if (!HideAccSize) if (!m_EdtAccount.Text(FormatDouble(DoubleToString(AccSize, 2)))) return false; /* Account Asterisk */ @@ -1313,7 +1368,7 @@ bool CPositionSizeCalculator::DisplayValues() case Balance_minus_Risk: if (sets.CustomBalance > 0) { - m_LblAdditionalFundsAsterisk.Show(); + if (!m_minimized) m_LblAdditionalFundsAsterisk.Show(); ObjectSetString(ChartID(), m_name + "m_LblAdditionalFundsAsterisk", OBJPROP_TOOLTIP, "Custom balance set"); } else @@ -1329,7 +1384,7 @@ bool CPositionSizeCalculator::DisplayValues() { if (AdditionalFunds != 0) { - m_LblAdditionalFundsAsterisk.Show(); + if (!m_minimized) m_LblAdditionalFundsAsterisk.Show(); string tooltip = ""; if (AdditionalFunds > 0) tooltip = "+" + DoubleToString(AdditionalFunds, 2) + " additional funds"; else if (AdditionalFunds < 0) tooltip = DoubleToString(-AdditionalFunds, 2) + " funds subtracted"; @@ -1473,8 +1528,12 @@ bool CPositionSizeCalculator::DisplayValues() if (!TradingTPShareEdits[i].Text(IntegerToString(sets.TPShare[i]))) return false; } } - /* Maximum Position Size */ if (!m_EdtMaxPositionSize.Text(DoubleToString(sets.MaxPositionSize, LotStep_digits))) return false; - + if (ShowMaxParametersOnTrading) + { + /* Maximum Position Size */ if (!m_EdtMaxPositionSizeTotal.Text(DoubleToString(sets.MaxPositionSizeTotal, LotStep_digits))) return false; + if (!m_EdtMaxPositionSizePerSymbol.Text(DoubleToString(sets.MaxPositionSizePerSymbol, LotStep_digits))) return false; + } + return true; } @@ -1589,7 +1648,7 @@ void CPositionSizeCalculator::RefreshValues() sets.StopLossLevel = NormalizeDouble(MathRound(sets.StopLossLevel / TickSize) * TickSize, _Digits); if ((!StopLossLineIsBeingMoved) || (sets.ATRMultiplierSL == 0) || (!ShowATROptions)) ObjectSetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, sets.StopLossLevel); sets.TakeProfitLevel = NormalizeDouble(MathRound(sets.TakeProfitLevel / TickSize) * TickSize, _Digits); - if ((!TakeProfitLineIsBeingMoved) || (sets.ATRMultiplierTP == 0) || (!ShowATROptions)) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, sets.TakeProfitLevel); + if ((!TakeProfitLineIsBeingMoved[0]) || (sets.ATRMultiplierTP == 0) || (!ShowATROptions)) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, sets.TakeProfitLevel); if (sets.TakeProfitsNumber > 1) { for (int i = 0; i < sets.TakeProfitsNumber; i++) @@ -1638,7 +1697,7 @@ void CPositionSizeCalculator::RefreshValues() { if (sets.TradeDirection == Long) sets.TakeProfitLevel = sets.EntryLevel + sets.TakeProfit * _Point; else sets.TakeProfitLevel = sets.EntryLevel - sets.TakeProfit * _Point; - if (!TakeProfitLineIsBeingMoved) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, sets.TakeProfitLevel); + if (!TakeProfitLineIsBeingMoved[0]) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, sets.TakeProfitLevel); } // Additional take-profits. if (sets.TakeProfitsNumber > 1) @@ -1650,7 +1709,7 @@ void CPositionSizeCalculator::RefreshValues() if (sets.TradeDirection == Long) sets.TP[i] = sets.EntryLevel + StringToDouble(AdditionalTPEdits[i - 1].Text()) * _Point; else sets.TP[i] = sets.EntryLevel - StringToDouble(AdditionalTPEdits[i - 1].Text()) * _Point; } - if (!TakeProfitLineIsBeingMoved) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, sets.TP[i]); + if (!TakeProfitLineIsBeingMoved[i]) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, sets.TP[i]); } } } @@ -1682,6 +1741,8 @@ void CPositionSizeCalculator::RefreshValues() RecalculatePositionSize(); DisplayValues(); + + DoBreakEven(); LastRecalculationTime = GetTickCount(); } @@ -1775,12 +1836,7 @@ void CPositionSizeCalculator::ShowMain() m_EdtRiskMRes.Show(); if (sets.TakeProfitLevel != 0) { - m_LblReward.Show(); - m_EdtReward1.Show(); - m_EdtReward2.Show(); - m_LblRR.Show(); - if (InputRR != "") m_EdtRR1.Show(); - m_EdtRR2.Show(); + ShowTPRelatedEdits(); } m_LblPosSize.Show(); if (ShowMaxPSButton) m_BtnMaxPS.Show(); @@ -1974,12 +2030,7 @@ void CPositionSizeCalculator::ProcessTPChange(const bool tp_button_click) { if (sets.SelectedTab == MainTab) { - m_LblRR.Show(); - if (InputRR != "") m_EdtRR1.Show(); - m_EdtRR2.Show(); - m_LblReward.Show(); - m_EdtReward1.Show(); - m_EdtReward2.Show(); + ShowTPRelatedEdits(); } } if (sets.ShowLines) @@ -2116,21 +2167,20 @@ void CPositionSizeCalculator::OnClickBtnOrderType() sets.WasSelectedEntryLine = ObjectGetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTED); ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTABLE, false); ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTED, false); - if (!m_EdtEntryLevel.ReadOnly(true)) return; - if (!m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE)) return; - m_BtnOrderType.Text("Instant"); m_BtnEntryIncrease.Hide(); m_BtnEntryDecrease.Hide(); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); } else // Pending { ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTABLE, true); if ((sets.WasSelectedEntryLine) || (DefaultLinesSelected)) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTED, true); - if (!m_EdtEntryLevel.ReadOnly(false)) return; - if (!m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_ENABLE)) return; - m_BtnOrderType.Text("Pending"); - m_BtnEntryIncrease.Show(); - m_BtnEntryDecrease.Show(); + if ((sets.SelectedTab == MainTab) && (!m_minimized)) + { + m_BtnEntryIncrease.Show(); + m_BtnEntryDecrease.Show(); + } + if ((sets.ShowLines) && (ShowLineLabels)) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); } RefreshValues(); @@ -2199,6 +2249,11 @@ void CPositionSizeCalculator::OnClickBtnLines() ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_BACK, DrawTextAsBackground); } + if (sets.EntryType == Pending) + { + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_BACK, DrawTextAsBackground); + } if (StringToDouble(m_EdtTP.Text()) != 0) { ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -2250,6 +2305,7 @@ void CPositionSizeCalculator::OnClickBtnLines() ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); } ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); @@ -2445,8 +2501,10 @@ void CPositionSizeCalculator::OnClickBtnMaxPS() { OutputPositionSize = OutputMaxPositionSize; sets.RiskFromPositionSize = true; - double d_val = StringToDouble(m_EdtPosSize.Text()); - if (OutputPositionSize != d_val) + string text = m_EdtPosSize.Text(); + StringReplace(text, ",", ""); // Remove commas that might appear as the thousands separator due to number formatting. + double field_value = StringToDouble(text); + if (OutputPositionSize != field_value) { m_EdtPosSize.Text(FormatDouble(DoubleToString(OutputPositionSize, LotStep_digits), LotStep_digits)); sets.PositionSize = OutputPositionSize; @@ -2520,6 +2578,11 @@ void CPositionSizeCalculator::OnClickBtnTradingTPShare() } sets.ShareVolumeMode = Equal; // Next mode. } + // Switch color back to normal if it was red because the button results in correct shares. + for (int j = 0; j < sets.TakeProfitsNumber; j++) + { + TradingTPShareEdits[j].Color(m_EdtSL.Color()); // Normal color. + } RefreshValues(); } @@ -2842,13 +2905,39 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (ArraySize(sets.TP) < sets.TakeProfitsNumber) // Resize only if required. Sometimes, when switching symbols, this won't be required. { ArrayResize(sets.TP, sets.TakeProfitsNumber); + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); ArrayResize(sets.TPShare, sets.TakeProfitsNumber); - ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); + if (sets.ShareVolumeMode == Decreasing) // Do the previous method because sets.ShareVolumeMode gets switched over once you click the button. + { + ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); + } + else if (sets.ShareVolumeMode == Increasing) + { + sets.TPShare[0] = 50; + int remaining_volume = 50; + for (int i = 1; i < sets.TakeProfitsNumber; i++) + { + if (i == sets.TakeProfitsNumber - 1) sets.TPShare[i] = remaining_volume; + else sets.TPShare[i] = (int)MathRound((double)remaining_volume / 2.0); + remaining_volume -= sets.TPShare[i]; + } + } + else if (sets.ShareVolumeMode == Equal) + { + sets.TPShare[sets.TakeProfitsNumber - 1] = 50; + int remaining_volume = 50; + for (int i = sets.TakeProfitsNumber - 2; i >= 0 ; i--) + { + if (i == 0) sets.TPShare[i] = remaining_volume; + else sets.TPShare[i] = (int)MathRound((double)remaining_volume / 2.0); + remaining_volume -= sets.TPShare[i]; + } + } ArrayResize(sets.WasSelectedAdditionalTakeProfitLine, sets.TakeProfitsNumber - 1); // -1 because the flag for the main TP is saved elsewhere. ArrayResize(ArrayPositionSize, sets.TakeProfitsNumber); } - // Move everything on the Trading tab down by one line to insert the new take-profit. + // Move everything on the Main tab down by one line to insert the new take-profit. int col_height = (int)MathRound(24 * m_DPIScale); CStringForList * obj; bool start_moving = false; // Wait till the first panel object that has to be moved is found. @@ -2880,6 +2969,11 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (MaxTakeProfitsNumber == 1) { ButtonCreate(MainTabList, m_BtnTakeProfitsNumberRemove, first_column_start, y, first_column_start + v_spacing * 4 - 1, y + element_height, name, "x", "Remove Take-profit"); + if (DarkMode) + { + m_BtnTakeProfitsNumberRemove.ColorBackground(DARKMODE_BUTTON_BG_COLOR); + m_BtnTakeProfitsNumberRemove.ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } MainTabList.MoveListElementByName(name, index); } } @@ -2893,25 +2987,48 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (MaxTakeProfitsNumber < sets.TakeProfitsNumber) { int i = sets.TakeProfitsNumber - 2; - name = "AdditionalTPLabels" + IntegerToString(i + 2); + name = "m_LblAdditionalTPLabels" + IntegerToString(i + 2); LabelCreate(MainTabList, AdditionalTPLabels[i], first_column_start + v_spacing * 4, y, first_column_start + normal_label_width, y + element_height, name, additional_tp_label_beginning + IntegerToString(i + 2) + additional_tp_label_end); + if (DarkMode) + { + AdditionalTPLabels[i].Color(DARKMODE_TEXT_COLOR); + } MainTabList.MoveListElementByName(name, index); - name = "AdditionalTPEdits" + IntegerToString(i + 2); + name = "m_EdtAdditionalTPEdits" + IntegerToString(i + 2); EditCreate(MainTabList, AdditionalTPEdits[i], second_column_start, y, second_column_start + normal_edit_width, y + element_height, name, ""); AdditionalTPEdits[i].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + AdditionalTPEdits[i].ColorBackground(DARKMODE_EDIT_BG_COLOR); + AdditionalTPEdits[i].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } MainTabList.MoveListElementByName(name, index + 1); - name = "AdditionalTPButtonsIncrease" + IntegerToString(i + 2); + name = "m_BtnAdditionalTPButtonsIncrease" + IntegerToString(i + 2); ButtonCreate(MainTabList, AdditionalTPButtonsIncrease[i], second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, name, "+", "Increase Take-profit #" + IntegerToString(i + 2) + " by 1 point"); + if (DarkMode) + { + AdditionalTPButtonsIncrease[i].ColorBackground(DARKMODE_BUTTON_BG_COLOR); + AdditionalTPButtonsIncrease[i].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } MainTabList.MoveListElementByName(name, index + 2); - name = "AdditionalTPButtonsDecrease" + IntegerToString(i + 2); + name = "m_BtnAdditionalTPButtonsDecrease" + IntegerToString(i + 2); ButtonCreate(MainTabList, AdditionalTPButtonsDecrease[i], second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, name, "-", "Decrease Take-profit #" + IntegerToString(i + 2) + " by 1 point"); + if (DarkMode) + { + AdditionalTPButtonsDecrease[i].ColorBackground(DARKMODE_BUTTON_BG_COLOR); + AdditionalTPButtonsDecrease[i].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } MainTabList.MoveListElementByName(name, index + 3); - name = "AdditionalTPWarnings" + IntegerToString(i + 2); + name = "m_LblAdditionalTPWarnings" + IntegerToString(i + 2); LabelCreate(MainTabList, AdditionalTPWarnings[i], third_column_start, y, third_column_start + narrow_label_width, y + element_height, name, " "); + if (DarkMode) + { + AdditionalTPWarnings[i].Color(DARKMODE_TEXT_COLOR); + } MainTabList.MoveListElementByName(name, index + 4); } @@ -2926,8 +3043,8 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() { if (!start_moving) { - // The "Points" label on the Trading tab. - if (obj.Name == "m_LblTradingPoints") + // The "Points" label on the Trading tab. If it is absent, then the "Subtract position volume" checkbox. If it is absent, "Ask for confimration" checkbox. + if (((ShowFusesOnTrading) && (obj.Name == "m_LblTradingPoints")) || ((ShowCheckboxesOnTrading) && (obj.Name == "m_ChkSubtractPositions")) || (obj.Name == "m_ChkAskForConfirmation")) { start_moving = true; // From now on everything below should be moved down. y = obj.Obj.Top() - col_height - remember_top; // Remember the y where the new TP fields will be inserted. Relative measurement. @@ -2951,18 +3068,37 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() { name = "m_LblTradingTP"; LabelCreate(TradingTabList, m_LblTradingTP, multi_tp_column_start, y, multi_tp_column_start + multi_tp_label_width, y + element_height, name, "TP"); + if (DarkMode) + { + m_LblTradingTP.Color(DARKMODE_TEXT_COLOR); + } TradingTabList.MoveListElementByName(name, index); name = "m_BtnTPsInward"; ButtonCreate(TradingTabList, m_BtnTPsInward, multi_tp_button_start, y, multi_tp_button_start + leverage_edit_width, y + element_height, name, "<<", "Fill additional TPs equidistantly between Entry and Main TP."); + if (DarkMode) + { + m_BtnTPsInward.ColorBackground(DARKMODE_BUTTON_BG_COLOR); + m_BtnTPsInward.ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 1); name = "m_BtnTPsOutward"; ButtonCreate(TradingTabList, m_BtnTPsOutward, multi_tp_button_start + leverage_edit_width + v_spacing, y, multi_tp_button_start + 2 * leverage_edit_width + v_spacing, y + element_height, name, ">>", "Place additional TPs beyond the Main TP using the same distance."); + if (DarkMode) + { + m_BtnTPsOutward.ColorBackground(DARKMODE_BUTTON_BG_COLOR); + m_BtnTPsOutward.ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 2); name = "m_BtnTradingTPShare"; ButtonCreate(TradingTabList, m_BtnTradingTPShare, third_trading_column_start, y, third_trading_column_start + normal_edit_width, y + element_height, name, "Share, %", "Automatically fill the volume shares"); + if (DarkMode) + { + m_BtnTradingTPShare.ColorBackground(DARKMODE_BUTTON_BG_COLOR); + m_BtnTradingTPShare.ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 3); y += col_height; @@ -2972,16 +3108,30 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() name = "m_LblTradingTPLabel1"; LabelCreate(TradingTabList, TradingTPLabels[0], first_column_start, y, first_column_start + normal_label_width, y + element_height, name, "Take-profit 1"); + if (DarkMode) + { + TradingTPLabels[0].Color(DARKMODE_TEXT_COLOR); + } TradingTabList.MoveListElementByName(name, index); name = "m_EdtTradingTPEdit1"; EditCreate(TradingTabList, TradingTPEdits[0], multi_tp_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, name, ""); TradingTPEdits[0].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + TradingTPEdits[0].ColorBackground(DARKMODE_EDIT_BG_COLOR); + TradingTPEdits[0].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 1); name = "m_EdtTradingTPShareEdit1"; EditCreate(TradingTabList, TradingTPShareEdits[0], third_trading_column_start, y, third_trading_column_start + leverage_edit_width, y + element_height, name, ""); TradingTPShareEdits[0].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + TradingTPShareEdits[0].ColorBackground(DARKMODE_EDIT_BG_COLOR); + TradingTPShareEdits[0].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 2); } else @@ -3008,16 +3158,30 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() { name = "m_LblTradingTPLabel" + IntegerToString(sets.TakeProfitsNumber); LabelCreate(TradingTabList, TradingTPLabels[sets.TakeProfitsNumber - 1], first_column_start, y, first_column_start + normal_label_width, y + element_height, name, "Take-profit " + IntegerToString(sets.TakeProfitsNumber)); + if (DarkMode) + { + TradingTPLabels[sets.TakeProfitsNumber - 1].Color(DARKMODE_TEXT_COLOR); + } TradingTabList.MoveListElementByName(name, index); name = "m_EdtTradingTPEdit" + IntegerToString(sets.TakeProfitsNumber); EditCreate(TradingTabList, TradingTPEdits[sets.TakeProfitsNumber - 1], multi_tp_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, name, ""); TradingTPEdits[sets.TakeProfitsNumber - 1].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + TradingTPEdits[sets.TakeProfitsNumber - 1].ColorBackground(DARKMODE_EDIT_BG_COLOR); + TradingTPEdits[sets.TakeProfitsNumber - 1].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 1); name = "m_EdtTradingTPShareEdit" + IntegerToString(sets.TakeProfitsNumber); EditCreate(TradingTabList, TradingTPShareEdits[sets.TakeProfitsNumber - 1], third_trading_column_start, y, third_trading_column_start + leverage_edit_width, y + element_height, name, ""); TradingTPShareEdits[sets.TakeProfitsNumber - 1].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + TradingTPShareEdits[sets.TakeProfitsNumber - 1].ColorBackground(DARKMODE_EDIT_BG_COLOR); + TradingTPShareEdits[sets.TakeProfitsNumber - 1].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 2); } else @@ -3029,6 +3193,17 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (MaxTakeProfitsNumber < sets.TakeProfitsNumber) MaxTakeProfitsNumber = sets.TakeProfitsNumber; + if (sets.TakeProfitLevel != 0) // If added a new TP when the first TP was already set, set some value to the new one too. + { + if (!TPDistanceInPoints) sets.TP[sets.TakeProfitsNumber - 1] = sets.EntryLevel + (sets.TakeProfitLevel - sets.EntryLevel) * sets.TakeProfitsNumber; + else + { + if (sets.TradeDirection == Short) sets.TP[sets.TakeProfitsNumber - 1] = sets.EntryLevel - sets.TakeProfit * _Point * sets.TakeProfitsNumber; + else if (sets.TradeDirection == Long) sets.TP[sets.TakeProfitsNumber - 1] = sets.EntryLevel + sets.TakeProfit * _Point * sets.TakeProfitsNumber; + AdditionalTPEdits[sets.TakeProfitsNumber - 2].Text(IntegerToString(sets.TakeProfit * sets.TakeProfitsNumber)); + } + } + if ((ShowLineLabels) || (ShowAdditionalTPLabel)) Initialization(); // Creates necessary line labels. HideShowMaximize(); // For panel resizing. RefreshValues(); // For some value to appear inside the TP edit field. @@ -3038,7 +3213,7 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() // Removed TPs should still be deleted from the TabList lists of names and probably hidden? void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberRemove() { - // Move everything on the Trading tab up by one line as the bottom-most take-profit is removed. + // Move everything on the Main tab up by one line as the bottom-most take-profit is removed. int col_height = (int)MathRound(24 * m_DPIScale); CStringForList * obj; bool start_moving = false; // Wait till the first panel object that has to be moved is found. @@ -3085,8 +3260,8 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberRemove() { if (!start_moving) { - // The "Points" label on the Trading tab. - if (obj.Name == "m_LblTradingPoints") + // The "Points" label on the Trading tab. If it is absent, then the "Subtract position volume" checkbox. If it is absent, "Ask for confimration" checkbox. + if (((ShowFusesOnTrading) && (obj.Name == "m_LblTradingPoints")) || ((ShowCheckboxesOnTrading) && (obj.Name == "m_ChkSubtractPositions")) || (obj.Name == "m_ChkAskForConfirmation")) { start_moving = true; // From now on everything below should be moved up. if (sets.TakeProfitsNumber == 2) m = 3; // Will be moving three rows up: headers + main TP + first secondary TP. @@ -3120,7 +3295,37 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberRemove() // Clean up data of the delted TP. sets.TakeProfitsNumber--; ArrayResize(sets.TP, sets.TakeProfitsNumber); - ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); + if (sets.ShareVolumeMode == Decreasing) // Do the previous method because sets.ShareVolumeMode gets switched over once you click the button. + { + ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); + } + else if (sets.ShareVolumeMode == Increasing) + { + sets.TPShare[0] = 50; + int remaining_volume = 50; + for (int j = 1; j < sets.TakeProfitsNumber; j++) + { + if (j == sets.TakeProfitsNumber - 1) sets.TPShare[j] = remaining_volume; + else sets.TPShare[j] = (int)MathRound((double)remaining_volume / 2.0); + remaining_volume -= sets.TPShare[j]; + } + } + else if (sets.ShareVolumeMode == Equal) + { + sets.TPShare[sets.TakeProfitsNumber - 1] = 50; + int remaining_volume = 50; + for (int j = sets.TakeProfitsNumber - 2; j >= 0 ; j--) + { + if (j == 0) sets.TPShare[j] = remaining_volume; + else sets.TPShare[j] = (int)MathRound((double)remaining_volume / 2.0); + remaining_volume -= sets.TPShare[j]; + } + } + for (int j = 0; j < sets.TakeProfitsNumber; j++) + { + TradingTPShareEdits[j].Text(IntegerToString(sets.TPShare[j])); // Display. + } ArrayResize(sets.TPShare, sets.TakeProfitsNumber); ArrayResize(sets.WasSelectedAdditionalTakeProfitLine, sets.TakeProfitsNumber - 1); // -1 because the flag for the main TP is saved elsewhere. ArrayResize(ArrayPositionSize, sets.TakeProfitsNumber); @@ -3276,12 +3481,7 @@ void CPositionSizeCalculator::OnEndEditEdtTP() } else // Show. { - m_LblRR.Show(); - if (InputRR != "") m_EdtRR1.Show(); - m_EdtRR2.Show(); - m_LblReward.Show(); - m_EdtReward1.Show(); - m_EdtReward2.Show(); + ShowTPRelatedEdits(); if (sets.ShowLines) { ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -3328,6 +3528,17 @@ void CPositionSizeCalculator::OnEndEditEdtTP() } } +// A public function to be run from event processing and from member functions. +void CPositionSizeCalculator::ShowTPRelatedEdits() +{ + m_LblRR.Show(); + if (InputRR != "") m_EdtRR1.Show(); + m_EdtRR2.Show(); + m_LblReward.Show(); + m_EdtReward1.Show(); + m_EdtReward2.Show(); +} + void CPositionSizeCalculator::OnEndEditEdtCommissionSize() { if (sets.CommissionPerLot != StringToDouble(m_EdtCommissionSize.Text())) @@ -3341,7 +3552,9 @@ void CPositionSizeCalculator::OnEndEditEdtCommissionSize() void CPositionSizeCalculator::OnEndEditEdtAccount() { - double field_value = StringToDouble(m_EdtAccount.Text()); + string text = m_EdtAccount.Text(); + StringReplace(text, ",", ""); // Remove commas that might appear as the thousands separator due to number formatting. + double field_value = StringToDouble(text); if (sets.CustomBalance != field_value) { if (field_value >= 0) sets.CustomBalance = field_value; @@ -3352,11 +3565,14 @@ void CPositionSizeCalculator::OnEndEditEdtAccount() void CPositionSizeCalculator::OnEndEditEdtRiskPIn() { + string text = m_EdtRiskPIn.Text(); + StringReplace(text, ",", ""); // Remove commas that might appear as the thousands separator due to number formatting. + double field_value = StringToDouble(text); sets.UseMoneyInsteadOfPercentage = false; sets.RiskFromPositionSize = false; - if (sets.Risk != StringToDouble(m_EdtRiskPIn.Text())) + if (sets.Risk != field_value) { - sets.Risk = StringToDouble(m_EdtRiskPIn.Text()); + sets.Risk = field_value; CalculateRiskAndPositionSize(); DisplayValues(); } @@ -3364,13 +3580,14 @@ void CPositionSizeCalculator::OnEndEditEdtRiskPIn() void CPositionSizeCalculator::OnEndEditEdtRiskMIn() { - string s_val = m_EdtRiskMIn.Text(); - StringReplace(s_val, ",", ""); + string text = m_EdtRiskMIn.Text(); + StringReplace(text, ",", ""); + double field_value = StringToDouble(text); sets.UseMoneyInsteadOfPercentage = true; sets.RiskFromPositionSize = false; - if (sets.MoneyRisk != StringToDouble(s_val)) + if (sets.MoneyRisk != field_value) { - sets.MoneyRisk = StringToDouble(s_val); + sets.MoneyRisk = field_value; CalculateRiskAndPositionSize(); DisplayValues(); } @@ -3378,15 +3595,16 @@ void CPositionSizeCalculator::OnEndEditEdtRiskMIn() void CPositionSizeCalculator::OnEndEditEdtPosSize() { - sets.RiskFromPositionSize = true; - - double d_val = StringToDouble(m_EdtPosSize.Text()); - if (d_val >= 0) + string text = m_EdtPosSize.Text(); + StringReplace(text, ",", ""); + double field_value = StringToDouble(text); + if (field_value >= 0) { - if (OutputPositionSize != d_val) + if (OutputPositionSize != field_value) { - OutputPositionSize = d_val; + OutputPositionSize = field_value; sets.PositionSize = OutputPositionSize; + sets.RiskFromPositionSize = true; CalculateRiskAndPositionSize(); DisplayValues(); } @@ -3460,12 +3678,7 @@ void CPositionSizeCalculator::OnEndEditATRMultiplierTP() } else if (sets.ATRMultiplierTP == 0) // Was zero. { - m_LblRR.Show(); - if (InputRR != "") m_EdtRR1.Show(); - m_EdtRR2.Show(); - m_LblReward.Show(); - m_EdtReward1.Show(); - m_EdtReward2.Show(); + ShowTPRelatedEdits(); sets.ATRMultiplierTP = d_val; RefreshValues(); MoveAndResize(); @@ -3581,10 +3794,20 @@ void CPositionSizeCalculator::OnEndEditEdtMinEntrySLDistance() sets.MinEntrySLDistance = (int)StringToInteger(m_EdtMinEntrySLDistance.Text()); } -void CPositionSizeCalculator::OnEndEditEdtMaxPositionSize() +void CPositionSizeCalculator::OnEndEditEdtMaxPositionSizeTotal() +{ + sets.MaxPositionSizeTotal = (double)StringToDouble(m_EdtMaxPositionSizeTotal.Text()); + // Only allow changing the total value to be no lower than the per symbol value. Zero is an exception. + if ((sets.MaxPositionSizeTotal < sets.MaxPositionSizePerSymbol) && (sets.MaxPositionSizeTotal != 0)) sets.MaxPositionSizeTotal = sets.MaxPositionSizePerSymbol; + m_EdtMaxPositionSizeTotal.Text(DoubleToString(sets.MaxPositionSizeTotal, LotStep_digits)); +} + +void CPositionSizeCalculator::OnEndEditEdtMaxPositionSizePerSymbol() { - sets.MaxPositionSize = (double)StringToDouble(m_EdtMaxPositionSize.Text()); - m_EdtMaxPositionSize.Text(DoubleToString(sets.MaxPositionSize, LotStep_digits)); + sets.MaxPositionSizePerSymbol = (double)StringToDouble(m_EdtMaxPositionSizePerSymbol.Text()); + // Only allow changing the per symbol value to be no greater than the per symbol value. Zero is an exception. + if ((sets.MaxPositionSizePerSymbol > sets.MaxPositionSizeTotal) && (sets.MaxPositionSizeTotal != 0)) sets.MaxPositionSizePerSymbol = sets.MaxPositionSizeTotal; + m_EdtMaxPositionSizePerSymbol.Text(DoubleToString(sets.MaxPositionSizePerSymbol, LotStep_digits)); } void CPositionSizeCalculator::OnChangeChkSubtractPositions() @@ -3629,21 +3852,36 @@ void CPositionSizeCalculator::OnEndEditEdtBreakEvenPoints() m_EdtBreakEvenPoints.Text(IntegerToString(sets.BreakEvenPoints)); } -void CPositionSizeCalculator::OnEndEditEdtMaxNumberOfTrades() +void CPositionSizeCalculator::OnEndEditEdtMaxNumberOfTradesTotal() { - sets.MaxNumberOfTrades = (int)StringToInteger(m_EdtMaxNumberOfTrades.Text()); - m_EdtMaxNumberOfTrades.Text(IntegerToString(sets.MaxNumberOfTrades)); + sets.MaxNumberOfTradesTotal = (int)StringToInteger(m_EdtMaxNumberOfTradesTotal.Text()); + // Only allow changing the total value to be no lower than the per symbol value. Zero is an exception. + if ((sets.MaxNumberOfTradesTotal < sets.MaxNumberOfTradesPerSymbol) && (sets.MaxNumberOfTradesTotal != 0)) sets.MaxNumberOfTradesTotal = sets.MaxNumberOfTradesPerSymbol; + m_EdtMaxNumberOfTradesTotal.Text(IntegerToString(sets.MaxNumberOfTradesTotal)); } -void CPositionSizeCalculator::OnEndEditEdtMaxTotalRisk() +void CPositionSizeCalculator::OnEndEditEdtMaxNumberOfTradesPerSymbol() { - sets.MaxTotalRisk = StringToDouble(m_EdtMaxTotalRisk.Text()); - m_EdtMaxTotalRisk.Text(DoubleToString(sets.MaxTotalRisk, 2)); + sets.MaxNumberOfTradesPerSymbol = (int)StringToInteger(m_EdtMaxNumberOfTradesPerSymbol.Text()); + // Only allow changing the per symbol value to be no greater than the per symbol value. Zero is an exception. + if ((sets.MaxNumberOfTradesPerSymbol > sets.MaxNumberOfTradesTotal) && (sets.MaxNumberOfTradesTotal != 0)) sets.MaxNumberOfTradesPerSymbol = sets.MaxNumberOfTradesTotal; + m_EdtMaxNumberOfTradesPerSymbol.Text(IntegerToString(sets.MaxNumberOfTradesPerSymbol)); } -void CPositionSizeCalculator::OnChangeChkAllSymbols() +void CPositionSizeCalculator::OnEndEditEdtMaxRiskTotal() { - sets.AllSymbols = m_ChkAllSymbols.Checked(); + sets.MaxRiskTotal = StringToDouble(m_EdtMaxRiskTotal.Text()); + // Only allow changing the total value to be no lower than the per symbol value. Zero is an exception. + if ((sets.MaxRiskTotal < sets.MaxRiskPerSymbol) && (sets.MaxRiskTotal != 0)) sets.MaxRiskTotal = sets.MaxRiskPerSymbol; + m_EdtMaxRiskTotal.Text(DoubleToString(sets.MaxRiskTotal, 2)); +} + +void CPositionSizeCalculator::OnEndEditEdtMaxRiskPerSymbol() +{ + sets.MaxRiskPerSymbol = StringToDouble(m_EdtMaxRiskPerSymbol.Text()); + // Only allow changing the per symbol value to be no greater than the per symbol value. Zero is an exception. + if ((sets.MaxRiskPerSymbol > sets.MaxRiskTotal) && (sets.MaxRiskTotal != 0)) sets.MaxRiskPerSymbol = sets.MaxRiskTotal; + m_EdtMaxRiskPerSymbol.Text(DoubleToString(sets.MaxRiskPerSymbol, 2)); } //+-----------------------+ @@ -3738,8 +3976,6 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(sets.MaxEntrySLDistance)); FileWrite(fh, "MinEntrySLDistance"); FileWrite(fh, IntegerToString(sets.MinEntrySLDistance)); - FileWrite(fh, "MaxPositionSize"); - FileWrite(fh, DoubleToString(sets.MaxPositionSize, LotStep_digits)); FileWrite(fh, "StopLoss"); FileWrite(fh, IntegerToString(sets.StopLoss)); FileWrite(fh, "TakeProfit"); @@ -3789,12 +4025,18 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(sets.TrailingStopPoints)); FileWrite(fh, "BreakEvenPoints"); FileWrite(fh, IntegerToString(sets.BreakEvenPoints)); - FileWrite(fh, "MaxNumberOfTrades"); - FileWrite(fh, IntegerToString(sets.MaxNumberOfTrades)); - FileWrite(fh, "MaxTotalRisk"); - FileWrite(fh, DoubleToString(sets.MaxTotalRisk, 2)); - FileWrite(fh, "AllSymbols"); - FileWrite(fh, IntegerToString(sets.AllSymbols)); + FileWrite(fh, "MaxNumberOfTradesTotal"); + FileWrite(fh, IntegerToString(sets.MaxNumberOfTradesTotal)); + FileWrite(fh, "MaxNumberOfTradesPerSymbol"); + FileWrite(fh, IntegerToString(sets.MaxNumberOfTradesPerSymbol)); + FileWrite(fh, "MaxPositionSizeTotal"); + FileWrite(fh, DoubleToString(sets.MaxPositionSizeTotal, LotStep_digits)); + FileWrite(fh, "MaxPositionSizePerSymbol"); + FileWrite(fh, DoubleToString(sets.MaxPositionSizePerSymbol, LotStep_digits)); + FileWrite(fh, "MaxRiskTotal"); + FileWrite(fh, DoubleToString(sets.MaxRiskTotal, 2)); + FileWrite(fh, "MaxRiskPerSymbol"); + FileWrite(fh, DoubleToString(sets.MaxRiskPerSymbol, 2)); FileWrite(fh, "IsPanelMinimized"); FileWrite(fh, IntegerToString(sets.IsPanelMinimized)); FileWrite(fh, "TPLockedOnSL"); @@ -3805,9 +4047,9 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(sets.TemplateChanged)); // These are not part of settings but are panel-related input parameters. - // When indicator is reloaded due to its input parameters change, these should be compared to the new values. + // When the EA is reloaded due to its input parameters change, these should be compared to the new values. // If the value is changed, it should be updated in the panel too. - // Is indicator reloading due to the input parameters change? + // Is the EA reloading due to the input parameters change? if (GlobalVariableGet("PS-" + IntegerToString(ChartID()) + "-Parameters") > 0) { FileWrite(fh, "Parameter_DefaultTradeDirection"); @@ -3870,8 +4112,10 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(DefaultMaxEntrySLDistance)); FileWrite(fh, "Parameter_DefaultMinEntrySLDistance"); FileWrite(fh, IntegerToString(DefaultMinEntrySLDistance)); - FileWrite(fh, "Parameter_DefaultMaxPositionSize"); - FileWrite(fh, DoubleToString(DefaultMaxPositionSize, 2)); + FileWrite(fh, "Parameter_DefaultMaxPositionSizeTotal"); + FileWrite(fh, DoubleToString(DefaultMaxPositionSizeTotal, LotStep_digits)); + FileWrite(fh, "Parameter_DefaultMaxPositionSizePerSymbol"); + FileWrite(fh, DoubleToString(DefaultMaxPositionSizePerSymbol, LotStep_digits)); FileWrite(fh, "Parameter_DefaultSubtractOPV"); FileWrite(fh, IntegerToString(DefaultSubtractOPV)); FileWrite(fh, "Parameter_DefaultSubtractPOV"); @@ -3898,12 +4142,14 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(DefaultSpreadAdjustmentSL)); FileWrite(fh, "Parameter_DefaultSpreadAdjustmentTP"); FileWrite(fh, IntegerToString(DefaultSpreadAdjustmentTP)); - FileWrite(fh, "Parameter_DefaultMaxNumberOfTrades"); - FileWrite(fh, IntegerToString(DefaultMaxNumberOfTrades)); - FileWrite(fh, "Parameter_DefaultMaxTotalRisk"); - FileWrite(fh, DoubleToString(DefaultMaxTotalRisk)); - FileWrite(fh, "Parameter_DefaultAllSymbols"); - FileWrite(fh, IntegerToString(DefaultAllSymbols)); + FileWrite(fh, "Parameter_DefaultMaxNumberOfTradesTotal"); + FileWrite(fh, IntegerToString(DefaultMaxNumberOfTradesTotal)); + FileWrite(fh, "Parameter_DefaultMaxNumberOfTradesPerSymbol"); + FileWrite(fh, IntegerToString(DefaultMaxNumberOfTradesPerSymbol)); + FileWrite(fh, "Parameter_DefaultMaxRiskTotal"); + FileWrite(fh, DoubleToString(DefaultMaxRiskTotal)); + FileWrite(fh, "Parameter_DefaultMaxRiskPerSymbol"); + FileWrite(fh, DoubleToString(DefaultMaxRiskPerSymbol)); FileWrite(fh, "Parameter_DefaultTakeProfitsNumber"); FileWrite(fh, IntegerToString(DefaultTakeProfitsNumber)); } @@ -3957,6 +4203,7 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); ArrayResize(sets.WasSelectedAdditionalTakeProfitLine, sets.TakeProfitsNumber - 1); // -1 because the flag for the main TP is saved elsewhere. } + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); } else if (var_name == "Risk") sets.Risk = StringToDouble(var_content); @@ -4003,12 +4250,18 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() sets.TrailingStopPoints = (int)StringToInteger(var_content); else if (var_name == "BreakEvenPoints") sets.BreakEvenPoints = (int)StringToInteger(var_content); - else if (var_name == "MaxNumberOfTrades") - sets.MaxNumberOfTrades = (int)StringToInteger(var_content); - else if (var_name == "MaxTotalRisk") - sets.MaxTotalRisk = StringToDouble(var_content); - else if (var_name == "AllSymbols") - sets.AllSymbols = (bool)StringToInteger(var_content); + else if (var_name == "MaxNumberOfTradesTotal") + sets.MaxNumberOfTradesTotal = (int)StringToInteger(var_content); + else if (var_name == "MaxNumberOfTradesPerSymbol") + sets.MaxNumberOfTradesPerSymbol = (int)StringToInteger(var_content); + else if (var_name == "MaxPositionSizeTotal") + sets.MaxPositionSizeTotal = StringToDouble(var_content); + else if (var_name == "MaxPositionSizePerSymbol") + sets.MaxPositionSizePerSymbol = StringToDouble(var_content); + else if (var_name == "MaxRiskTotal") + sets.MaxRiskTotal = StringToDouble(var_content); + else if (var_name == "MaxRiskPerSymbol") + sets.MaxRiskPerSymbol = StringToDouble(var_content); else if (var_name == "DisableTradingWhenLinesAreHidden") sets.DisableTradingWhenLinesAreHidden = (bool)StringToInteger(var_content); // Multiple TPs. @@ -4032,8 +4285,6 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() sets.MaxEntrySLDistance = (int)StringToInteger(var_content); else if (var_name == "MinEntrySLDistance") sets.MinEntrySLDistance = (int)StringToInteger(var_content); - else if (var_name == "MaxPositionSize") - sets.MaxPositionSize = StringToDouble(var_content); else if (var_name == "TradeDirection") sets.TradeDirection = (TRADE_DIRECTION)StringToInteger(var_content); else if (var_name == "StopLoss") @@ -4084,11 +4335,11 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() else if (var_name == "TemplateChanged") sets.TemplateChanged = (bool)StringToInteger(var_content); - // Is indicator reloading due to the input parameters change? - if (GlobalVariableGet("PS-" + IntegerToString(ChartID()) + "-Parameters") > 0) + // Is expert advisor reloading due to the input parameters change? + else if (GlobalVariableGet("PS-" + IntegerToString(ChartID()) + "-Parameters") > 0) { // These are not part of settings but are panel-related input parameters. - // When indicator is reloaded due to its input parameters change, these should be compared to the new values. + // When the expert advisor is reloaded due to its input parameters change, these should be compared to the new values. // If the value is changed, it should be updated in the panel too. if (var_name == "Parameter_DefaultTradeDirection") { @@ -4168,10 +4419,10 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() } else if (var_name == "Parameter_DefaultMoneyRisk") { - if ((StringToDouble(var_content) != DefaultMoneyRisk) && (DefaultMoneyRisk > 0)) + if (DefaultMoneyRisk > 0) { - sets.MoneyRisk = DefaultMoneyRisk; - sets.UseMoneyInsteadOfPercentage = true; + sets.UseMoneyInsteadOfPercentage = true; // Should be set to true whenever the DefaultMoneyRisk is non-zero. + if (StringToDouble(var_content) != DefaultMoneyRisk) sets.MoneyRisk = DefaultMoneyRisk; } else sets.UseMoneyInsteadOfPercentage = false; } @@ -4240,9 +4491,13 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() { if (StringToInteger(var_content) != DefaultMinEntrySLDistance) sets.MinEntrySLDistance = DefaultMinEntrySLDistance; } - else if (var_name == "Parameter_DefaultMaxPositionSize") + else if (var_name == "Parameter_DefaultMaxPositionSizeTotal") { - if (StringToDouble(var_content) != DefaultMaxPositionSize) sets.MaxPositionSize = DefaultMaxPositionSize; + if (StringToDouble(var_content) != DefaultMaxPositionSizeTotal) sets.MaxPositionSizeTotal = DefaultMaxPositionSizeTotal; + } + else if (var_name == "Parameter_DefaultMaxPositionSizePerSymbol") + { + if (StringToDouble(var_content) != DefaultMaxPositionSizePerSymbol) sets.MaxPositionSizePerSymbol = DefaultMaxPositionSizePerSymbol; } else if (var_name == "Parameter_DefaultSubtractOPV") { @@ -4289,25 +4544,29 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() { if (StringToInteger(var_content) != DefaultBreakEven) sets.BreakEvenPoints = DefaultBreakEven; } - else if (var_name == "Parameter_DefaultMaxNumberOfTrades") + else if (var_name == "Parameter_DefaultSpreadAdjustmentSL") { - if (StringToInteger(var_content) != DefaultMaxNumberOfTrades) sets.MaxNumberOfTrades = DefaultMaxNumberOfTrades; + if ((bool)StringToInteger(var_content) != DefaultSpreadAdjustmentSL) sets.SpreadAdjustmentSL = DefaultSpreadAdjustmentSL; } - else if (var_name == "Parameter_DefaultMaxTotalRisk") + else if (var_name == "Parameter_DefaultSpreadAdjustmentTP") { - if (StringToDouble(var_content) != DefaultMaxTotalRisk) sets.MaxTotalRisk = DefaultMaxTotalRisk; + if ((bool)StringToInteger(var_content) != DefaultSpreadAdjustmentTP) sets.SpreadAdjustmentTP = DefaultSpreadAdjustmentTP; } - else if (var_name == "Parameter_DefaultAllSymbols") + else if (var_name == "Parameter_DefaultMaxNumberOfTradesTotal") { - if ((bool)StringToInteger(var_content) != DefaultAllSymbols) sets.AllSymbols = DefaultAllSymbols; + if (StringToInteger(var_content) != DefaultMaxNumberOfTradesTotal) sets.MaxNumberOfTradesTotal = DefaultMaxNumberOfTradesTotal; } - else if (var_name == "Parameter_DefaultSpreadAdjustmentSL") + else if (var_name == "Parameter_DefaultMaxNumberOfTradesPerSymbol") { - if ((bool)StringToInteger(var_content) != DefaultSpreadAdjustmentSL) sets.SpreadAdjustmentSL = DefaultSpreadAdjustmentSL; + if (StringToInteger(var_content) != DefaultMaxNumberOfTradesPerSymbol) sets.MaxNumberOfTradesPerSymbol = DefaultMaxNumberOfTradesPerSymbol; } - else if (var_name == "Parameter_DefaultSpreadAdjustmentTP") + else if (var_name == "Parameter_DefaultMaxRiskTotal") { - if ((bool)StringToInteger(var_content) != DefaultSpreadAdjustmentTP) sets.SpreadAdjustmentTP = DefaultSpreadAdjustmentTP; + if (StringToDouble(var_content) != DefaultMaxRiskTotal) sets.MaxRiskTotal = DefaultMaxRiskTotal; + } + else if (var_name == "Parameter_DefaultMaxRiskPerSymbol") + { + if (StringToDouble(var_content) != DefaultMaxRiskPerSymbol) sets.MaxRiskPerSymbol = DefaultMaxRiskPerSymbol; } else if (var_name == "Parameter_DefaultTakeProfitsNumber") { @@ -4330,15 +4589,20 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); ArrayResize(sets.WasSelectedAdditionalTakeProfitLine, sets.TakeProfitsNumber - 1); // -1 because the flag for the main TP is saved elsewhere. } + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); } } } } + // Make sure total and per symbol values do not contradict each other. + if ((sets.MaxPositionSizeTotal < sets.MaxPositionSizePerSymbol) && (sets.MaxPositionSizeTotal != 0)) sets.MaxPositionSizeTotal = sets.MaxPositionSizePerSymbol; + if ((sets.MaxNumberOfTradesTotal < sets.MaxNumberOfTradesPerSymbol) && (sets.MaxNumberOfTradesTotal != 0)) sets.MaxNumberOfTradesTotal = sets.MaxNumberOfTradesPerSymbol; + if ((sets.MaxRiskTotal < sets.MaxRiskPerSymbol) && (sets.MaxRiskTotal != 0)) sets.MaxRiskTotal = sets.MaxRiskPerSymbol; FileClose(fh); Print("Loaded settings successfully."); - // Is indicator reloading due to the input parameters change? Delete the flag variable. + // Is expert advisor reloading due to the input parameters change? Delete the flag variable. if (GlobalVariableGet("PS-" + IntegerToString(ChartID()) + "-Parameters") > 0) GlobalVariableDel("PS-" + IntegerToString(ChartID()) + "-Parameters"); return true; @@ -4764,6 +5028,7 @@ string OutputPointValue = "", OutputSwapsType = "Unknown", SwapsTripleDay = "?", OutputSwapsCurrencyDailyLot = "", OutputSwapsCurrencyDailyPS = "", OutputSwapsCurrencyYearlyLot = "", OutputSwapsCurrencyYearlyPS = ""; string ProfitCurrency, account_currency, ReferenceSymbol = NULL, BaseCurrency, SwapConversionSymbol = "", AdditionalReferenceSymbol = NULL; bool ReferenceSymbolMode, AdditionalReferenceSymbolMode; +int WarnedAboutZeroUnitCost = 0; // Was there already a warning? // Used only when percentage commission is enabled: string ReferenceSymbolCommission = NULL, AdditionalReferenceSymbolCommission = NULL; bool ReferenceSymbolCommissionMode, AdditionalReferenceSymbolCommissionMode; @@ -4922,6 +5187,16 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_BACK, DrawTextAsBackground); ObjectSetString(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TOOLTIP, "Risk, % ($)"); } + + ObjectCreate(ChartID(), ObjectPrefix + "EntryLabel", OBJ_LABEL, 0, 0, 0); + if ((sets.ShowLines) && (sets.EntryType == Pending)) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_COLOR, clrNONE); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_SELECTABLE, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_HIDDEN, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_BACK, DrawTextAsBackground); + ObjectSetString(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TOOLTIP, "Entry Distance, points"); } if (ObjectFind(ChartID(), ObjectPrefix + "TakeProfitLine") == -1) @@ -4952,19 +5227,16 @@ void Initialization() } if (ShowLineLabels) { - if (ObjectFind(ChartID(), ObjectPrefix + "TakeProfitLabel") == -1) - { - ObjectCreate(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJ_LABEL, 0, 0, 0); - if ((sets.TakeProfitLevel > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); - else ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_COLOR, clrNONE); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_SELECTABLE, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_HIDDEN, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TOOLTIP, "TP Distance, points"); - } - if ((ShowAdditionalTPLabel) && (ObjectFind(0, ObjectPrefix + "TPAdditionalLabel") == -1)) + ObjectCreate(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJ_LABEL, 0, 0, 0); + if ((sets.TakeProfitLevel > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_COLOR, clrNONE); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_SELECTABLE, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_HIDDEN, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_BACK, DrawTextAsBackground); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TOOLTIP, "TP Distance, points"); + if (ShowAdditionalTPLabel) { ObjectCreate(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJ_LABEL, 0, 0, 0); if ((sets.TakeProfitLevel > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -5009,19 +5281,16 @@ void Initialization() } if (ShowLineLabels) { - if (ObjectFind(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i)) == -1) - { - ObjectCreate(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJ_LABEL, 0, 0, 0); - if ((sets.TP[i] > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); - else ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_COLOR, clrNONE); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_SELECTABLE, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_HIDDEN, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_CORNER, CORNER_LEFT_UPPER); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TOOLTIP, "TP #" + IntegerToString(i + 1) + " Distance, points"); - } - if ((ShowAdditionalTPLabel) && (ObjectFind(0, ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i)) == -1)) + ObjectCreate(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJ_LABEL, 0, 0, 0); + if ((sets.TP[i] > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_COLOR, clrNONE); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_SELECTABLE, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_HIDDEN, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_CORNER, CORNER_LEFT_UPPER); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_BACK, DrawTextAsBackground); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TOOLTIP, "TP #" + IntegerToString(i + 1) + " Distance, points"); + if (ShowAdditionalTPLabel) { ObjectCreate(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJ_LABEL, 0, 0, 0); if ((sets.TP[i] > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -5234,6 +5503,12 @@ void RecalculatePositionSize() if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); else ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); } + if (sets.EntryType == Pending) + { + DrawLineLabel(ObjectPrefix + "EntryLabel", IntegerToString((int)MathRound((MathAbs(tEntryLevel - AskBid) / _Point))), tEntryLevel, entry_label_font_color); + if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + } if (tTakeProfitLevel > 0) { DrawLineLabel(ObjectPrefix + "TakeProfitLabel", IntegerToString((int)MathRound((MathAbs(tTakeProfitLevel - tEntryLevel) / _Point))), tTakeProfitLevel, tp_label_font_color); @@ -5830,12 +6105,9 @@ double BrokerizePositionSize(const double position_size) return position_size; } -//+------------------------------------------------------------------+ -//| Calculates risk size and position size. Sets object values. | -//| Trading tab mode lets calculate quickly calculate percentage | -//| risk based on sets.AllSymbols to use when executing a trade. | -//+------------------------------------------------------------------+ -void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) +// Calculates risk size and position size. Sets object values. +// Trading tab mode lets calculate quickly calculate percentage risk either as total or for a given symbol to use when executing a trade. +void CalculatePortfolioRisk(const CALCULATE_RISK_FOR_TRADING_TAB calculate_risk_for_trading_tab = CALCULATE_RISK_FOR_TRADING_TAB_NO) { PortfolioLossMoney = 0; double PortfolioRewardMoney = 0; @@ -5853,7 +6125,7 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) { if ((OrderSymbol() != Symbol()) && (sets.IgnoreOtherSymbols)) continue; } - else if ((OrderSymbol() != Symbol()) && (!sets.AllSymbols)) continue; + else if ((OrderSymbol() != Symbol()) && (calculate_risk_for_trading_tab == CALCULATE_RISK_FOR_TRADING_TAB_PER_SYMBOL)) continue; // Buy if ((OrderType() == ORDER_TYPE_BUY) || (((OrderType() == ORDER_TYPE_BUY_LIMIT) || (OrderType() == ORDER_TYPE_BUY_STOP)) && ((sets.CountPendingOrders) || (calculate_risk_for_trading_tab)))) @@ -6505,7 +6777,7 @@ int CountDecimalPlaces(double number) //+------------------------------------------------------------------+ //| Draws a label for a line with a geiven text. | //+------------------------------------------------------------------+ -void DrawLineLabel(const string label, const string text, const double price, const color col, bool above = false) +void DrawLineLabel(const string label, const string text, const double price, const color col, bool above = false, int font_size_modifier = 0) { // Data not loaded yet. if (Bars <= 0) return; @@ -6514,12 +6786,12 @@ void DrawLineLabel(const string label, const string text, const double price, co long real_x; uint w, h; - ObjectSetText(label, text, font_size, font_face, col); + ObjectSetText(label, text, font_size + font_size_modifier, font_face, col); real_x = ChartGetInteger(0, CHART_WIDTH_IN_PIXELS) - 2; // Needed only for y, x is derived from the chart width. ChartTimePriceToXY(0, 0, Time[0], price, x, y); // Get the width of the text based on font and its size. Negative because OS-dependent, *10 because set in 1/10 of pt. - TextSetFont(font_face, font_size * -10); + TextSetFont(font_face, (font_size + font_size_modifier) * -10); TextGetSize(text, w, h); ObjectSetInteger(0, label, OBJPROP_XDISTANCE, real_x - w); if (above) y -= int(h + 1); @@ -6548,11 +6820,11 @@ void CalculateSymbolLeverage() else tickValue = SymbolInfoDouble(Symbol(), SYMBOL_TRADE_TICK_VALUE); if ((TickSize == 0) || (tickValue == 0)) return; - double lotValue = SymbolInfoDouble(Symbol(), SYMBOL_ASK) / TickSize * tickValue; + double lotValue = SymbolInfoDouble(Symbol(), SYMBOL_ASK) / TickSize * tickValue; if (PreHedgingPositionMargin == 0) return; double margin = PreHedgingPositionMargin; if ((OriginalPreHedgingPositionMargin > 0) && (CustomLeverage > 0)) margin = OriginalPreHedgingPositionMargin; // Recalculate margin using the original leverage, not the custom leverage. - SymbolLeverage = lotValue / margin * OutputPositionSize; + SymbolLeverage = lotValue / margin * OutputPositionSize; if ((SymbolLeverage - MathRound(SymbolLeverage)) / SymbolLeverage < 0.01) SymbolLeverageDecimals = 0; // Avoid resiudual decimal places when they are too small. else SymbolLeverageDecimals = CountDecimalPlaces(SymbolLeverage); @@ -6635,9 +6907,13 @@ void DissectHotKeyCombination(const string hotkey, bool &shift_required, bool &c void WarnAboutZeroUnitCost() { - static bool was_alert = false; - if (!was_alert) Alert("Misconfigured symbol on trading server - zero unit cost."); - was_alert = true; + if (WarnedAboutZeroUnitCost == 1) // Issue the actual alert only after the first dry run, to avoid sending an alert when symbol data is still loading. + { + if (WarnedAboutZeroUnitCost != 2) Alert("Misconfigured symbol on trading server - zero unit cost."); + WarnedAboutZeroUnitCost = 2; + return; + } + if (WarnedAboutZeroUnitCost != 2) WarnedAboutZeroUnitCost = 1; } double CalculateCommission() diff --git a/MQL5/Experts/Position Sizer/Defines.mqh b/MQL5/Experts/Position Sizer/Defines.mqh index 65a0615..3f4c2f9 100644 --- a/MQL5/Experts/Position Sizer/Defines.mqh +++ b/MQL5/Experts/Position Sizer/Defines.mqh @@ -9,11 +9,19 @@ #include #include -#define CONTROLS_EDIT_COLOR_ENABLE C'255,255,255' -#define CONTROLS_EDIT_COLOR_DISABLE C'221,221,211' +color CONTROLS_EDIT_COLOR_ENABLE = C'255,255,255'; +color CONTROLS_EDIT_COLOR_DISABLE = C'221,221,211'; -#define CONTROLS_BUTTON_COLOR_ENABLE C'200,200,200' -#define CONTROLS_BUTTON_COLOR_DISABLE C'224,224,224' +color CONTROLS_BUTTON_COLOR_ENABLE = C'200,200,200'; +color CONTROLS_BUTTON_COLOR_DISABLE = C'224,224,224'; + +color DARKMODE_BG_DARK_COLOR = 0x444444; +color DARKMODE_CONTROL_BRODER_COLOR = 0x888888; +color DARKMODE_MAIN_AREA_BORDER_COLOR = 0x333333; +color DARKMODE_MAIN_AREA_BG_COLOR = 0x666666; +color DARKMODE_EDIT_BG_COLOR = 0xAAAAAA; +color DARKMODE_BUTTON_BG_COLOR = 0xA19999; +color DARKMODE_TEXT_COLOR = 0x000000;; enum ENTRY_TYPE { @@ -83,6 +91,13 @@ enum COMMISSION_TYPE COMMISSION_PERCENT, // Percentage }; +enum CALCULATE_RISK_FOR_TRADING_TAB +{ + CALCULATE_RISK_FOR_TRADING_TAB_NO, // Normal calculation + CALCULATE_RISK_FOR_TRADING_TAB_TOTAL, // For Trading tab - total + CALCULATE_RISK_FOR_TRADING_TAB_PER_SYMBOL // For Trading tab - per symbol +}; + struct Settings { ENTRY_TYPE EntryType; @@ -118,7 +133,6 @@ struct Settings int MaxSpread; int MaxEntrySLDistance; int MinEntrySLDistance; - double MaxPositionSize; // For SL/TP distance modes: int StopLoss; int TakeProfit; @@ -134,8 +148,13 @@ struct Settings int TrailingStopPoints; int BreakEvenPoints; int MaxNumberOfTrades; - bool AllSymbols; double MaxTotalRisk; + int MaxNumberOfTradesTotal; + int MaxNumberOfTradesPerSymbol; + double MaxPositionSizeTotal; + double MaxPositionSizePerSymbol; + double MaxRiskTotal; + double MaxRiskPerSymbol; // For ATR: int ATRPeriod; double ATRMultiplierSL; diff --git a/MQL5/Experts/Position Sizer/EF-Icon-64x64px.ico b/MQL5/Experts/Position Sizer/EF-Icon-64x64px.ico new file mode 100644 index 0000000000000000000000000000000000000000..30c9d729d1b7cafcb9c1b272402220fd54da61d1 GIT binary patch literal 2686 zcmZQzU<5)32LT|-!jQqmz#zuJz@P!d4nW)h#2|58pstI9;pjzwT+*ZB!zBa+u>-jG zuuBV$%0okd*5LyWXfOkA8>%pzH!2Se0eFa@GDr^}xDHeX+*nj$IB!%Q8UpYTL1j=a ieBcIw8E{Kbh2gwWd1wg0Lj;vU>+nIfZIm}`LjVArAv>u6 literal 0 HcmV?d00001 diff --git a/MQL5/Experts/Position Sizer/Position Sizer Trading.mqh b/MQL5/Experts/Position Sizer/Position Sizer Trading.mqh index 8922a63a132fa2a7b7a4bb868f83dc388e322965..4c53ff33fdd0071d17c9ba45e02283143030b575 100644 GIT binary patch literal 98358 zcmeI5`*K`IlArtUjqp1_-0%!EvM9}L#M-;EXU(gIE0UlINZi@+27(ueqQu)0pd_v| z59F7$onIw>$f`PZZjEjLlsXVVqr1;Jm6etE%*y(I|M!!{CyS33A76lgT)*Bf6x9tTs*N)UM`+4E-zjz{(bR{ zeg5-`;kjmGzh1nv(Vp2j-xxGoi~nQ4e^`8Kzkj#*FZTZpgXE3Danr7SWAOcG@I1Ev zU#tP1z%j5K8El7(e@yuQVZqO38{eV%x&zH81w0ptexRYhO>6mh@qF>t*7d+({qHBM zd|)%wiXWV;_8-$)ckjEDXyi?rKTkTe)nNTzpU{%%zU;RudZEGT3v9 z-&%ZaczS6w6MtN`Yu51-9CeZK^S!O^GozD`1P6=l#fNDY%PA5z5A@V z4l2++hY8y*TecR+fEV_2VE8^t-1W|`{2%sv$$tDP`Q6WKZMF=W4{R)?)r+)(4~?>K z*%RPPUXSd%r|J7`yY9x~{^E{(es^(YaeJ|EpWL_quG{DP>66=woy7xtcirabvlOi5 zZ1w3C8;!A#3=V(RU6Y@;?OA&^%8re*Z{yvt&vxyz&rinr+`fy^f#-93f8Flkx~ujC zhoQusMn(D^8C@a`%PanR!f7o`Jvf$Gj&b1JGVBS%AKE+kfwg{RKU+ri&+YZlM%%Ji z^uZ7I7cKGB{{P;dh7>_kI}YWmkiabFot z-ClfY|1XP+90yN~0^TkjCCZ0Z?k)bZ__w5?`G426H=6MvefpWr-)ZWOaVH%5*yw31 z(bSRsy?k>2mfiI-NgC)azAK-H9q=e&o$H?)Jw7z6fhR)Kq1E{0$RL4oU)VK#>#*`U z)a^8z&+CdojqHDCSVfz;6$D@3OS8-2dbs$`uDO@E;cL4Rc<&lqFAO^5L5=63XU7bg z-7=%(vk-;OdCu12k2dn}C($W$2Agvv-W{X8+leyaWn?Wl-CulVGz(oKA@_}P{$zA| z|M-7C6@N<$fFEQN+Tpp~{VK^HG)9TTOSZa~I%^<)7KT{a;b+0YTZ@0NA7tat$@ZRd zmt*tO#QCKb5e#h^sc)CjD(H}FhR^#6gJ|O}e!*!?nHp2C{klb0xQ@{~y}BKYK6dJW zBYoXIHTmoBz~&sf^!q+CDZdOBT{1m0+2nBKBO|l;rqrIAi(YGa*7vNSzM-d{eeCETFqkQ(2BzIpKue~+v3aR&F;*0VsWIuM>M@jeHN|Hhr z82q+t-0KqLsnLq4 zk8M=!{3FwuZQJpRaTomcrSTcObtlQH&+U4*@ph6G$#Z>-Y1i*3Zr!tI-LjeQ+p})i z)3F`V>eFn{F5OJQL`&j}5{ISJG8&+q7ua)rVe>NM8-`o{Vt2QBvg95?>bAvQTRrsr zTcaBMwAc2E=7)a|lkR?-=mefXIz7$4$HQ~m_V*^QKVAH1yYH2KhJ73QrL=H0x=WZ( zn-Zo=i?BUHsX&^s3<=xwLDXgk^@W+=rQvL-p*2 z=D&<)zvxtyV=E|g+iX&|@B=@*$5M4FxMZ);@l?7+2mOn!GWPYIYL!~!%CG8Dq2L&@ zn8n)E|;rVF+{AfRu1haWV=hCp!gUwu3^22vk*COp3ZF@VNtK*t9f$)R{@2uc)-%a z?=O)PZ^bg zHZ(p=dmG-KBd1C~n#kH1emA`Bx_3F=2H%(LcStvvyzO4$X?c5mUC)QNb4}=)C69gX zn9V7B60ahnY{BK>eb=&V=t=iXkH0b7AS~Q?VoBj`57u?9M}R$s=#im1f}g{TW-dLi z(93R(KTcMQKk3tC;k{099%gXvn+4-nV`C5z%cB|bM9*klq=>|yOmbhhScD=H5zluI zSJC{J$=dKZJhAz$5v$Bsb}V+NCl8OS zt7L$sAS2_ zT?ke&&o;beT(Jvn?$0uNkJ9C`q~!^7Wj{9)nQn8k)<&<+{o~h{o|Eowe+u1!Z*e3m zwq?IinA6bHB#od|XbV4z*w#zCj|gqVJegxz1q4@nH4wEwM0=6E2X?Q=A3_3?!)wX1 zVZKt_?!cZ&3hRu;{3c=%xOJAcU_sy>KJ8$J$q;-&d@%KAMnJU_1R2nYB4 zkmmN=t_Azt?RVwc;j(@6 zWm*^XCC~KP>iJHCWJh@lvXqz&vJ|+$LwpXkLIY2F)H9{2vd|Jx{hk*(bB+@gJBG2tVq*UBPg!qZYiVh9RN5|u0 zX^^#`5{KGHzk16?`O%&Nra~G3aa%suRKE@l)zS+t`N6lJPwN$;l2kB_i#Bi}Sm z^z0FQxohtfiTW3Nf6cB|U1}GeSj}+?3aFu^vDjD*b)C2B!&!Sq;5O=XhvqSdDm9~Z zM9D?j!MXiDrO#*1T6hdB?iio-y=0N(zVEVJ-F;GDL{2z(zq$L~v9`-~3ROEpeBQs- zqPd{qUmx#}V|4vepi9MCnRQ5mQuF5;Uh<*l<@?F5|ITE$qMN~G`TcF)x@Pvk^W+UZ zPre0p%dgB1Ju)AHDiQX5X@qUl5y)3Gh3{gZGWWh|kzK33**E=yWfeNcqrzUBb2WV~ z?bjDIFRRC?1Uxir<+ElCN%-i(tGxRigB>4-c$P;XubaM&{OU3mhG25v!hPcsTdmRI z+#U02v@1Xu4G593Wc@w5AG-v8XP>nyyd*L8Dr^LNEh|pr2CcMlpr^KJM&Ii7Vp?6f z-9W^b3PQ5!w~p;E(QU|A*>$su1B z%5f=C!#_ouX~l_Xw)Yt63cZ%{Z1_{ftaGWQJBBIoVp1UT?`E>G$&C2U21!76D~;3S zlrx-e2r1Nt-AZmu(@>aGb-&tPz3310|v*55-uG`=5 z&8HxT;{7a$S>r#D6JeKT9Sf%#A0Ozo{XDeX>VesN z?uPM%KQIUL+Bx=xJ$Wxx&L|gp%V^?d!o)$MkT=IwL|q89PVK1OyiDpib{y~HeGP6| zH4uAsd5H?$skz=@wjviDM z9s9+e)P1W6d7C1iUQ>)L8@q!TfY+J$JtaJnPPrw*ZtuME1lv9;(IN|fm~@$XBt)#C zdw*SNNKI&tgSN!!MzMF2J@vBa1F=1d0ms=KTuF}0Hqh%bG7t&D4)W{AI+3`#c6;wz zd>y~G&%Am!I^?(x zqIO)mfr>XW8@?Z1bza!YUhVX;ed9hw_&ZdO@^nTlE58EbD+U$25vh1RGK$30iW%fq zk5}g+E2ctBZ5s9P{%o%zrW!7w-ZC14?p#{Q2l0y4Ez__QhfioL;3doBMUm-?mEIL&{)YPOK~wR8Fst%N-*`eVPpBr^Jm z9&9DOXij={EZk1qg8mr7Ls-Br1&}T+F36$4r=f4(-Xu6gVMuw=*bqcRD$|h2Wb)JNpyVs|RQyyV&lnBKraDhL77Xt@6>A>C zdZ)i7rStfIDlnI#;>TIc$4`u)Q3>F&-~$oZwu9-wapvzq2T3~K|) zAn$O|wo|5!CX0P|yk$HwI@$cQ`CH(bIDzN!${mjCpgG?Y>BI7T&qEZdSJ7hM2yQ>r zT~c(nUWe&jSFIbbP^b6CB{N3%M|!Ezvy?8ceg3DQ)9ZM3gsyCB)UI!*>xJvEC%v|| z5BEfnefM$Xf?Bd~82hEAUwR#IXg3mq$CmH>$vb2E{&nq+3J6?=@5G`gWZXiCS^%%zWx=FDrk zTD(}7pNZ0kozIh(T^#-z`M|DXw>de4zU#M>jS6=9 zWE0;7-W5yJo`;B3me;lR492zio^6>mChzejiK-K$k7({^gAvAY&DU@9dnEJAgaP(y z=uChatmiygy^Um}O`VqS;-{8H9c8C_;8Wpry6NkFCVc9Z{zT+Y;g0ccSZ&{4&x(kY zXl8o?Z;NV(W4q@ss>x+86%KDK4@-9P&~o_nBuAe_6wL1%^)0g#yr#aq zpYeLAFJH%DEz+i__NOh4?$Y;jqXw@Xb4>wtytNECr|8is>al4E&aFWTlUb^>;(dMX zxmq>GeSK2;Ww#`+%Zxda953lx>t(RqnH=K2IT8b1;~nd|5em(%22MJB@;k>?PnEJ{wU)xA| z9GxoWJmWtG$y9s;=Wu1r9HU}bAnFNv1>em5$fP+H{B*XfN5Dc3 zNXE3!v@u#1590)FXq+kY**?C{cQBXT895`xpX#TH#oSxf1GzWgmOl80gW4H(Wvi5J zD)U8A*Kt;Pt2}Gw`6^YG2n%jGt`-a3YKP_V(0vwbqFIdNG48K%;rJ*iO!5ytpg);E z|KSNQ_!%g&`}3}X=p;YEk4}N)>2KTL=tFjBRHvR~-f2-!eP(iQth*rfS=^0Q+cs$W zr59GiYO+Kc}+fkeyb~2Bs>wicV>)Q3KNpxTQCcVjNtg=flo7PdSs;af8Rjwh&ppkK^_p68yVFiay9IxBjTKrQQp?hz{ zt+vwHqTbcJrE}(wBJ0GX2Gj}HqqW9~Yka=X6L!!Aym$EgFLA&66x}gTQ|mmB_NT-> z>SzN|26Fqv8qjo9!fW?TSSX5v#2&4jrtTZgpbO6W;{PM_pM2jUyFa_9P!k{16X(Qw zg%vXELC4eTyYbD&V-_0Wyrr0UHz==V-_{X5w=4ZDy=7=2*1OyvNHvbuYksd4c2iul zXeRp(^^|csiuHwB;Hlv=M747Dt27P1r|&?Wb53etM38UUdF>tx{Pq~C`54J}L*}@} z>LY46C#!Y7*j;Ad!YVnj&8Ow3GL1ut+Xu)hk3kKd3+rAQ+<>iSK>cOusnOVn>+y4pZz#T#*qif zBJyZlaQy0at_hm<3hG0-w?kN${LfFg0Sp&DI(PW#d&6f0t>(ecwgd9O2=4G_KFC=+;xY#n>0A9kzH@ zEgLsgo9tG-m~wOVHGsJ;og-=RYv=m6Q62v4se51jiY+f?rmyduNZxv6>Qp~;Q^iTQ ziswnMZK^o?H14K~b83x>SM+SEICsrD=LAlATh(=Rn<~zih8?ev+Ej580e#mSLv;MO zhvruPT&t<3zW1eyv!%g3X8oY5eep8_y;h%7K=Gc`pHtm9^9r=v7Sp(A-1)WH=|nl$ zqxw9{j2{};Mqg2NSt1gwd_}t=k*p_G(VPJa1irHS_Sx4a1<9KX6LOoso804kpDwm8PD zA(=Ca{t73@{n&i2oJg}i3pw=EaIDdxZpn77qH}#N!^^6B?}r^{zxwW_*9IYd5|J~p z|E?{kHIm|PXW2(Os64W|b)8a~ktQx1dkB~5Lp@ya_|v3HM_(1_#H&$1Njem{j_!PA zwW+Qr(SN>YE^_K*kVCHxuZh+s?#N|?w1uwfd(H0-4jQ|=tPZH3EozAsyl(RXBg6IW zL$p2(_aVu~W+0gJ`A@%l74vV^Car@0rmtcP2h;C%91N|Q=zt1-QT4vj0Q*k*_6T&Z zoV#COdOZU2LKW>T80XgLkB_W66Dk?K4!%2I*?Q+)6F;=FF5|9cd%m(Ex0T|`Ir z;}t4fR=>iEdj$(N`zL0>L^ozWaXIMw#$F_9;j{WG_B*+(ByYewKa+gyZ17DL|9G{< zH2Ert;VUz=D`8W`FI?5Hs!tl?FWs}ARq3~JKbvIX2)h2~`0AsBCB?Ae)?dXx1*g(V zWrcrjt)F$Bf7B}y!OFD)R!RLCI+V{gRq~I`vf$Js^%2=r$%{MtUhi06@;rve-UH-0 z`w+GaoAGX*G}yCy=@f!C&Y!tmJag)9ctJ02rAnave8!5s6Tbd#UHWOXpDzAe+BqT5 zaQWx_!%Ch5R8x1d2n+M{fbLqRf->LPLceUHoZ8t^cl=Ow|1uT$oUXKIeM|4#^Y=}T z?bvRK8%BR#?J&O6pn=iz<1*l+B8 z=M)mzOxT-b1KB(8(aLF&#~K^I^yqLzm)V~K7v)hbMUv|H*4gNKQDmMCSWQNkD4A0m zXUNfO<}h{r@iTjL9;M>jd7S4k`6#|`n^?D~&pWme4R@L&lEa=d{6qMmuMd#ut?zX? zD@jl5=3VIyG>vx{8$oD-@ z802f8Ck#ZE*FzWith&_~`M0V?pa;h9Qx`%a)za0cb)2?M)e*>sCEBG&f~zu3K*G(sPld8hf1+Kdqnj)2#SreYbS%2WGuS zmoBf7Vwcg5Np<+)P1@6-Xa#&LF5&;6RNhI#Ny>oDxfVkW=jmptr=7hAtdW$0h_p0D&suBCIb6wK^z03Rl?_DPI z{g{lHCIi;T<87)dKZSq%rxnl0KMToA?@6fck!jn5lbEn)ns-gMLeEd^3cMEYaYH9X zeNGp`d2`Nd1fZumCysJ2y_qiAU7X){kl;8nZsEN3@6)a>kM_`MH$IiEpJMhWw~!lt@0z|bU%p`O`b;?bA6wG9&*C10_f5yIV^#)HdA)NShca+4NySI`7zsh zbnjMmtj}kK2c zCTXs_|CD4c@&+4W*TzNC(8Gpoo=e1QiK~GL3&XQ_c$j~G+zqb(x;_oqhG`hK>oz|4 zDq+;@`$p0;hey;^vE!j@Z9z#Twgl1V2HBD22f)sO$!hm51Q}8!qUm*h&g1LSCW52y zb(tJSd&F)Qub#1B%4w+&E>Y75h5`9hrS!dQn!fDJ>XA?Gd}lOOk6!y-W9uu(rmeHC zMk^u5STVY#zp?*WXJ66VNn0IRCPd#t`=1q3R!{1CU1r7d{O+BUb-iULv;289#~WFx zk{0oM*@Y0@HDbQ%K<8T8`@h9}q3~9h!|wfa_DBm?%V;}hv94~1%XQMjZsSbJd-nH= z{k>=JZyC*S{`D}el$N%zqSq-glxftyJ}N&gb-UKSVYLNhtM3}$(Yf9;k6j6Mv8j4} z)ZC_%_NPNsGfXY3r;>G2$G+*}TPD@$opj%11`}s47H}MJkLgj0Q&$MN$a=nT*wP>^u1xYsvU zEmhL0aIdjH=va(%MsHcIZJLX5S8WR}v$nbI*V2x)HNR`rSJ&g+N;E4^y~_4 z$Ck9wcViSlh0XS2c`qj9;9UP@7&5^xX%zPNs{EDH(&{hKPgy<1Y8~5>Pv44y&&nSu zq49UQ{0xaa4A1Z|CQ;*x5+k896PL^ zuo8TKwp$NaL7yB)30|Ad8AH_+GetRGxWgPl;XL;DNd;Ss&g>8N0>p zFRu1@VMJL1GHfM0d}2_1>bBVn`_H8YaZinfMdaN=$Pc;=1Z>Z2My=C9wbSOS3~SqV zZ5|u{O@Y&Wi5x<5QL ze+pZg+ypbhcOe>y#NA5YeV=fE)L*Wp&8CRwl0;r$d7@-t)ULdK~Zu?`^{+M^CpX)Yne8G3a} z^%Dh3Ivu)8606HUL-SJBj9HE6)cQ`0n}f-@BkI&X$7Zg_B^Y({>X=t6IU~%!rBJ1}DNjrX*Gytb1x@M%h<4KaP>dofXAzC0h zI!u$2QM4;DjvWorG}U7I@= zH$7YHf$m|>r8S<1wUl(zvNP>!_bxVc4IN#-G^)k+7}D!)SW4~Q9VOTCQ+4_`N$!!C zpNF-sZg0apPAS4o*kj$9=^8&>@b829W9;~Woq`s!y9BbFw!OL`|M^CW3FpXLEUFLs~B}%^Ew}{5(UP( zEzehEy2!P9f3f!J^vTokF(i3Qoj=ds3jNr!RmQZ4+gShGG<@ELQQ=vN>XGNHJ!QoMB1+ooT2r5z{ztQb{LJ+B{INr~Ppr|Y z*tla>68oudnYO=e_Mfow;Y6%oTC`TEJHyg$BM(D#(>+4Zkz7rl9$7DTx?*;%y=~q* zr@RTvr&&=!7WB6)F7ld^mcuxW0F-&uR~-sE=WPO#a-V$f10yWva7XGZLXC zo*DBP+L`E(5=Hf$KSbK0oRX%>TvK@uQZV*shIi;ue&ngDQ;CnWcSjNONA{kvs6cfq zU%QK||}oEk`ujdMI=1@d~n8nW&Pf~@3K)m_oupXa+T0j)82qVv2G`-gMA zQx_Q*;<0y)l6}9e@(*}!WM6lT8=bb%i0brtnlYTmIh~soZ9V&rd0Rx7+EDwqd9I`d zE70aVUI-l6U1fmvN* z1hw206$lSGt?RosP3l|G&vufO>_?UK^wpV%75SO@DtO#LQjvK)O?Z)9X|D!rm&>j0 zdaSwzNf@bL14EH7?n0v+Bw6D!>+g6RpHDmixqyAsKZ-J)rNvW2KD_d}`ia3CH4F4$ zaJfWh9j_ljNB)P=Uhczf8>NP&!0eE%{a3W8pvyy7jRWZR;5{@#>-Je4;2MhZJwd;- z`}Q-9&+}{Fw=G453%zR19UJKO_Ntci?XDO1;|I0)Qe)|L+G^=)K{$M_PuUqJ*Ab5U z+o_^qxw+A&gSkzco#58%Dzs9*Q?k@Y;t!;=zYfXk`r7*aGMIBL z)Lm7iwbil4-{*YY;@Y_DlJNz2?TZ{zQB$6GPjzJ6|F?40lrEWDEv>H=uSpo>zu7i_Lhdx?8aAY`rN1p>OOaP6@hRF zz9GB1mN{jdV&1osb@@J_i)2YD|39q9rfKIV7s!^nVzT!O)6Pye=Wk14G2S+4==QRl z^mLwMM#H{C&KLMK#N)lo3z0@VIp2NiRyJPp@Y;*sr_q3}-dJdNlYGXjrRQF4p^5J{ zHX6|tVd1=OG_6W#n~jyWvC?Eo_1T`&Et!p#Rz}p$+e#}fyYgKgwIDb1+lRo$E*JbX6U0Bp59i>Pg>w%B*u~k>{ zx?{8bXM5hC%t9kW1vE}!!kS)*HnuZ4Etu%R@q2p`xKqz`^&4a_UpZ%u(Vn}$J+wK* z-YAXw(q>0yyo-ms$KPyQ4yA>IXG>y2@Myhr`EoNwN7=np!{^wJp8iCYs9k<$xk~AN zDDRTthPe8-%}MBFnBC((Cv;Hp&Ir&2`|MdO-;GKvnXL3tx+bUWv7PqZLpP>6 zgQjfWhbC=eO^Df)aV0#E_`cjH*1}JIHI*XBkDZLNhj4~Z(Wcybz2kFB7FVOkJ8LG#eo z4<ve($9p}UQl-H%vtDNW@9j&~QAD-l@I_fzr4YX>aXwDOm`kcF6X zFVYxv65caCuQI_Irr({MxyQ(qDCpwbhlrEhjg%ew$jq zO|4(vu?1UcIA2%#PpypIs%!mnDJ;pXSNE3KrHN+i*3c9Ec#$ft*%P78O0KECO!r)C zT;X0J@l)!i*pG!*t{t~{WN1j&rFdfa@^~}Ud=7horRU^bUcf)yM2Y;d8@e2eSPn99 z2n(Tkmz`5?BZrO9!j1RY@k$uQB*(L|ZTYKJ)T?}7d|kTQJU7gE4BI{5=Z1^E6(v61 z?Sw=38>(d0?OP-Dy_W0K9*Y&}_EvA~FYHsW@7UP3z2w6)fmUkBMY)2f zesy1Ch^_;Z7pa0sT_1-apC+wJSplz-TlpqY$zk$jJtqXWjzzF;8!G zmDnwe%#91K9uwo7w2BCz>u=xJhbD(FhckB}HJo;GOr5@p9gTiH>5(6j9#OR2&lx8> zbDG@`vA4+Mr+w59X6xDId4(O5On&;ulVeyF?|y0c^9)iQ=iajTH@4ZZr6qY))1>c? zgeUXbX{=g&(ChZA{T1b|iB@$rvn%}v?TMJK^+QTtHQj+;@tABMMsrK8bw^N9c_q>* zzVm(K%ki2j`*^PRTkpE2n=j{ywQL3dx+8z8 z+vntE0vbOZo?XwSZ5dhncmmJW9$P&>w=JPdECTvYe4Mx(??Qe7T>pd3=gmY4ou+L> z&yMj2_H^u8Fs)N+=o`$Zo`aEB;`8>(4l>4Mn#dIm=|7F7SJCKc_OH}Z030tzfA7a$ z7N`7Q_f8gH^YV0H)hlfFu{dqG52c#DT>p3!BC@1?d9(bURy=02kHx#iIKGiP!uBt( zLUOZDguP7c8lYnsI|qjJ+%(NwTaXvW&-2r&u!V_l{hIweFmdtyyzP!J)Xr*o?Z}v1 zmmNM9v7h!F)eU+q_hNgGLp&{;wdC3>#v$JsjjYS>)Bdex{64|v8F#mty1q{C&9&|b z+dseZ{i3*w=}i*Zai1={&9m?$zcFv^Y4VJ{cG_#G>Fq$LmJcWTaMN_0xMt&BUTp7D zb`3ofh^%b<%gr9V?vB|_r-TE`XVs^jEEjER=UDI}>zZM4^8>)^oSo;YNkOuM96bSAILi-FdH_MZ-97AHB3wylMeFm3!4{9`4rvl{6CB zoN|SI73#Vg#ktGg=E@E6O2pmw>vT^~%DZfPw-dUMVvYNbth&>F`+B;Z)3eX}^|8B- zo_(C(c-Q{&G^Yf5Q?fS`ilSl%3MCr==D<5UxS&Y7Q#yr{n}Kr6*nf$4@unzJyR~?3 z;LP9A8zR={bSJwD^KkFL@pAX*YuuH3seD)O<+^J;m!D9)WnGX$TKZ{?+JC8RI6kNI@?*m<`>^3| za+SVnULgiI`+2}z!w#>ga6~Rh@^ccM?{jq@60OFQxCTi<)#2CngH}V5cz!dq13Sxh z>^t;kd5(DfBtM;!=ef)YZOQKOgY0v^GIXXeypc!3MEx548Wo!D4#na#VtHd6ypcy` zCCIAeQERnsB;Mk@ggyI(17sUeRm-WK&Nr-@s<30N`|m~yQ;R^24_&3H?eQn%)=*7P zdhhlG{*rci6Wwxa0)6TAIYij8PpN-=cPu%cB#Bf?-mgtgP??HF>GB7;QChU^v$h0} zUi(V*G`Eoc@y$GvX&)DtphlVXAc#SWY$uA7AZ<0la^bNU*jE+^1^!KWc*Y-{B zqe!MhMJ?$MeU+NRCA-#%(>+;tJXq0-n)>?_-LtFP9e_MaS<)_2prna>Zh1Yns>I6}QQkM;S{m8+WlilH08YByqWJXF zWNYjhrtwenQv`|Jcx`zfrfYi0p+wHqCm$}~GbC~Vz`Q&><*LlbUUV_pHOc;Gv-fW# z{5eFi_W){oXL{nG!!unRtqvx-s&O98{U%JYA7XsnRtM9A)VXZWqNuTQfhVllCx)wU z&J<5>SNZ8WIzI&HB7T3C7~=F%&WQm6WDs%D@$pM(vOH&%-FSc@*9~2{<&++>lsoD? z9MCID4xF!&#L{lcxYy%r;puQCaXDn;>th=$x8bCdL(kX!O1#c=ojgX@BKmjIne$5e zZ#S)+q^q9^#km@s9CgdM@w!R=dOahGcb>4)!>|w17T#-Ymwm(XJ4)Rud-v7ST6Nj( zVL^uhYpGcUTfPpb)v$4n0^H#mR)1?s(D=U`+SZINK8*`fz2-FF_RH$@V5yty9-^gP zeHQS{*MVmN)t{2JK-TtdlB)e0`7EGe%{XNfNe(CH@As4KchjuEecRoA?^xdVarZhY zE4LrC-<0l8bTOb#mEIh9QBO?^d-UT;M<4ZLbA5KkrPM98P5Ic*;f;~=XEq*PnYw4h z>v(UbHEfR}ncL1%*1X@%6VHq0Y2Q2cj^^Xu`SclaB2arSA#KlgR(Xta*?H+1?U~h2 zy<~K-Y?uA^2;v&~-eD`WI{^zKWI~@W8sCMt6CN1fhHT^A$BV!3aHU5~{4ep#kL;@R J|M_U~{{d>g-e~{; delta 6379 zcmeHLdrXws6~A|fHv`TH1M(U^hPNW1F0Qb+A_9T}B2d=tvaCE8mB%cDvY1tI(^T8I z202@9H8yIRR=bTB_uDv4ni%zuCN)Mev723LT1_@->MLM2>(*z_x!-)uFhbR4>t7q9 z`R3kp&+DG^JLlX}1AY&$_>5%x)!5i_*1_Im-ArM%tcNwS7Pf(P;ff-^9Jtbi6s`Cx z0oSVJcO!G)ih}>TCifMc6L1~|SMs9an!f^P?)$)Lzk`W3R>OKxik;0z4&8X(f#>Zg zvD?MJ6MpZ1DcHu|lxwH~B%HHY9H`A!DQgQ#>R_AkI{_|7$GEr~VQ+P)niBYs8*Hos zPMR$V3fqEAiL_H5bg*_j+T;4hRrp!(qXjlrhRQc1WslrzM)jUPNjwzRMpSUz9FwJ> z`U;-wmejq-chjW18gacJcYBc^xv`Zw;BsCvj9Rnd%<=#j{A-$87jn^nqAPK;7yoom zcOpYNKt89PR#c4sZ(*6ZMrK9UD69{ux>zdiXx}|3oc3$v88A@SCog zeA9||qToK!Q}~ctZckDG_AZ=s9a-3pM8u|7evxbSYxEE!ZO|gk2=>s~V2}5MYY|4Z zExdrIKes(%qMBO*DIQzt@}MFjIi?f8K0t*#Whjx-?)~epTGX+Kx>sIILYTQ2EusMF zXIXe}0Zj+15m}u)3NmlvfmwW= zh+fYZ?i&d(WU;w$JuN{Dw(}p0;n#Qp4BlSio6hF4EVw!MO*ots1nXA?K>kqZBFP6` z*on|VneJfesQQQar?52qn^EdF)msheEL}aCw9@Yx65pq!i0NY)$a8~?RYDPpU4k)% zHH(RjJXNG^BBMVEP!G)Wd1YpUfAcI8U(aj}Y?iU1us2|5S{P(!S)nPb-~|J$IT3a1 zM#R$dRm;ybW|Nj^BFHA2^w}G1DSmrLUY88`CQOAMFK!yDVemsnmJJH`WFWc~iiQQ~ z1k5{gtppFk>1vtin_yyBB$$>Ki9rXS1EawKFwz&QURYYqr=eZDcP-YV=LaCV2!ddO z6}$WAE?I;nhpvb)gKD3K_kB`MGvcBij&0IrOg6Egk%!H9W3pZ_ zS`o^qtPo?Z>||mLyv{;c5FB~i!fn7y!-ftAsefO&iZ8dZH7Jm7n<9Wrqnz_DS9!Qs z;@YFABihy4Z-Qm@R#_=u^ZcyJFc7I^QwKs-i~OiDU4g%;SYrv1cz>&`1Rk#nP;1M- zFN7GZh<8D^8Do1UT*62_PBNG(a%uv%q7paH((|1Fq&a0b1 z!yVX88DV7C5@_kOf@yaT_;tp@$nNz}y|?NGfg;i~d#3aRx#=*tKHrxLb{`oY?6oV- zaE_?oj^%bRGu1n>W@1a2k^in0#vk~=F>4x_BIhC|4%uT}Hkn|=W>iauJ~MEeSUZnf zd}ZSY%Z8VN{Z|Uu&V}dd{(YA3w1z=PK#XGa-F$U?csKXvoeSCBKFB{j*rU{w(FvZi zs?ilK7!A#n8Gva{JYjq|6Atb#0n<>DT429roMmIhmTOL0(qG^JoDyx@*M%cGCEQ%76lB5@t zq({OW4OWzRJGZS?ACIK*RBhg(^5`zlGaP`&BPMZpAveM`H3LG`CJgGy+_QxZKmQ!AV7tKfPiWdL3&+q0NG;=2+LCt z0nbrcp!rVsA(dIQLcKi}#c>>qfWhrJlATvz{b&^^mB!rXW`XL_Xhcs`Ssqfyw6VS zXZ6n5V*WpSHx8;o)70NyJsR4N+7RH%G%8hN@#fL|=*53sGRz_9DVXC(}J zTq!0Y=cLJ+d$qS9Dv7P6#8PPZFkF}nyabh?nYF~ThS;(Jl6-)g1c5ic>XigT#0<6D*QQR~mA6M6j+*&YC;_%hU==>yr z|J(=w;L(W zm#^ddv)s<3Gg^vQ;KvYt$g*B+k;0O`5u|7N6r z4F*9uD}Q-r3N-U~&g?|)!<~Br`5<+r)8F@5gQ1WW!=+=X;$a1^6zi7p4@CAX9yA=v z!(p(tG#Dp(Il~cI!p%gXEaOW=?QC8sPOsoekxh6tQ~)Ss$?r5JV1;rXDdMZS_#&1s z7D@t-rmulTo|UiyuZCtNDrW9jLn-p&CWBH&+5*C%r{(B(-iTr1S>#@NggG(7{>fqV zSPFTuS`=0AUQaI;h@coAWX{(eDPJ#ASc;gK&*Lc-^n-LWq*s;>(SMB>vH depOi8_(A9W_jrcy)AUY!V_d<-r#twb{{Xc 0) DoTrailingStop(); - if (sets.BreakEvenPoints > 0) DoBreakEven(); } void OnChartEvent(const int id, @@ -448,32 +545,42 @@ void OnChartEvent(const int id, const double &dparam, const string &sparam) { - // Mouse move while left mouse button is down. - if ((id == CHARTEVENT_MOUSE_MOVE) && (((uint)sparam & 1) == 1)) + if (id == CHARTEVENT_MOUSE_MOVE) { - if ((SLDistanceInPoints) || ((ShowATROptions) && (sets.ATRMultiplierSL > 0))) + Mouse_Last_X = (int)lparam; + Mouse_Last_Y = (int)dparam; + if (((uint)sparam & 1) == 1) // While left mouse button is down. { - double current_line_price = ObjectGetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, 0); - if (current_line_price != tStopLossLevel) StopLossLineIsBeingMoved = true; - else StopLossLineIsBeingMoved = false; - } - if ((TPDistanceInPoints) || ((ShowATROptions) && (sets.ATRMultiplierTP > 0))) - { - TakeProfitLineIsBeingMoved = false; - double current_line_price = ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, 0); - if (current_line_price != tTakeProfitLevel) TakeProfitLineIsBeingMoved = true; - // Additional take-profits. - else + if ((SLDistanceInPoints) || ((ShowATROptions) && (sets.ATRMultiplierSL > 0))) + { + double current_line_price = NormalizeDouble(ObjectGetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, 0), _Digits); + if (MathAbs(current_line_price - tStopLossLevel) > _Point / 2.0) // != for doubles. + { + StopLossLineIsBeingMoved = true; + } + else StopLossLineIsBeingMoved = false; + } + if ((TPDistanceInPoints) || ((ShowATROptions) && (sets.ATRMultiplierTP > 0))) { - for (int i = 1; i < sets.TakeProfitsNumber; i++) // Will fire only if sets.TakeProfitsNumber > 1. + ArrayInitialize(TakeProfitLineIsBeingMoved, false); + double current_line_price = NormalizeDouble(ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, 0), _Digits); + if (MathAbs(current_line_price - tTakeProfitLevel) > _Point / 2.0) // != for doubles. { - if (sets.TP[i] != 0) // With zero points TP, keep the TP lines at zero level - as with the main TP level. + TakeProfitLineIsBeingMoved[0] = true; + } + // Additional take-profits. + else + { + for (int i = 1; i < sets.TakeProfitsNumber; i++) // Will fire only if sets.TakeProfitsNumber > 1. { - current_line_price = ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, 0); - if (current_line_price != sets.TP[i]) + if (sets.TP[i] != 0) // With zero points TP, keep the TP lines at zero level - as with the main TP level. { - TakeProfitLineIsBeingMoved = true; - break; + current_line_price = NormalizeDouble(ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, 0), _Digits); + if (MathAbs(current_line_price - sets.TP[i]) > _Point / 2.0) // != for doubles. + { + TakeProfitLineIsBeingMoved[i] = true; + break; + } } } } @@ -481,6 +588,12 @@ void OnChartEvent(const int id, } } + if (id == CHARTEVENT_CLICK) // Avoid "sticking" of xxxLineIsBeingMoved variables. + { + StopLossLineIsBeingMoved = false; + ArrayInitialize(TakeProfitLineIsBeingMoved, false); + } + // Remember the panel's location to have the same location for minimized and maximized states. if ((id == CHARTEVENT_CUSTOM + ON_DRAG_END) && (lparam == -1)) { @@ -495,9 +608,9 @@ void OnChartEvent(const int id, //if (id == CHARTEVENT_CUSTOM + ON_END_EDIT) { // Additional take-profit field #N on Main tab. - if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "AdditionalTPEdits")) == ExtDialog.Name() + "AdditionalTPEdits") + if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "m_EdtAdditionalTPEdits")) == ExtDialog.Name() + "m_EdtAdditionalTPEdits") { - int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "AdditionalTPEdits"))) - 1; + int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "m_EdtAdditionalTPEdits"))) - 1; ExtDialog.UpdateAdditionalTPEdit(i); } // Take-profit field #N on Trading tab. @@ -516,15 +629,15 @@ void OnChartEvent(const int id, else if (id == CHARTEVENT_CUSTOM + ON_CLICK) { // Additional take-profit increase button #N on Main tab. - if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "AdditionalTPButtonsIncrease")) == ExtDialog.Name() + "AdditionalTPButtonsIncrease") + if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "m_BtnAdditionalTPButtonsIncrease")) == ExtDialog.Name() + "m_BtnAdditionalTPButtonsIncrease") { - int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "AdditionalTPButtonsIncrease"))) - 1; + int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "m_BtnAdditionalTPButtonsIncrease"))) - 1; ExtDialog.ProcessAdditionalTPButtonsIncrease(i); } // Additional take-profit decrease button #N on Main tab. - else if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "AdditionalTPButtonsDecrease")) == ExtDialog.Name() + "AdditionalTPButtonsDecrease") + else if (StringSubstr(sparam, 0, StringLen(ExtDialog.Name() + "m_BtnAdditionalTPButtonsDecrease")) == ExtDialog.Name() + "m_BtnAdditionalTPButtonsDecrease") { - int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "AdditionalTPButtonsDecrease"))) - 1; + int i = (int)StringToInteger(StringSubstr(sparam, StringLen(ExtDialog.Name() + "m_BtnAdditionalTPButtonsDecrease"))) - 1; ExtDialog.ProcessAdditionalTPButtonsDecrease(i); } // Because there is a bug that keeps a control's Id() = -1 if it is created after the panel is initialized. So, it cannot be processed with the panel's event processor. @@ -586,6 +699,50 @@ void OnChartEvent(const int id, Trade(); } } + // Set stop-loss: + else if ((MainKey_SetStopLossHotKey != 0) && (lparam == MainKey_SetStopLossHotKey)) + { + if (((!ShiftRequired_SetStopLossHotKey) || (TerminalInfoInteger(TERMINAL_KEYSTATE_SHIFT) < 0)) // Shift + && ((!CtrlRequired_SetStopLossHotKey) || (TerminalInfoInteger(TERMINAL_KEYSTATE_CONTROL) < 0))) // Control + { + // Capture point price location. + int subwindow; + double price; + datetime time; // Dummy. + ChartXYToTimePrice(ChartID(), Mouse_Last_X, Mouse_Last_Y, subwindow, time, price); + // If valid, move line SL there. + if ((subwindow == 0) && (price > 0)) + { + ObjectSetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, price); + if ((SLDistanceInPoints) || (ShowATROptions)) ExtDialog.UpdateFixedSL(); + ExtDialog.RefreshValues(); + } + } + } + // Set take-profit: + else if ((MainKey_SetTakeProfitHotKey != 0) && (lparam == MainKey_SetTakeProfitHotKey)) + { + if (((!ShiftRequired_SetTakeProfitHotKey) || (TerminalInfoInteger(TERMINAL_KEYSTATE_SHIFT) < 0)) // Shift + && ((!CtrlRequired_SetTakeProfitHotKey) || (TerminalInfoInteger(TERMINAL_KEYSTATE_CONTROL) < 0))) // Control + { + // Capture point price location. + int subwindow; + double price; + datetime time; // Dummy. + ChartXYToTimePrice(ChartID(), Mouse_Last_X, Mouse_Last_Y, subwindow, time, price); + // If valid, move line SL there. + if ((subwindow == 0) && (price > 0)) + { + ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, price); + if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + if ((TPDistanceInPoints) || (ShowATROptions)) ExtDialog.UpdateFixedTP(); + ExtDialog.ShowTPRelatedEdits(); + ExtDialog.RefreshValues(); + ExtDialog.HideShowMaximize(); + ExtDialog.MoveAndResize(); + } + } + } } // Call Panel's event handler only if it is not a CHARTEVENT_CHART_CHANGE - workaround for minimization bug on chart switch. @@ -623,7 +780,7 @@ void OnChartEvent(const int id, } if (sparam == ObjectPrefix + "StopLossLine") StopLossLineIsBeingMoved = false; // In any case ending moving state for the stop-loss line. - if (StringFind(sparam, ObjectPrefix + "TakeProfitLine") != -1) TakeProfitLineIsBeingMoved = false; // In any case ending moving state for the take-profit line. + if (StringFind(sparam, ObjectPrefix + "TakeProfitLine") != -1) ArrayInitialize(TakeProfitLineIsBeingMoved, false); // In any case ending moving state for the take-profit line. if (id != CHARTEVENT_CHART_CHANGE) ExtDialog.RefreshValues(); diff --git a/MQL5/Experts/Position Sizer/Position Sizer.mqh b/MQL5/Experts/Position Sizer/Position Sizer.mqh index 761b9e0..ed777f2 100644 --- a/MQL5/Experts/Position Sizer/Position Sizer.mqh +++ b/MQL5/Experts/Position Sizer/Position Sizer.mqh @@ -9,14 +9,13 @@ class CPositionSizeCalculator : public CAppDialog { private: CButton m_BtnTabMain, m_BtnTabRisk, m_BtnTabMargin, m_BtnTabSwaps, m_BtnTabTrading, m_BtnOrderType, m_BtnAccount, m_BtnLines, m_BtnStopLoss, m_BtnTakeProfit, m_BtnEntry, m_BtnATRTimeframe, m_BtnCommissionType, m_BtnMaxPS, m_BtnTrade, m_BtnTPsInward, m_BtnTPsOutward, m_BtnTradingTPShare, m_BtnQuickRisk1, m_BtnQuickRisk2, m_BtnEntryIncrease, m_BtnEntryDecrease, m_BtnStopLossIncrease, m_BtnStopLossDecrease, m_BtnTakeProfitIncrease, m_BtnTakeProfitDecrease, m_BtnStopPriceIncrease, m_BtnStopPriceDecrease, m_BtnTakeProfitsNumberAdd, m_BtnTakeProfitsNumberRemove;; - CCheckBox m_ChkSpreadAdjustmentSL, m_ChkSpreadAdjustmentTP, m_ChkCountPendings, m_ChkIgnoreOrdersWithoutSL, m_ChkIgnoreOrdersWithoutTP, m_ChkIgnoreOtherSymbols, m_ChkDisableTradingWhenLinesAreHidden, m_ChkSubtractPositions, m_ChkSubtractPendingOrders, m_ChkDoNotApplyStopLoss, m_ChkDoNotApplyTakeProfit, m_ChkAskForConfirmation, m_ChkCommentAutoSuffix, m_ChkAllSymbols; - CEdit m_EdtEntryLevel, m_EdtSL, m_EdtTP, m_EdtStopPrice, m_EdtAccount, m_EdtCommissionSize, m_EdtRiskPIn, m_EdtRiskPRes, m_EdtRiskMIn, m_EdtRiskMRes, m_EdtReward1, m_EdtReward2, m_EdtRR1, m_EdtRR2, m_EdtPosSize, m_EdtPointValue, m_EdtATRPeriod, m_EdtATRMultiplierSL, m_EdtATRMultiplierTP, m_EdtCurRiskM, m_EdtCurRiskP, m_EdtPotRiskM, m_EdtPotRiskP, m_EdtCurProfitM, m_EdtCurProfitP, m_EdtPotProfitM, m_EdtPotProfitP, m_EdtCurL, m_EdtPotL, m_EdtPosMargin, m_EdtUsedMargin, m_EdtFreeMargin, m_EdtCustomLeverage, m_EdtMaxPositionSizeByMargin, m_EdtSwapsType, m_EdtSwapsTripleDay, m_EdtSwapsNominalLong, m_EdtSwapsNominalShort, m_EdtSwapsDailyLongLot, m_EdtSwapsDailyShortLot, m_EdtSwapsDailyLongPS, m_EdtSwapsDailyShortPS, m_EdtSwapsYearlyLongLot, m_EdtSwapsYearlyShortLot, m_EdtSwapsYearlyLongPS, m_EdtSwapsYearlyShortPS, m_EdtMagicNumber, m_EdtCommentary, m_EdtMaxSlippage, m_EdtMaxSpread, m_EdtMaxEntrySLDistance, m_EdtMinEntrySLDistance, m_EdtMaxPositionSize, m_EdtTrailingStopPoints, m_EdtBreakEvenPoints, m_EdtMaxNumberOfTrades, m_EdtMaxTotalRisk; - CLabel m_LblEntryLevel, m_LblEntryWarning, m_LblSL, m_LblSLWarning, m_LblTPWarning, m_LblStopPrice, m_LblStopPriceWarning, m_LblOrderType, m_LblCommissionSize, m_LblAdditionalFundsAsterisk, m_LblInput, m_LblResult, m_LblRisk, m_LblRiskM, m_LblReward, m_LblRR, m_LblPosSize, m_LblPointValue, m_LblATRPeriod, m_LblATRMultiplierSL, m_LblATRMultiplierTP, m_LblATRValue, m_LblATRTimeframe, m_LblCurrentRiskMoney, m_LblCurrentRiskPerc, m_LblCurrentProfitMoney, m_LblCurrentProfitPerc, m_LblPotentialRiskMoney, m_LblPotentialRiskPerc, m_LblPotentialProfitMoney, m_LblPotentialProfitPerc, m_LblCurrentLots, m_LblPotentialLots, m_LblCurrentPortfolio, m_LblPotentialPortfolio, m_LblPosMargin, m_LblUsedMargin, m_LblFreeMargin, m_LblCustomLeverage, m_LblAccLeverage, m_LblSymbolLeverage, m_LblMaxPositionSizeByMargin, m_LblSwapsType, m_LblSwapsTripleDay, m_LblSwapsLong, m_LblSwapsShort, m_LblSwapsNominal, m_LblSwapsDaily, m_LblSwapsYearly, m_LblSwapsPerLotDaily, m_LblSwapsPerPSDaily, m_LblSwapsPerLotYearly, m_LblSwapsPerPSYearly, m_LblMagicNumber, m_LblCommentary, m_LblTradingPoints, m_LblMaxSlippage, m_LblMaxSpread, m_LblMaxEntrySLDistance, m_LblMinEntrySLDistance, m_LblTradingLots, m_LblMaxPositionSize, m_LblURL, m_LblTradingTP, m_LblTrailingStop, m_LblBreakEven, m_LblMaxNumberOfTrades, m_LblMaxTotalRisk; + CCheckBox m_ChkSpreadAdjustmentSL, m_ChkSpreadAdjustmentTP, m_ChkCountPendings, m_ChkIgnoreOrdersWithoutSL, m_ChkIgnoreOrdersWithoutTP, m_ChkIgnoreOtherSymbols, m_ChkDisableTradingWhenLinesAreHidden, m_ChkSubtractPositions, m_ChkSubtractPendingOrders, m_ChkDoNotApplyStopLoss, m_ChkDoNotApplyTakeProfit, m_ChkAskForConfirmation, m_ChkCommentAutoSuffix; + CEdit m_EdtEntryLevel, m_EdtSL, m_EdtTP, m_EdtStopPrice, m_EdtAccount, m_EdtCommissionSize, m_EdtRiskPIn, m_EdtRiskPRes, m_EdtRiskMIn, m_EdtRiskMRes, m_EdtReward1, m_EdtReward2, m_EdtRR1, m_EdtRR2, m_EdtPosSize, m_EdtPointValue, m_EdtATRPeriod, m_EdtATRMultiplierSL, m_EdtATRMultiplierTP, m_EdtCurRiskM, m_EdtCurRiskP, m_EdtPotRiskM, m_EdtPotRiskP, m_EdtCurProfitM, m_EdtCurProfitP, m_EdtPotProfitM, m_EdtPotProfitP, m_EdtCurL, m_EdtPotL, m_EdtPosMargin, m_EdtUsedMargin, m_EdtFreeMargin, m_EdtCustomLeverage, m_EdtMaxPositionSizeByMargin, m_EdtSwapsType, m_EdtSwapsTripleDay, m_EdtSwapsNominalLong, m_EdtSwapsNominalShort, m_EdtSwapsDailyLongLot, m_EdtSwapsDailyShortLot, m_EdtSwapsDailyLongPS, m_EdtSwapsDailyShortPS, m_EdtSwapsYearlyLongLot, m_EdtSwapsYearlyShortLot, m_EdtSwapsYearlyLongPS, m_EdtSwapsYearlyShortPS, m_EdtMagicNumber, m_EdtCommentary, m_EdtMaxSlippage, m_EdtMaxSpread, m_EdtMaxEntrySLDistance, m_EdtMinEntrySLDistance, m_EdtMaxPositionSize, m_EdtTrailingStopPoints, m_EdtBreakEvenPoints, m_EdtMaxNumberOfTradesTotal, m_EdtMaxNumberOfTradesPerSymbol, m_EdtMaxPositionSizeTotal, m_EdtMaxPositionSizePerSymbol, m_EdtMaxRiskTotal, m_EdtMaxRiskPerSymbol; + CLabel m_LblEntryLevel, m_LblEntryWarning, m_LblSL, m_LblSLWarning, m_LblTPWarning, m_LblStopPrice, m_LblStopPriceWarning, m_LblOrderType, m_LblCommissionSize, m_LblAdditionalFundsAsterisk, m_LblInput, m_LblResult, m_LblRisk, m_LblRiskM, m_LblReward, m_LblRR, m_LblPosSize, m_LblPointValue, m_LblATRPeriod, m_LblATRMultiplierSL, m_LblATRMultiplierTP, m_LblATRValue, m_LblATRTimeframe, m_LblCurrentRiskMoney, m_LblCurrentRiskPerc, m_LblCurrentProfitMoney, m_LblCurrentProfitPerc, m_LblPotentialRiskMoney, m_LblPotentialRiskPerc, m_LblPotentialProfitMoney, m_LblPotentialProfitPerc, m_LblCurrentLots, m_LblPotentialLots, m_LblCurrentPortfolio, m_LblPotentialPortfolio, m_LblPosMargin, m_LblUsedMargin, m_LblFreeMargin, m_LblCustomLeverage, m_LblAccLeverage, m_LblSymbolLeverage, m_LblMaxPositionSizeByMargin, m_LblSwapsType, m_LblSwapsTripleDay, m_LblSwapsLong, m_LblSwapsShort, m_LblSwapsNominal, m_LblSwapsDaily, m_LblSwapsYearly, m_LblSwapsPerLotDaily, m_LblSwapsPerPSDaily, m_LblSwapsPerLotYearly, m_LblSwapsPerPSYearly, m_LblMagicNumber, m_LblCommentary, m_LblTradingPoints, m_LblMaxSlippage, m_LblMaxSpread, m_LblMaxEntrySLDistance, m_LblMinEntrySLDistance, m_LblTradingLots, m_LblURL, m_LblTradingTP, m_LblTrailingStop, m_LblBreakEven, m_LblMaxNumberOfTrades, m_LblMaxNumberOfTradesTotal, m_LblMaxNumberOfTradesPerSymbol, m_LblMaxPositionSize, m_LblMaxPositionSizeTotal, m_LblMaxPositionSizePerSymbol, m_LblMaxRisk, m_LblMaxRiskTotal, m_LblMaxRiskPerSymbol;; string m_FileName; double m_DPIScale; bool NoPanelMaximization; // A crutch variable to prevent panel maximization when Maximize() is called at the indicator's initialization. - bool PosSizeEditing; // Prevent updating position size field while user is editing. int ATR_handle; int PanelWidth; @@ -55,6 +54,7 @@ public: return(CAppDialog::Run()); } virtual void HideShowMaximize(); + virtual void MoveAndResize(); // Arranges panel objects on the panel. virtual void InitATR(); virtual void UpdateFixedSL(); virtual void UpdateFixedTP(); @@ -84,7 +84,8 @@ public: int MaxTakeProfitsNumber; void OnClickBtnTakeProfitsNumberAdd(); virtual void UpdateAdditionalTradingPanelTP(int i); - + void ShowTPRelatedEdits(); + void SetFileName(string file_name) {m_FileName = file_name;} // Remember the panel's location to have the same location for minimized and maximized states. int remember_top, remember_left; @@ -103,7 +104,6 @@ private: virtual bool CreateObjects(); virtual bool InitObjects(); - virtual void MoveAndResize(); // Arranges panel objects on the panel. virtual bool DisplayValues(); // Updates values in the panel. virtual void ProcessTPChange(const bool tp_button_click); @@ -135,7 +135,6 @@ private: void OnEndEditEdtAccount(); void OnEndEditEdtRiskPIn(); void OnEndEditEdtRiskMIn(); - void OnStartEdtPosSize(); void OnEndEditEdtPosSize(); void OnEndEditATRPeriod(); void OnEndEditATRMultiplierSL(); @@ -154,12 +153,14 @@ private: void OnEndEditEdtMaxSpread(); void OnEndEditEdtMaxEntrySLDistance(); void OnEndEditEdtMinEntrySLDistance(); - void OnEndEditEdtMaxPositionSize(); + void OnEndEditEdtMaxPositionSizeTotal(); + void OnEndEditEdtMaxPositionSizePerSymbol(); void OnEndEditEdtTrailingStopPoints(); void OnEndEditEdtBreakEvenPoints(); - void OnEndEditEdtMaxNumberOfTrades(); - void OnEndEditEdtMaxTotalRisk(); - void OnChangeChkAllSymbols(); + void OnEndEditEdtMaxNumberOfTradesTotal(); + void OnEndEditEdtMaxNumberOfTradesPerSymbol(); + void OnEndEditEdtMaxRiskTotal(); + void OnEndEditEdtMaxRiskPerSymbol(); void OnChangeChkSubtractPositions(); void OnChangeChkSubtractPendingOrders(); void OnChangeChkDoNotApplyStopLoss(); @@ -204,7 +205,6 @@ ON_EVENT(ON_END_EDIT, m_EdtCommissionSize, OnEndEditEdtCommissionSize) ON_EVENT(ON_END_EDIT, m_EdtAccount, OnEndEditEdtAccount) ON_EVENT(ON_END_EDIT, m_EdtRiskPIn, OnEndEditEdtRiskPIn) ON_EVENT(ON_END_EDIT, m_EdtRiskMIn, OnEndEditEdtRiskMIn) -ON_EVENT(ON_START_EDIT, m_EdtPosSize, OnStartEdtPosSize) ON_EVENT(ON_END_EDIT, m_EdtPosSize, OnEndEditEdtPosSize) ON_EVENT(ON_END_EDIT, m_EdtATRPeriod, OnEndEditATRPeriod) ON_EVENT(ON_END_EDIT, m_EdtATRMultiplierSL, OnEndEditATRMultiplierSL) @@ -223,12 +223,14 @@ ON_EVENT(ON_END_EDIT, m_EdtMaxSlippage, OnEndEditEdtMaxSlippage) ON_EVENT(ON_END_EDIT, m_EdtMaxSpread, OnEndEditEdtMaxSpread) ON_EVENT(ON_END_EDIT, m_EdtMaxEntrySLDistance, OnEndEditEdtMaxEntrySLDistance) ON_EVENT(ON_END_EDIT, m_EdtMinEntrySLDistance, OnEndEditEdtMinEntrySLDistance) -ON_EVENT(ON_END_EDIT, m_EdtMaxPositionSize, OnEndEditEdtMaxPositionSize) +ON_EVENT(ON_END_EDIT, m_EdtMaxPositionSizeTotal, OnEndEditEdtMaxPositionSizeTotal) +ON_EVENT(ON_END_EDIT, m_EdtMaxPositionSizePerSymbol, OnEndEditEdtMaxPositionSizePerSymbol) ON_EVENT(ON_END_EDIT, m_EdtTrailingStopPoints, OnEndEditEdtTrailingStopPoints) ON_EVENT(ON_END_EDIT, m_EdtBreakEvenPoints, OnEndEditEdtBreakEvenPoints) -ON_EVENT(ON_END_EDIT, m_EdtMaxNumberOfTrades, OnEndEditEdtMaxNumberOfTrades) -ON_EVENT(ON_END_EDIT, m_EdtMaxTotalRisk, OnEndEditEdtMaxTotalRisk) -ON_EVENT(ON_CHANGE, m_ChkAllSymbols, OnChangeChkAllSymbols) +ON_EVENT(ON_END_EDIT, m_EdtMaxNumberOfTradesTotal, OnEndEditEdtMaxNumberOfTradesTotal) +ON_EVENT(ON_END_EDIT, m_EdtMaxNumberOfTradesPerSymbol, OnEndEditEdtMaxNumberOfTradesPerSymbol) +ON_EVENT(ON_END_EDIT, m_EdtMaxRiskTotal, OnEndEditEdtMaxRiskTotal) +ON_EVENT(ON_END_EDIT, m_EdtMaxRiskPerSymbol, OnEndEditEdtMaxRiskPerSymbol) ON_EVENT(ON_CHANGE, m_ChkSubtractPositions, OnChangeChkSubtractPositions) ON_EVENT(ON_CHANGE, m_ChkSubtractPendingOrders, OnChangeChkSubtractPendingOrders) ON_EVENT(ON_CHANGE, m_ChkDoNotApplyStopLoss, OnChangeChkDoNotApplyStopLoss) @@ -243,7 +245,7 @@ ON_EVENT(ON_CLICK, m_BtnTabTrading, OnClickBtnTabTrading) if (DefaultSL > 0) ON_EVENT(ON_CLICK, m_BtnStopLoss, OnClickBtnStopLoss) ON_EVENT(ON_CLICK, m_BtnTakeProfit, OnClickBtnTakeProfit) ON_EVENT(ON_CLICK, m_BtnEntry, OnClickBtnEntry) -if (!ShowATROptions) ON_EVENT(ON_CLICK, m_BtnATRTimeframe, OnClickBtnATRTimeframe) +if (ShowATROptions) ON_EVENT(ON_CLICK, m_BtnATRTimeframe, OnClickBtnATRTimeframe) ON_EVENT(ON_CLICK, m_BtnTrade, OnClickBtnTrade) if (QuickRisk1 > 0) ON_EVENT(ON_CLICK, m_BtnQuickRisk1, OnClickBtnQuickRisk1) if (QuickRisk2 > 0) ON_EVENT(ON_CLICK, m_BtnQuickRisk2, OnClickBtnQuickRisk2) @@ -480,34 +482,34 @@ bool CPositionSizeCalculator::CreateObjects() // Tabs - if (!ButtonCreate(NULL, m_BtnTabMain, tab_button_start, y, tab_button_start + tab_button_width, y + element_height, "m_BtnTabMain", "Main")) return false; + if (!ButtonCreate(NULL, m_BtnTabMain, tab_button_start, y, tab_button_start + tab_button_width, y + element_height, "m_BtnTabMain", TRANSLATION_TAB_BUTTON_MAIN)) return false; MainTabList = new CPanelList; - if (!ButtonCreate(NULL, m_BtnTabRisk, tab_button_start + tab_button_width + tab_button_spacing, y, tab_button_start + tab_button_width * 2 + tab_button_spacing, y + element_height, "m_BtnTabRisk", "Risk")) return false; + if (!ButtonCreate(NULL, m_BtnTabRisk, tab_button_start + tab_button_width + tab_button_spacing, y, tab_button_start + tab_button_width * 2 + tab_button_spacing, y + element_height, "m_BtnTabRisk", TRANSLATION_TAB_BUTTON_RISK)) return false; RiskTabList = new CPanelList; - if (!ButtonCreate(NULL, m_BtnTabMargin, tab_button_start + tab_button_width * 2 + tab_button_spacing * 2, y, tab_button_start + tab_button_width * 3 + tab_button_spacing * 2, y + element_height, "m_BtnTabMargin", "Margin")) return false; + if (!ButtonCreate(NULL, m_BtnTabMargin, tab_button_start + tab_button_width * 2 + tab_button_spacing * 2, y, tab_button_start + tab_button_width * 3 + tab_button_spacing * 2, y + element_height, "m_BtnTabMargin", TRANSLATION_TAB_BUTTON_MARGIN)) return false; MarginTabList = new CPanelList; - if (!ButtonCreate(NULL, m_BtnTabSwaps, tab_button_start + tab_button_width * 3 + tab_button_spacing * 3, y, tab_button_start + tab_button_width * 4 + tab_button_spacing * 3, y + element_height, "m_BtnTabSwaps", "Swaps")) return false; + if (!ButtonCreate(NULL, m_BtnTabSwaps, tab_button_start + tab_button_width * 3 + tab_button_spacing * 3, y, tab_button_start + tab_button_width * 4 + tab_button_spacing * 3, y + element_height, "m_BtnTabSwaps", TRANSLATION_TAB_BUTTON_SWAPS)) return false; SwapsTabList = new CPanelList; - if (!ButtonCreate(NULL, m_BtnTabTrading, tab_button_start + tab_button_width * 4 + tab_button_spacing * 4, y, tab_button_start + tab_button_width * 5 + tab_button_spacing * 4, y + element_height, "m_BtnTabTrading", "Trading")) return false; + if (!ButtonCreate(NULL, m_BtnTabTrading, tab_button_start + tab_button_width * 4 + tab_button_spacing * 4, y, tab_button_start + tab_button_width * 5 + tab_button_spacing * 4, y + element_height, "m_BtnTabTrading", TRANSLATION_TAB_BUTTON_TRADING)) return false; TradingTabList = new CPanelList; // Main y = row_start + element_height + 3 * v_spacing; - if (!LabelCreate(MainTabList, m_LblEntryLevel, first_column_start, y, first_column_start + narrowest_label_width, y + element_height, "m_LblEntryLevel", "Entry:")) return false; + if (!LabelCreate(MainTabList, m_LblEntryLevel, first_column_start, y, first_column_start + narrowest_label_width, y + element_height, "m_LblEntryLevel", TRANSLATION_LABEL_ENTRY + ":")) return false; // Button to quickly switch between Long/Short trade planning. - if (!ButtonCreate(MainTabList, m_BtnEntry, first_column_start + narrowest_label_width + v_spacing, y, second_column_start - v_spacing, y + element_height, "m_BtnEntry", EnumToString(sets.TradeDirection), "Switch between Long and Short")) return false; + if (!ButtonCreate(MainTabList, m_BtnEntry, first_column_start + narrowest_label_width + v_spacing, y, second_column_start - v_spacing, y + element_height, "m_BtnEntry", EnumToString(sets.TradeDirection), TRANSLATION_TOOLTIP_BUTTON_LONG_SHORT)) return false; if (!EditCreate(MainTabList, m_EdtEntryLevel, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtEntryLevel", "")) return false; - if (!ButtonCreate(MainTabList, m_BtnEntryIncrease, second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnEntryIncrease", "+", "Increase Entry by 1 point")) return false; - if (!ButtonCreate(MainTabList, m_BtnEntryDecrease, second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnEntryDecrease", "-", "Decrease Entry by 1 point")) return false; + if (!ButtonCreate(MainTabList, m_BtnEntryIncrease, second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnEntryIncrease", "+", TRANSLATION_TOOLTIP_ENTRY_INCREASE)) return false; + if (!ButtonCreate(MainTabList, m_BtnEntryDecrease, second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnEntryDecrease", "-", TRANSLATION_TOOLTIP_ENTRY_DECREASE)) return false; if (!LabelCreate(MainTabList, m_LblEntryWarning, third_column_start, y, third_column_start + narrow_label_width, y + element_height, "m_LblEntryWarning", "")) return false; y += element_height + v_spacing; - string stoploss_label_text = "Stop-loss: "; - if (SLDistanceInPoints) stoploss_label_text = "SL, points: "; + string stoploss_label_text = TRANSLATION_LABEL_STOPLOSS + ":"; + if (SLDistanceInPoints) stoploss_label_text = TRANSLATION_BUTTON_SL + ":"; if (DefaultSL > 0) // Use button to quickly set SL. { @@ -516,19 +518,19 @@ bool CPositionSizeCalculator::CreateObjects() else if (!LabelCreate(MainTabList, m_LblSL, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblSL", stoploss_label_text)) return false; if (!EditCreate(MainTabList, m_EdtSL, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtSL", "")) return false; - if (!ButtonCreate(MainTabList, m_BtnStopLossIncrease, second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnStopLossIncrease", "+", "Increase Stop-loss by 1 point")) return false; - if (!ButtonCreate(MainTabList, m_BtnStopLossDecrease, second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnStopLossDecrease", "-", "Decrease Stop-loss by 1 point")) return false; + if (!ButtonCreate(MainTabList, m_BtnStopLossIncrease, second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnStopLossIncrease", "+", TRANSLATION_TOOLTIP_STOPLOSS_INCREASE)) return false; + if (!ButtonCreate(MainTabList, m_BtnStopLossDecrease, second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnStopLossDecrease", "-", TRANSLATION_TOOLTIP_STOPLOSS_DECREASE)) return false; if (!LabelCreate(MainTabList, m_LblSLWarning, third_column_start, y, third_column_start + narrow_label_width, y + element_height, "m_LblSLWarning", "")) return false; y += element_height + v_spacing; - string takeprofit_label_text = "Take-profit: "; - if (TPDistanceInPoints) takeprofit_label_text = "TP, points: "; - if (!ButtonCreate(MainTabList, m_BtnTakeProfitsNumberAdd, first_column_start, y, first_column_start + v_spacing * 4 - 1, y + element_height, "m_BtnTakeProfitsNumberAdd", "+", "Add a take-profit level")) return false; - if (!ButtonCreate(MainTabList, m_BtnTakeProfit, first_column_start + v_spacing * 4, y, first_column_start + v_spacing * 3 + normal_label_width, y + element_height, "m_BtnTakeProfit", takeprofit_label_text, "Set TP based on SL or enable locked TP mode")) return false; + string takeprofit_label_text = TRANSLATION_LABEL_TAKEPROFIT + ":"; + if (TPDistanceInPoints) takeprofit_label_text = TRANSLATION_BUTTON_TP + ":"; + if (!ButtonCreate(MainTabList, m_BtnTakeProfitsNumberAdd, first_column_start, y, first_column_start + v_spacing * 4 - 1, y + element_height, "m_BtnTakeProfitsNumberAdd", "+", TRANSLATION_TOOLTIP_TAKEPROFIT_ADD)) return false; + if (!ButtonCreate(MainTabList, m_BtnTakeProfit, first_column_start + v_spacing * 4, y, first_column_start + v_spacing * 3 + normal_label_width, y + element_height, "m_BtnTakeProfit", takeprofit_label_text, TRANSLATION_TOOLTIP_BUTTON_TP)) return false; if (!EditCreate(MainTabList, m_EdtTP, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtTP", "")) return false; - if (!ButtonCreate(MainTabList, m_BtnTakeProfitIncrease, second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnTakeProfitIncrease", "+", "Increase Take-profit by 1 point")) return false; - if (!ButtonCreate(MainTabList, m_BtnTakeProfitDecrease, second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnTakeProfitDecrease", "-", "Decrease Take-profit by 1 point")) return false; + if (!ButtonCreate(MainTabList, m_BtnTakeProfitIncrease, second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnTakeProfitIncrease", "+", TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE)) return false; + if (!ButtonCreate(MainTabList, m_BtnTakeProfitDecrease, second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnTakeProfitDecrease", "-", TRANSLATION_TOOLTIP_TAKEPROFIT_DECREASE)) return false; if (!LabelCreate(MainTabList, m_LblTPWarning, third_column_start, y, third_column_start + narrow_label_width, y + element_height, "m_LblTPWarning", "")) return false; // Multiple TP levels for the Main tab. @@ -543,12 +545,12 @@ bool CPositionSizeCalculator::CreateObjects() ArrayResize(AdditionalWarningTP, sets.TakeProfitsNumber - 1); // String array. ArrayResize(AdditionalOutputRR, sets.TakeProfitsNumber - 1); // String array. ArrayResize(AdditionalOutputReward, sets.TakeProfitsNumber - 1); // Double array. - string additional_tp_label_beginning = "Take-profit "; + string additional_tp_label_beginning = TRANSLATION_LABEL_TAKEPROFIT + " "; string additional_tp_label_end = ":"; if (TPDistanceInPoints) { - additional_tp_label_beginning = "TP "; - additional_tp_label_end = ", points:"; + additional_tp_label_beginning = TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE + " "; + additional_tp_label_end = ", " + TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_POINTS + ":"; } for (int i = 0; i < sets.TakeProfitsNumber - 1; i++) { @@ -556,65 +558,65 @@ bool CPositionSizeCalculator::CreateObjects() if (i == sets.TakeProfitsNumber - 2) // The last iteration. { // Because only one Remove button is needed. - if (!ButtonCreate(MainTabList, m_BtnTakeProfitsNumberRemove, first_column_start, y, first_column_start + v_spacing * 4 - 1, y + element_height, "m_BtnTakeProfitsNumberRemove", "x", "Remove Take-profit")) return false; + if (!ButtonCreate(MainTabList, m_BtnTakeProfitsNumberRemove, first_column_start, y, first_column_start + v_spacing * 4 - 1, y + element_height, "m_BtnTakeProfitsNumberRemove", "x", TRANSLATION_TOOLTIP_TAKEPROFIT_REMOVE)) return false; } - if (!LabelCreate(MainTabList, AdditionalTPLabels[i], first_column_start + v_spacing * 4, y, first_column_start + normal_label_width, y + element_height, "AdditionalTPLabels" + IntegerToString(i + 2), additional_tp_label_beginning + IntegerToString(i + 2) + additional_tp_label_end)) return false; - if (!EditCreate(MainTabList, AdditionalTPEdits[i], second_column_start, y, second_column_start + normal_edit_width, y + element_height, "AdditionalTPEdits" + IntegerToString(i + 2), "")) return false; - if (!ButtonCreate(MainTabList, AdditionalTPButtonsIncrease[i], second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "AdditionalTPButtonsIncrease" + IntegerToString(i + 2), "+", "Increase Take-profit #" + IntegerToString(i + 2) + " by 1 point")) return false; - if (!ButtonCreate(MainTabList, AdditionalTPButtonsDecrease[i], second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "AdditionalTPButtonsDecrease" + IntegerToString(i + 2), "-", "Decrease Take-profit #" + IntegerToString(i + 2) + " by 1 point")) return false; - if (!LabelCreate(MainTabList, AdditionalTPWarnings[i], third_column_start, y, third_column_start + narrow_label_width, y + element_height, "AdditionalTPWarnings" + IntegerToString(i + 2), "")) return false; + if (!LabelCreate(MainTabList, AdditionalTPLabels[i], first_column_start + v_spacing * 4, y, first_column_start + normal_label_width, y + element_height, "m_LblAdditionalTPLabels" + IntegerToString(i + 2), additional_tp_label_beginning + IntegerToString(i + 2) + additional_tp_label_end)) return false; + if (!EditCreate(MainTabList, AdditionalTPEdits[i], second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtAdditionalTPEdits" + IntegerToString(i + 2), "")) return false; + if (!ButtonCreate(MainTabList, AdditionalTPButtonsIncrease[i], second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnAdditionalTPButtonsIncrease" + IntegerToString(i + 2), "+", TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE_MULTIPLE + " #" + IntegerToString(i + 2) + " " + TRANSLATION_TOOLTIP_TAKEPROFIT_BY_ONE_POINT)) return false; + if (!ButtonCreate(MainTabList, AdditionalTPButtonsDecrease[i], second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnAdditionalTPButtonsDecrease" + IntegerToString(i + 2), "-", TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE_MULTIPLE + " #" + IntegerToString(i + 2) + " " + TRANSLATION_TOOLTIP_TAKEPROFIT_BY_ONE_POINT)) return false; + if (!LabelCreate(MainTabList, AdditionalTPWarnings[i], third_column_start, y, third_column_start + narrow_label_width, y + element_height, "m_LblAdditionalTPWarnings" + IntegerToString(i + 2), "")) return false; } } y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblStopPrice, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblStopPrice", "Stop price: ")) return false; + if (!LabelCreate(MainTabList, m_LblStopPrice, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblStopPrice", TRANSLATION_LABEL_STOPPRICE + ":")) return false; if (!EditCreate(MainTabList, m_EdtStopPrice, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtStopPrice", "")) return false; - if (!ButtonCreate(MainTabList, m_BtnStopPriceIncrease, second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnStopPriceIncrease", "+", "Increase Stop price by 1 point")) return false; - if (!ButtonCreate(MainTabList, m_BtnStopPriceDecrease, second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnStopPriceDecrease", "-", "Decrease Stop price by 1 point")) return false; + if (!ButtonCreate(MainTabList, m_BtnStopPriceIncrease, second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, "m_BtnStopPriceIncrease", "+", TRANSLATION_TOOLTIP_STOPPRICE_INCREASE)) return false; + if (!ButtonCreate(MainTabList, m_BtnStopPriceDecrease, second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, "m_BtnStopPriceDecrease", "-", TRANSLATION_TOOLTIP_STOPPRICE_DECREASE)) return false; if (!LabelCreate(MainTabList, m_LblStopPriceWarning, third_column_start, y, third_column_start + narrow_label_width, y + element_height, "m_LblStopPriceWarning", "")) return false; if (ShowATROptions) { y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblATRPeriod, first_column_start, y, first_column_start + atr_period_label_width, y + element_height, "m_LblATRPeriod", "ATR period:")) return false; + if (!LabelCreate(MainTabList, m_LblATRPeriod, first_column_start, y, first_column_start + atr_period_label_width, y + element_height, "m_LblATRPeriod", TRANSLATION_LABEL_ATR_PERIOD + ":")) return false; if (!EditCreate(MainTabList, m_EdtATRPeriod, first_column_start + atr_period_label_width, y, first_column_start + atr_period_label_width + atr_period_edit_width, y + element_height, "m_EdtATRPeriod", "")) return false; - if (!LabelCreate(MainTabList, m_LblATRMultiplierSL, second_column_start, y, second_column_start + narrow_label_width, y + element_height, "m_LblATRMultiplierSL", "SL multiplier:")) return false; + if (!LabelCreate(MainTabList, m_LblATRMultiplierSL, second_column_start, y, second_column_start + narrow_label_width, y + element_height, "m_LblATRMultiplierSL", TRANSLATION_LABEL_ATR_SL_MULTIPLIER + ":")) return false; if (!EditCreate(MainTabList, m_EdtATRMultiplierSL, second_column_start + narrow_label_width, y, second_column_start + narrow_label_width + tab_button_width, y + element_height, "m_EdtATRMultiplierSL", "")) return false; if (PanelWidth > 350) { - if (!CheckBoxCreate(MainTabList, m_ChkSpreadAdjustmentSL, second_column_start + narrow_label_width + tab_button_width + v_spacing, y, second_column_start + narrow_label_width + tab_button_width + normal_label_width / 2 - v_spacing * 2, y + element_height, "m_ChkSpreadAdjustmentSL", "SA", "Apply spread adjustment to stop-loss")) return false; - if (!LabelCreate(MainTabList, m_LblATRTimeframe, third_column_start, y, third_column_start + normal_label_width, y + element_height, "m_LblATRTimeframe", "ATR timeframe:")) return false; + if (!CheckBoxCreate(MainTabList, m_ChkSpreadAdjustmentSL, second_column_start + narrow_label_width + tab_button_width + v_spacing, y, second_column_start + narrow_label_width + tab_button_width + normal_label_width / 2 - v_spacing * 2, y + element_height, "m_ChkSpreadAdjustmentSL", TRANSLATION_CHECKBOX_ATR_SA, TRANSLATION_TOOLTIP_ATR_SA_SL)) return false; + if (!LabelCreate(MainTabList, m_LblATRTimeframe, third_column_start, y, third_column_start + normal_label_width, y + element_height, "m_LblATRTimeframe", TRANSLATION_LABEL_ATR_TIMEFRAME + ":")) return false; } else { - if (!CheckBoxCreate(MainTabList, m_ChkSpreadAdjustmentSL, third_column_start + normal_edit_width / 2 + v_spacing, y, third_column_start + normal_edit_width + v_spacing, y + element_height, "m_ChkSpreadAdjustmentSL", "SA", "Apply spread adjustment to stop-loss")) return false; + if (!CheckBoxCreate(MainTabList, m_ChkSpreadAdjustmentSL, third_column_start + normal_edit_width / 2 + v_spacing, y, third_column_start + normal_edit_width + v_spacing, y + element_height, "m_ChkSpreadAdjustmentSL", TRANSLATION_CHECKBOX_ATR_SA, TRANSLATION_TOOLTIP_ATR_SA_SL)) return false; } y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblATRValue, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblATRValue", "ATR = ")) return false; + if (!LabelCreate(MainTabList, m_LblATRValue, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblATRValue", TRANSLATION_LABEL_ATR_VALUE + " = ")) return false; - if (!LabelCreate(MainTabList, m_LblATRMultiplierTP, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_LblATRMultiplierTP", "TP multiplier:")) return false; + if (!LabelCreate(MainTabList, m_LblATRMultiplierTP, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_LblATRMultiplierTP", TRANSLATION_LABEL_ATR_TP_MULTIPLIER + ":")) return false; if (!EditCreate(MainTabList, m_EdtATRMultiplierTP, second_column_start + narrow_label_width, y, second_column_start + narrow_label_width + tab_button_width, y + element_height, "m_EdtATRMultiplierTP", "")) return false; if (PanelWidth > 350) { - if (!CheckBoxCreate(MainTabList, m_ChkSpreadAdjustmentTP, second_column_start + narrow_label_width + tab_button_width + v_spacing, y, second_column_start + narrow_label_width + tab_button_width + normal_label_width / 2 - v_spacing * 2, y + element_height, "m_ChkSpreadAdjustmentTP", "SA", "Apply spread adjustment to take-profit")) return false; + if (!CheckBoxCreate(MainTabList, m_ChkSpreadAdjustmentTP, second_column_start + narrow_label_width + tab_button_width + v_spacing, y, second_column_start + narrow_label_width + tab_button_width + normal_label_width / 2 - v_spacing * 2, y + element_height, "m_ChkSpreadAdjustmentTP", TRANSLATION_CHECKBOX_ATR_SA, TRANSLATION_TOOLTIP_ATR_SA_TP)) return false; if (!ButtonCreate(MainTabList, m_BtnATRTimeframe, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_BtnATRTimeframe", EnumToString((ENUM_TIMEFRAMES)_Period))) return false; } else { - if (!CheckBoxCreate(MainTabList, m_ChkSpreadAdjustmentTP, third_column_start + normal_edit_width / 2 + v_spacing, y, third_column_start + normal_edit_width + v_spacing, y + element_height, "m_ChkSpreadAdjustmentTP", "SA", "Apply spread adjustment to take-profit")) return false; + if (!CheckBoxCreate(MainTabList, m_ChkSpreadAdjustmentTP, third_column_start + normal_edit_width / 2 + v_spacing, y, third_column_start + normal_edit_width + v_spacing, y + element_height, "m_ChkSpreadAdjustmentTP", TRANSLATION_CHECKBOX_ATR_SA, TRANSLATION_TOOLTIP_ATR_SA_TP)) return false; y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblATRTimeframe, first_column_start, y, first_column_start + atr_period_label_width, y + element_height, "m_LblATRTimeframe", "ATR timeframe:")) return false; + if (!LabelCreate(MainTabList, m_LblATRTimeframe, first_column_start, y, first_column_start + atr_period_label_width, y + element_height, "m_LblATRTimeframe", TRANSLATION_LABEL_ATR_TIMEFRAME + ":")) return false; if (!ButtonCreate(MainTabList, m_BtnATRTimeframe, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_BtnATRTimeframe", EnumToString((ENUM_TIMEFRAMES)_Period))) return false; } @@ -622,39 +624,39 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblOrderType, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblOrderType", "Order type:")) return false; - if (!ButtonCreate(MainTabList, m_BtnOrderType, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_BtnOrderType", "Instant", "Switch between Instant, Pending, and Stop Limit")) return false; + if (!LabelCreate(MainTabList, m_LblOrderType, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblOrderType", TRANSLATION_LABEL_ORDER_TYPE + ":")) return false; + if (!ButtonCreate(MainTabList, m_BtnOrderType, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_BtnOrderType", TRANSLATION_BUTTON_ORDER_TYPE_INSTANT, TRANSLATION_TOOLTIP_ORDER_TYPE)) return false; - if (!ButtonCreate(MainTabList, m_BtnLines, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_BtnLines", "Hide lines")) return false; + if (!ButtonCreate(MainTabList, m_BtnLines, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_BtnLines", TRANSLATION_BUTTON_HIDE_LINES)) return false; y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblCommissionSize, first_column_start, y, second_column_start + risk_perc_edit_width, y + element_height, "m_LblCommissionSize", "Commission (one-way) per lot:", "In account currency or %, per 1 standard lot")) return false; - if (!ButtonCreate(MainTabList, m_BtnCommissionType, second_column_start + risk_perc_edit_width, y, third_column_start - v_spacing, y + element_height, "m_BtnCommissionType", "???", "Click to switch")) return false; + if (!LabelCreate(MainTabList, m_LblCommissionSize, first_column_start, y, second_column_start + risk_perc_edit_width, y + element_height, "m_LblCommissionSize", TRANSLATION_LABEL_COMMISSION + ":", TRANSLATION_TOOLTIP_COMMISSION)) return false; + if (!ButtonCreate(MainTabList, m_BtnCommissionType, second_column_start + risk_perc_edit_width, y, third_column_start - v_spacing, y + element_height, "m_BtnCommissionType", "???", TRANSLATION_TOOLTIP_COMMISSION_TYPE)) return false; if (!EditCreate(MainTabList, m_EdtCommissionSize, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_EdtCommissionSize", "")) return false; y += element_height + v_spacing; if (!HideAccSize) { - if (!ButtonCreate(MainTabList, m_BtnAccount, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_BtnAccount", "Account balance", "Switch between balance, equity, and balance minus current portfolio risk")) return false; + if (!ButtonCreate(MainTabList, m_BtnAccount, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_BtnAccount", TRANSLATION_BUTTON_ACCOUNT_BALANCE, TRANSLATION_TOOLTIP_ACCOUNT_SIZE)) return false; if (!EditCreate(MainTabList, m_EdtAccount, second_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_EdtAccount", "")) return false; string tooltip = ""; - if (CustomBalance > 0) tooltip = "Custom balance set"; - else if (AdditionalFunds > 0) tooltip = "+" + DoubleToString(AdditionalFunds, 2) + " additional funds"; - else if (AdditionalFunds < 0) tooltip = DoubleToString(-AdditionalFunds, 2) + " funds subtracted"; + if (CustomBalance > 0) tooltip = TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_CUSTOM; + else if (AdditionalFunds > 0) tooltip = "+" + DoubleToString(AdditionalFunds, 2) + " " + TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_ADD; + else if (AdditionalFunds < 0) tooltip = DoubleToString(-AdditionalFunds, 2) + " " + TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_SUB; if (!LabelCreate(MainTabList, m_LblAdditionalFundsAsterisk, third_column_start + normal_edit_width + v_spacing, y, third_column_start + normal_edit_width + v_spacing * 2, y + element_height, "m_LblAdditionalFundsAsterisk", "*", tooltip)) return false; y += element_height + v_spacing; } - if (!LabelCreate(MainTabList, m_LblInput, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_LblInput", "Input")) return false; - if (!LabelCreate(MainTabList, m_LblResult, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_LblResult", "Result")) return false; + if (!LabelCreate(MainTabList, m_LblInput, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_LblInput", TRANSLATION_LABEL_INPUT)) return false; + if (!LabelCreate(MainTabList, m_LblResult, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_LblResult", TRANSLATION_LABEL_RESULT)) return false; y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblRisk, first_column_start, y, first_column_start + tab_button_width - v_spacing, y + element_height, "m_LblRisk", "Risk, %:")) return false; + if (!LabelCreate(MainTabList, m_LblRisk, first_column_start, y, first_column_start + tab_button_width - v_spacing, y + element_height, "m_LblRisk", TRANSLATION_LABEL_RISK + ", %:")) return false; if (QuickRisk1 > 0) if (!ButtonCreate(MainTabList, m_BtnQuickRisk1, first_column_start + quick_risk_button_offset, y, first_column_start + quick_risk_button_offset + quick_risk_button_width, y + element_height, "m_BtnQuickRisk1", "", "%")) return false; if (QuickRisk2 > 0) if (!ButtonCreate(MainTabList, m_BtnQuickRisk2, first_column_start + quick_risk_button_offset + quick_risk_button_width + v_spacing, y, first_column_start + quick_risk_button_offset + quick_risk_button_width * 2 + v_spacing, y + element_height, "m_BtnQuickRisk2", "", "%")) return false; @@ -666,7 +668,7 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblRiskM, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblRiskM", "Risk, money:")) return false; + if (!LabelCreate(MainTabList, m_LblRiskM, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblRiskM", TRANSLATION_LABEL_RISK + ", " + TRANSLATION_LABEL_MONEY + ":")) return false; if (!EditCreate(MainTabList, m_EdtRiskMIn, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtRiskMIn", "")) return false; if (!EditCreate(MainTabList, m_EdtRiskMRes, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_EdtRiskMRes", "")) return false; m_EdtRiskMRes.ReadOnly(true); @@ -674,7 +676,7 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblReward, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblReward", "Reward, money:")) return false; + if (!LabelCreate(MainTabList, m_LblReward, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblReward", TRANSLATION_LABEL_REWARD + ", " + TRANSLATION_LABEL_MONEY + ":")) return false; if (!EditCreate(MainTabList, m_EdtReward1, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtReward1", "")) return false; m_EdtReward1.ReadOnly(true); m_EdtReward1.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); @@ -684,7 +686,7 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblRR, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblRR", "Reward/risk:")) return false; + if (!LabelCreate(MainTabList, m_LblRR, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblRR", TRANSLATION_LABEL_REWARD_RISK + ":")) return false; if (!EditCreate(MainTabList, m_EdtRR1, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_EdtRR1", "")) return false; if (!EditCreate(MainTabList, m_EdtRR2, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_EdtRR2", "")) return false; m_EdtRR1.ReadOnly(true); @@ -694,15 +696,15 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblPosSize, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblPosSize", "Position size:")) return false; - if (ShowMaxPSButton) if (!ButtonCreate(MainTabList, m_BtnMaxPS, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_BtnMaxPS", "Max PS")) return false; + if (!LabelCreate(MainTabList, m_LblPosSize, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblPosSize", TRANSLATION_LABEL_POSITION_SIZE + ":")) return false; + if (ShowMaxPSButton) if (!ButtonCreate(MainTabList, m_BtnMaxPS, second_column_start, y, second_column_start + normal_edit_width, y + element_height, "m_BtnMaxPS", TRANSLATION_BUTTON_MAX_PS)) return false; if (!EditCreate(MainTabList, m_EdtPosSize, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_EdtPosSize", "")) return false; if (ShowPointValue) { y += element_height + v_spacing; - if (!LabelCreate(MainTabList, m_LblPointValue, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblPointValue", "Point value:", "")) return false; + if (!LabelCreate(MainTabList, m_LblPointValue, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblPointValue", TRANSLATION_LABEL_POINT_VALUE + ":", "")) return false; if (!EditCreate(MainTabList, m_EdtPointValue, third_column_start, y, third_column_start + normal_edit_width, y + element_height, "m_EdtPointValue", "")) return false; m_EdtPointValue.ReadOnly(true); m_EdtPointValue.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); @@ -720,29 +722,29 @@ bool CPositionSizeCalculator::CreateObjects() // Reset y = row_start + element_height + 3 * v_spacing; - if (!CheckBoxCreate(RiskTabList, m_ChkCountPendings, first_column_start, y, panel_end, y + element_height, "m_ChkCountPendings", "Count pending orders")) return false; + if (!CheckBoxCreate(RiskTabList, m_ChkCountPendings, first_column_start, y, panel_end, y + element_height, "m_ChkCountPendings", TRANSLATION_CHECKBOX_COUNT_PENDING_ORDERS)) return false; y += element_height + v_spacing; - if (!CheckBoxCreate(RiskTabList, m_ChkIgnoreOrdersWithoutSL, first_column_start, y, panel_end, y + element_height, "m_ChkIgnoreOrdersWithoutSL", "Ignore orders without stop-loss")) return false; + if (!CheckBoxCreate(RiskTabList, m_ChkIgnoreOrdersWithoutSL, first_column_start, y, panel_end, y + element_height, "m_ChkIgnoreOrdersWithoutSL", TRANSLATION_CHECKBOX_IGNORE_ORDERS_WO_SL)) return false; y += element_height + v_spacing; - if (!CheckBoxCreate(RiskTabList, m_ChkIgnoreOrdersWithoutTP, first_column_start, y, panel_end, y + element_height, "m_ChkIgnoreOrdersWithoutTP", "Ignore orders without take-profit")) return false; + if (!CheckBoxCreate(RiskTabList, m_ChkIgnoreOrdersWithoutTP, first_column_start, y, panel_end, y + element_height, "m_ChkIgnoreOrdersWithoutTP", TRANSLATION_CHECKBOX_IGNORE_ORDERS_WO_TP)) return false; y += element_height + v_spacing; - if (!CheckBoxCreate(RiskTabList, m_ChkIgnoreOtherSymbols, first_column_start, y, panel_end, y + element_height, "m_ChkIgnoreOtherSymbols", "Ignore orders in other symbols")) return false; + if (!CheckBoxCreate(RiskTabList, m_ChkIgnoreOtherSymbols, first_column_start, y, panel_end, y + element_height, "m_ChkIgnoreOtherSymbols", TRANSLATION_CHECKBOX_IGNORE_ORDERS_IN_OTHER_SYMBOLS)) return false; y += element_height + v_spacing; - if (!LabelCreate(RiskTabList, m_LblCurrentRiskMoney, second_risk_column_start, y, second_risk_column_start + narrow_label_width, y + element_height, "m_LblCurrentRiskMoney", "Risk $")) return false; - if (!LabelCreate(RiskTabList, m_LblCurrentRiskPerc, third_risk_column_start, y, third_risk_column_start + narrowest_label_width, y + element_height, "m_LblCurrentRiskPerc", "Risk %")) return false; - if (!LabelCreate(RiskTabList, m_LblCurrentLots, fourth_risk_column_start, y, fourth_risk_column_start + narrowest_label_width, y + element_height, "m_LblCurrentLots", "Lots")) return false; + if (!LabelCreate(RiskTabList, m_LblCurrentRiskMoney, second_risk_column_start, y, second_risk_column_start + narrow_label_width, y + element_height, "m_LblCurrentRiskMoney", TRANSLATION_LABEL_RISK + " $")) return false; + if (!LabelCreate(RiskTabList, m_LblCurrentRiskPerc, third_risk_column_start, y, third_risk_column_start + narrowest_label_width, y + element_height, "m_LblCurrentRiskPerc", TRANSLATION_LABEL_RISK + " %")) return false; + if (!LabelCreate(RiskTabList, m_LblCurrentLots, fourth_risk_column_start, y, fourth_risk_column_start + narrowest_label_width, y + element_height, "m_LblCurrentLots", TRANSLATION_LABEL_LOTS)) return false; y += element_height + v_spacing; - if (!LabelCreate(RiskTabList, m_LblCurrentPortfolio, first_column_start, y, second_risk_column_start, y + element_height, "m_LblCurrentPortfolio", "Current portfolio:", "Trades that are currently open")) return false; + if (!LabelCreate(RiskTabList, m_LblCurrentPortfolio, first_column_start, y, second_risk_column_start, y + element_height, "m_LblCurrentPortfolio", TRANSLATION_LABEL_CURRENT_PORTFOLIO + ":", TRANSLATION_TOOLTIP_CURRENT_PORTFOLIO)) return false; if (!EditCreate(RiskTabList, m_EdtCurRiskM, second_risk_column_start, y, second_risk_column_start + normal_edit_width, y + element_height, "m_EdtCurRiskM", "")) return false; m_EdtCurRiskM.ReadOnly(true); m_EdtCurRiskM.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); @@ -755,8 +757,8 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(RiskTabList, m_LblCurrentProfitMoney, second_risk_column_start, y, second_risk_column_start + narrow_label_width, y + element_height, "m_LblCurrentProfitMoney", "Reward $")) return false; - if (!LabelCreate(RiskTabList, m_LblCurrentProfitPerc, third_risk_column_start, y, third_risk_column_start + narrowest_label_width, y + element_height, "m_LblCurrentProfitPerc", "Reward %")) return false; + if (!LabelCreate(RiskTabList, m_LblCurrentProfitMoney, second_risk_column_start, y, second_risk_column_start + narrow_label_width, y + element_height, "m_LblCurrentProfitMoney", TRANSLATION_LABEL_REWARD + " $")) return false; + if (!LabelCreate(RiskTabList, m_LblCurrentProfitPerc, third_risk_column_start, y, third_risk_column_start + narrowest_label_width, y + element_height, "m_LblCurrentProfitPerc", TRANSLATION_LABEL_REWARD + " %")) return false; y += element_height + v_spacing; @@ -769,13 +771,13 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(RiskTabList, m_LblPotentialRiskMoney, second_risk_column_start, y, second_risk_column_start + narrow_label_width, y + element_height, "m_LblPotentialRiskMoney", "Risk $")) return false; - if (!LabelCreate(RiskTabList, m_LblPotentialRiskPerc, third_risk_column_start, y, third_risk_column_start + narrowest_label_width, y + element_height, "m_LblPotentialRiskPerc", "Risk %")) return false; - if (!LabelCreate(RiskTabList, m_LblPotentialLots, fourth_risk_column_start, y, fourth_risk_column_start + narrowest_label_width, y + element_height, "m_LblPotentialLots", "Lots")) return false; + if (!LabelCreate(RiskTabList, m_LblPotentialRiskMoney, second_risk_column_start, y, second_risk_column_start + narrow_label_width, y + element_height, "m_LblPotentialRiskMoney", TRANSLATION_LABEL_RISK + " $")) return false; + if (!LabelCreate(RiskTabList, m_LblPotentialRiskPerc, third_risk_column_start, y, third_risk_column_start + narrowest_label_width, y + element_height, "m_LblPotentialRiskPerc", TRANSLATION_LABEL_RISK + " %")) return false; + if (!LabelCreate(RiskTabList, m_LblPotentialLots, fourth_risk_column_start, y, fourth_risk_column_start + narrowest_label_width, y + element_height, "m_LblPotentialLots", TRANSLATION_LABEL_LOTS)) return false; y += element_height + v_spacing; - if (!LabelCreate(RiskTabList, m_LblPotentialPortfolio, first_column_start, y, second_risk_column_start, y + element_height, "m_LblPotentialPortfolio", "Potential portfolio:", "Including the position being calculated")) return false; + if (!LabelCreate(RiskTabList, m_LblPotentialPortfolio, first_column_start, y, second_risk_column_start, y + element_height, "m_LblPotentialPortfolio", TRANSLATION_LABEL_POTENTIAL_PORTFOLIO + ":", TRANSLATION_TOOLTIP_POTENTIAL_PORTFOLIO)) return false; if (!EditCreate(RiskTabList, m_EdtPotRiskM, second_risk_column_start, y, second_risk_column_start + normal_edit_width, y + element_height, "m_EdtPotRiskM", "")) return false; m_EdtPotRiskM.ReadOnly(true); m_EdtPotRiskM.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); @@ -788,8 +790,8 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(RiskTabList, m_LblPotentialProfitMoney, second_risk_column_start, y, second_risk_column_start + narrow_edit_width, y + element_height, "m_LblPotentialProfitMoney", "Reward $")) return false; - if (!LabelCreate(RiskTabList, m_LblPotentialProfitPerc, third_risk_column_start, y, third_risk_column_start + narrowest_label_width, y + element_height, "m_LblPotentialProfitPerc", "Reward %")) return false; + if (!LabelCreate(RiskTabList, m_LblPotentialProfitMoney, second_risk_column_start, y, second_risk_column_start + narrow_edit_width, y + element_height, "m_LblPotentialProfitMoney", TRANSLATION_LABEL_REWARD + " $")) return false; + if (!LabelCreate(RiskTabList, m_LblPotentialProfitPerc, third_risk_column_start, y, third_risk_column_start + narrowest_label_width, y + element_height, "m_LblPotentialProfitPerc", TRANSLATION_LABEL_REWARD + " %")) return false; y += element_height + v_spacing; @@ -805,21 +807,21 @@ bool CPositionSizeCalculator::CreateObjects() // Reset y = row_start + element_height + 3 * v_spacing; - if (!LabelCreate(MarginTabList, m_LblPosMargin, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblPosMargin", "Position margin:")) return false; + if (!LabelCreate(MarginTabList, m_LblPosMargin, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblPosMargin", TRANSLATION_LABEL_POSITION_MARGIN + ":")) return false; if (!EditCreate(MarginTabList, m_EdtPosMargin, second_margin_column_start, y, second_margin_column_start + wide_edit_width, y + element_height, "m_EdtPosMargin", "")) return false; m_EdtPosMargin.ReadOnly(true); m_EdtPosMargin.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); y += element_height + v_spacing; - if (!LabelCreate(MarginTabList, m_LblUsedMargin, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblUsedMargin", "Future used margin:")) return false; + if (!LabelCreate(MarginTabList, m_LblUsedMargin, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblUsedMargin", TRANSLATION_LABEL_FUTURE_USED_MARGIN + ":")) return false; if (!EditCreate(MarginTabList, m_EdtUsedMargin, second_margin_column_start, y, second_margin_column_start + wide_edit_width, y + element_height, "m_EdtUsedMargin", " ")) return false; m_EdtUsedMargin.ReadOnly(true); m_EdtUsedMargin.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); y += element_height + v_spacing; - if (!LabelCreate(MarginTabList, m_LblFreeMargin, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblFreeMargin", "Future free margin:")) return false; + if (!LabelCreate(MarginTabList, m_LblFreeMargin, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblFreeMargin", TRANSLATION_LABEL_FUTURE_FREE_MARGIN + ":")) return false; if (!EditCreate(MarginTabList, m_EdtFreeMargin, second_margin_column_start, y, second_margin_column_start + wide_edit_width, y + element_height, "m_EdtFreeMargin", "")) return false; m_EdtFreeMargin.ReadOnly(true); m_EdtFreeMargin.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); @@ -828,18 +830,18 @@ bool CPositionSizeCalculator::CreateObjects() string extra_spaces = ""; if (PanelWidth > 350) extra_spaces = " "; - if (!LabelCreate(MarginTabList, m_LblCustomLeverage, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblCustomLeverage", "Custom leverage = " + extra_spaces + " 1:")) return false; - if (!EditCreate(MarginTabList, m_EdtCustomLeverage, second_margin_column_start, y, second_margin_column_start + leverage_edit_width, y + element_height, "m_CustomLeverage", "")) return false; + if (!LabelCreate(MarginTabList, m_LblCustomLeverage, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblCustomLeverage", TRANSLATION_LABEL_CUSTOM_LEVERAGE + " = " + extra_spaces + " 1:")) return false; + if (!EditCreate(MarginTabList, m_EdtCustomLeverage, second_margin_column_start, y, second_margin_column_start + leverage_edit_width, y + element_height, "m_EdtCustomLeverage", "")) return false; if (!LabelCreate(MarginTabList, m_LblAccLeverage, second_margin_column_start + leverage_edit_width + 2 * h_spacing, y, second_margin_column_start + leverage_edit_width + h_spacing + wide_edit_width, y + element_height, "m_LblAccLeverage", "")) return false; y += element_height + v_spacing; - if (!LabelCreate(MarginTabList, m_LblSymbolLeverage, second_margin_column_start + leverage_edit_width + 2 * h_spacing, y, second_margin_column_start + leverage_edit_width + h_spacing + wide_edit_width, y + element_height, "m_LblSymbolLeverage", "(Symbol = 1:?)")) return false; + if (!LabelCreate(MarginTabList, m_LblSymbolLeverage, second_margin_column_start + leverage_edit_width + 2 * h_spacing, y, second_margin_column_start + leverage_edit_width + h_spacing + wide_edit_width, y + element_height, "m_LblSymbolLeverage", "(" + TRANSLATION_LABEL_SYMBOL + " = 1:?)")) return false; y += element_height + v_spacing; - if (!LabelCreate(MarginTabList, m_LblMaxPositionSizeByMargin, first_column_start, y, first_column_start + wide_label_width, y + element_height, "m_LblMaxPositionSizeByMargin", "Maximum position size by margin:")) return false; - if (!EditCreate(MarginTabList, m_EdtMaxPositionSizeByMargin, max_psc_column_start, y, second_margin_column_start + wide_edit_width, y + element_height, "m_EdtMaxPositionSizeByMargin", "", "In lots")) return false; + if (!LabelCreate(MarginTabList, m_LblMaxPositionSizeByMargin, first_column_start, y, first_column_start + wide_label_width, y + element_height, "m_LblMaxPositionSizeByMargin", TRANSLATION_LABEL_MAX_PS_BY_MARGIN + ":")) return false; + if (!EditCreate(MarginTabList, m_EdtMaxPositionSizeByMargin, max_psc_column_start, y, second_margin_column_start + wide_edit_width, y + element_height, "m_EdtMaxPositionSizeByMargin", "", TRANSLATION_TOOLTIP_MAX_PS_BY_MARGIN)) return false; m_EdtMaxPositionSizeByMargin.ReadOnly(true); m_EdtMaxPositionSizeByMargin.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); @@ -848,26 +850,26 @@ bool CPositionSizeCalculator::CreateObjects() // Reset y = row_start + element_height + 3 * v_spacing; - if (!LabelCreate(SwapsTabList, m_LblSwapsType, first_column_start, y, first_column_start + narrow_edit_width, y + element_height, "m_LblSwapsType", "Type:")) return false; - if (!EditCreate(SwapsTabList, m_EdtSwapsType, first_column_start + narrow_edit_width, y, second_swaps_column_start + swap_type_edit_width, y + element_height, "m_EdtSwapsType", "Unknown")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsType, first_column_start, y, first_column_start + narrow_edit_width, y + element_height, "m_LblSwapsType", TRANSLATION_LABEL_TYPE + ":")) return false; + if (!EditCreate(SwapsTabList, m_EdtSwapsType, first_column_start + narrow_edit_width, y, second_swaps_column_start + swap_type_edit_width, y + element_height, "m_EdtSwapsType", TRANSLATION_LABEL_UNKNOWN)) return false; m_EdtSwapsType.ReadOnly(true); m_EdtSwapsType.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); y += element_height + v_spacing; - if (!LabelCreate(SwapsTabList, m_LblSwapsTripleDay, first_column_start, y, first_column_start + narrow_edit_width, y + element_height, "m_LblSwapsTripleDay", "Triple swap:")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsTripleDay, first_column_start, y, first_column_start + narrow_edit_width, y + element_height, "m_LblSwapsTripleDay", TRANSLATION_LABEL_TRIPLE_SWAP + ":")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsTripleDay, first_column_start + narrow_edit_width, y, second_swaps_column_start + swap_type_edit_width, y + element_height, "m_EdtSwapsTripleDay", "?")) return false; m_EdtSwapsTripleDay.ReadOnly(true); m_EdtSwapsTripleDay.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); y += element_height + v_spacing; - if (!LabelCreate(SwapsTabList, m_LblSwapsLong, second_swaps_column_start, y, second_swaps_column_start + normal_edit_width, y + element_height, "m_LblSwapsLong", "Long")) return false; - if (!LabelCreate(SwapsTabList, m_LblSwapsShort, third_swaps_column_start, y, third_swaps_column_start + normal_edit_width, y + element_height, "m_LblSwapsShort", "Short")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsLong, second_swaps_column_start, y, second_swaps_column_start + normal_edit_width, y + element_height, "m_LblSwapsLong", TRANSLATION_BUTTON_LONG)) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsShort, third_swaps_column_start, y, third_swaps_column_start + normal_edit_width, y + element_height, "m_LblSwapsShort", TRANSLATION_BUTTON_SHORT)) return false; y += element_height + v_spacing; - if (!LabelCreate(SwapsTabList, m_LblSwapsNominal, first_column_start, y, first_column_start + narrowest_label_width, y + element_height, "m_LblSwapsNominal", "Nominal:")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsNominal, first_column_start, y, first_column_start + narrowest_label_width, y + element_height, "m_LblSwapsNominal", TRANSLATION_LABEL_NOMINAL + ":")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsNominalLong, second_swaps_column_start, y, second_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsNominalLong", "?")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsNominalShort, third_swaps_column_start, y, third_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsNominalShort", "?")) return false; m_EdtSwapsNominalLong.ReadOnly(true); @@ -877,10 +879,10 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(SwapsTabList, m_LblSwapsDaily, first_column_start, y, first_column_start + narrowest_label_width, y + element_height, "m_LblSwapsDaily", "Daily:")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsDaily, first_column_start, y, first_column_start + narrowest_label_width, y + element_height, "m_LblSwapsDaily", TRANSLATION_LABEL_DAILY+ ":")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsDailyLongLot, second_swaps_column_start, y, second_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsDailyLongLot", "?")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsDailyShortLot, third_swaps_column_start, y, third_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsDailyShortLot", "?")) return false; - if (!LabelCreate(SwapsTabList, m_LblSwapsPerLotDaily, fourth_swaps_column_start, y, fourth_swaps_column_start + swap_last_label_width, y + element_height, "m_LblSwapsPerLotDaily", "USD per lot")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsPerLotDaily, fourth_swaps_column_start, y, fourth_swaps_column_start + swap_last_label_width, y + element_height, "m_LblSwapsPerLotDaily", "USD " + TRANSLATION_LABEL_PER_LOT)) return false; m_EdtSwapsDailyLongLot.ReadOnly(true); m_EdtSwapsDailyLongLot.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); m_EdtSwapsDailyShortLot.ReadOnly(true); @@ -890,7 +892,7 @@ bool CPositionSizeCalculator::CreateObjects() if (!EditCreate(SwapsTabList, m_EdtSwapsDailyLongPS, second_swaps_column_start, y, second_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsDailyLongPS", "?")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsDailyShortPS, third_swaps_column_start, y, third_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsDailyShortPS", "?")) return false; - if (!LabelCreate(SwapsTabList, m_LblSwapsPerPSDaily, fourth_swaps_column_start, y, fourth_swaps_column_start + swap_last_label_width, y + element_height, "m_LblSwapsPerPSDaily", "USD per PS ()")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsPerPSDaily, fourth_swaps_column_start, y, fourth_swaps_column_start + swap_last_label_width, y + element_height, "m_LblSwapsPerPSDaily", "USD " + TRANSLATION_LABEL_PER_PS + " ()")) return false; m_EdtSwapsDailyLongPS.ReadOnly(true); m_EdtSwapsDailyLongPS.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); m_EdtSwapsDailyShortPS.ReadOnly(true); @@ -898,10 +900,10 @@ bool CPositionSizeCalculator::CreateObjects() y += element_height + v_spacing; - if (!LabelCreate(SwapsTabList, m_LblSwapsYearly, first_column_start, y, first_column_start + narrowest_label_width, y + element_height, "m_LblSwapsYearly", "Yearly:")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsYearly, first_column_start, y, first_column_start + narrowest_label_width, y + element_height, "m_LblSwapsYearly", TRANSLATION_LABEL_YEARLY + ":")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsYearlyLongLot, second_swaps_column_start, y, second_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsYearlyLongLot", "?")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsYearlyShortLot, third_swaps_column_start, y, third_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsYearlyShortLot", "?")) return false; - if (!LabelCreate(SwapsTabList, m_LblSwapsPerLotYearly, fourth_swaps_column_start, y, fourth_swaps_column_start + swap_last_label_width, y + element_height, "m_LblSwapsPerLotYearly", "USD per lot")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsPerLotYearly, fourth_swaps_column_start, y, fourth_swaps_column_start + swap_last_label_width, y + element_height, "m_LblSwapsPerLotYearly", "USD " + TRANSLATION_LABEL_PER_LOT)) return false; m_EdtSwapsYearlyLongLot.ReadOnly(true); m_EdtSwapsYearlyLongLot.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); m_EdtSwapsYearlyShortLot.ReadOnly(true); @@ -911,7 +913,7 @@ bool CPositionSizeCalculator::CreateObjects() if (!EditCreate(SwapsTabList, m_EdtSwapsYearlyLongPS, second_swaps_column_start, y, second_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsYearlyLongPS", "?")) return false; if (!EditCreate(SwapsTabList, m_EdtSwapsYearlyShortPS, third_swaps_column_start, y, third_swaps_column_start + swap_size_edit_width, y + element_height, "m_EdtSwapsYearlyShortPS", "?")) return false; - if (!LabelCreate(SwapsTabList, m_LblSwapsPerPSYearly, fourth_swaps_column_start, y, fourth_swaps_column_start + swap_last_label_width, y + element_height, "m_LblSwapsPerPSYearly", "USD per PS ()")) return false; + if (!LabelCreate(SwapsTabList, m_LblSwapsPerPSYearly, fourth_swaps_column_start, y, fourth_swaps_column_start + swap_last_label_width, y + element_height, "m_LblSwapsPerPSYearly", "USD " + TRANSLATION_LABEL_PER_PS + " ()")) return false; m_EdtSwapsYearlyLongPS.ReadOnly(true); m_EdtSwapsYearlyLongPS.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); m_EdtSwapsYearlyShortPS.ReadOnly(true); @@ -922,53 +924,63 @@ bool CPositionSizeCalculator::CreateObjects() // Reset y = row_start + element_height + 3 * v_spacing; - if (!ButtonCreate(TradingTabList, m_BtnTrade, first_column_start, y, first_column_start + tab_button_width, y + element_height, "m_BtnTrade", "Trade")) return false; - if (!LabelCreate(TradingTabList, m_LblTrailingStop, first_column_start + tab_button_width + v_spacing * 2, y, first_column_start + v_spacing + tab_button_width + normal_edit_width, y + element_height, "m_LblTrailingStop", "Trailing stop:")) return false; + if (!ButtonCreate(TradingTabList, m_BtnTrade, first_column_start, y, first_column_start + tab_button_width, y + element_height, "m_BtnTrade", TRANSLATION_BUTTON_TRADE)) return false; + if (!LabelCreate(TradingTabList, m_LblTrailingStop, first_column_start + tab_button_width + v_spacing * 2, y, first_column_start + v_spacing + tab_button_width + normal_edit_width, y + element_height, "m_LblTrailingStop", TRANSLATION_LABEL_TRAILING_STOP + ":")) return false; if (!EditCreate(TradingTabList, m_EdtTrailingStopPoints, first_column_start + v_spacing * 2 + tab_button_width + normal_edit_width, y, first_column_start + v_spacing * 2 + tab_button_width * 2 + normal_edit_width, y + element_height, "m_EdtTrailingStopPoints", "0")) return false; - if (!LabelCreate(TradingTabList, m_LblBreakEven, first_column_start + v_spacing * 5 + tab_button_width * 2 + normal_edit_width, y, first_column_start + v_spacing * 3 + tab_button_width * 2 + normal_edit_width + narrow_edit_width, y + element_height, "m_LblBreakEven", "Breakeven:")) return false; + if (!LabelCreate(TradingTabList, m_LblBreakEven, first_column_start + v_spacing * 5 + tab_button_width * 2 + normal_edit_width, y, first_column_start + v_spacing * 3 + tab_button_width * 2 + normal_edit_width + narrow_edit_width, y + element_height, "m_LblBreakEven", TRANSLATION_LABEL_BREAKEVEN + ":")) return false; if (!EditCreate(TradingTabList, m_EdtBreakEvenPoints, first_column_start + v_spacing * 4 + tab_button_width * 2 + normal_edit_width + narrow_edit_width, y, first_column_start + v_spacing * 4 + tab_button_width * 3 + normal_edit_width + narrow_edit_width, y + element_height, "m_EdtBreakEvenPoints", "0")) return false; y += element_height + v_spacing; - if (!LabelCreate(TradingTabList, m_LblMagicNumber, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMagicNumber", "Magic number:")) return false; + if (!LabelCreate(TradingTabList, m_LblMagicNumber, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMagicNumber", TRANSLATION_LABEL_MAGIC_NUMBER + ":")) return false; if (!EditCreate(TradingTabList, m_EdtMagicNumber, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMagicNumber", "")) return false; y += element_height + v_spacing; - if (!LabelCreate(TradingTabList, m_LblCommentary, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblCommentary", "Order commentary:")) return false; + if (!LabelCreate(TradingTabList, m_LblCommentary, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblCommentary", TRANSLATION_LABEL_ORDER_COMMENTARY + ":")) return false; if (!EditCreate(TradingTabList, m_EdtCommentary, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtCommentary", "")) return false; - if (!CheckBoxCreate(TradingTabList, m_ChkCommentAutoSuffix, third_trading_column_start, y, third_trading_column_start + narrow_label_width + h_spacing, y + element_height, "m_ChkCommentAutoSuffix", "Auto-suffix")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxNumberOfTrades, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxNumberOfTrades", "Max # of trades:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxNumberOfTrades, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxNumberOfTrades", "", "With a given Magic number")) return false; - if (!CheckBoxCreate(TradingTabList, m_ChkAllSymbols, third_trading_column_start, y, third_trading_column_start + narrow_label_width + h_spacing, y + element_height, "m_ChkAllSymbols", "All symbols", "Count trades on all symbols?")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxPositionSize, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxPositionSize", "Max total volume:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxPositionSize, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxPositionSize", "")) return false; - if (!LabelCreate(TradingTabList, m_LblTradingLots, third_trading_column_start, y, third_trading_column_start + narrow_label_width + h_spacing, y + element_height, "m_LblTradingLots", " lots")) return false; + if (!CheckBoxCreate(TradingTabList, m_ChkCommentAutoSuffix, third_trading_column_start, y, third_trading_column_start + narrow_label_width + h_spacing, y + element_height, "m_ChkCommentAutoSuffix", TRANSLATION_LABEL_ORDER_AUTOSUFFIX, TRANSLATION_TOOLTIP_ORDER_AUTOSUFFIX)) return false; y += element_height + v_spacing; - if (!LabelCreate(TradingTabList, m_LblMaxTotalRisk, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxTotalRisk", "Max total risk, %:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxTotalRisk, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxTotalRisk", "")) return false; - - y += element_height + v_spacing; + if (ShowMaxParametersOnTrading) + { + if (!LabelCreate(TradingTabList, m_LblMaxNumberOfTrades, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxNumberOfTrades", TRANSLATION_LABEL_MAX_NUMBER_OF_TRADES)) return false; + if (!LabelCreate(TradingTabList, m_LblMaxNumberOfTradesTotal, first_column_start + narrow_label_width + element_height - v_spacing * 2, y, multi_tp_column_start + tab_button_width, y + element_height, "m_LblMaxNumberOfTradesTotal", TRANSLATION_LABEL_TOTAL + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxNumberOfTradesTotal, first_column_start + v_spacing * 2 + tab_button_width + normal_edit_width, y, first_column_start + v_spacing * 2 + tab_button_width * 2 + normal_edit_width, y + element_height, "m_EdtMaxNumberOfTradesTotal", "")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxNumberOfTradesPerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 2, y, multi_tp_button_start + leverage_edit_width + v_spacing * 6 + tab_button_width, y + element_height, "m_LblMaxNumberOfTradesPerSymbol", TRANSLATION_LABEL_PER_SYMBOL + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxNumberOfTradesPerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width, y, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width * 2, y + element_height, "m_EdtMaxNumberOfTradesPerSymbol", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMaxPositionSize, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxPositionSize", TRANSLATION_LABEL_MAX_VOLUME)) return false; + if (!LabelCreate(TradingTabList, m_LblMaxPositionSizeTotal, first_column_start + narrow_label_width + element_height - v_spacing * 2, y, multi_tp_column_start + tab_button_width, y + element_height, "m_LblMaxPositionSizeTotal", TRANSLATION_LABEL_TOTAL + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxPositionSizeTotal, first_column_start + v_spacing * 2 + tab_button_width + normal_edit_width, y, first_column_start + v_spacing * 2 + tab_button_width * 2 + normal_edit_width, y + element_height, "m_EdtMaxPositionSizeTotal", "")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxPositionSizePerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 2, y, multi_tp_button_start + leverage_edit_width + v_spacing * 6 + tab_button_width, y + element_height, "m_LblMaxPositionSizePerSymbol", TRANSLATION_LABEL_PER_SYMBOL + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxPositionSizePerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width, y, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width * 2, y + element_height, "m_EdtMaxPositionSizePerSymbol", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMaxRisk, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxRisk", TRANSLATION_LABEL_MAX_RISK + ", %")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxRiskTotal, first_column_start + narrow_label_width + element_height - v_spacing * 2, y, multi_tp_column_start + tab_button_width, y + element_height, "m_LblMaxRiskTotal", TRANSLATION_LABEL_TOTAL + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxRiskTotal, first_column_start + v_spacing * 2 + tab_button_width + normal_edit_width, y, first_column_start + v_spacing * 2 + tab_button_width * 2 + normal_edit_width, y + element_height, "m_EdtMaxRiskTotal", "")) return false; + if (!LabelCreate(TradingTabList, m_LblMaxRiskPerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 2, y, multi_tp_button_start + leverage_edit_width + v_spacing * 6 + tab_button_width, y + element_height, "m_LblMaxRiskPerSymbol", TRANSLATION_LABEL_PER_SYMBOL + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxRiskPerSymbol, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width, y, multi_tp_button_start + leverage_edit_width + v_spacing * 7 + tab_button_width * 2, y + element_height, "m_EdtMaxRiskPerSymbol", "")) return false; + + y += element_height + v_spacing; + } - if (!CheckBoxCreate(TradingTabList, m_ChkDisableTradingWhenLinesAreHidden, first_column_start, y, panel_end, y + element_height, "m_ChkDisableTradingWhenLinesAreHidden", "Disable trading when lines are hidden")) return false; + if (!CheckBoxCreate(TradingTabList, m_ChkDisableTradingWhenLinesAreHidden, first_column_start, y, panel_end + h_spacing, y + element_height, "m_ChkDisableTradingWhenLinesAreHidden", TRANSLATION_CHECKBOX_DISABLE_TRADING_LINES_HIDDEN)) return false; y += element_height + v_spacing; // Need multiple TP targets. if (sets.TakeProfitsNumber > 1) { - if (!LabelCreate(TradingTabList, m_LblTradingTP, multi_tp_column_start, y, multi_tp_column_start + multi_tp_label_width, y + element_height, "m_LblTradingTP", "TP")) return false; - if (!ButtonCreate(TradingTabList, m_BtnTPsInward, multi_tp_button_start, y, multi_tp_button_start + leverage_edit_width, y + element_height, "m_BtnTPsInward", "<<", "Fill additional TPs equidistantly between Entry and Main TP.")) return false; - if (!ButtonCreate(TradingTabList, m_BtnTPsOutward, multi_tp_button_start + leverage_edit_width + v_spacing, y, multi_tp_button_start + 2 * leverage_edit_width + v_spacing, y + element_height, "m_BtnTPsOutward", ">>", "Place additional TPs beyond the Main TP using the same distance.")) return false; - if (!ButtonCreate(TradingTabList, m_BtnTradingTPShare, third_trading_column_start, y, third_trading_column_start + normal_edit_width, y + element_height, "m_BtnTradingTPShare", "Share, %", "Automatically fill the volume shares")) return false; + if (!LabelCreate(TradingTabList, m_LblTradingTP, multi_tp_column_start, y, multi_tp_column_start + multi_tp_label_width, y + element_height, "m_LblTradingTP", TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE)) return false; + if (!ButtonCreate(TradingTabList, m_BtnTPsInward, multi_tp_button_start, y, multi_tp_button_start + leverage_edit_width, y + element_height, "m_BtnTPsInward", "<<", TRANSLATION_TOOLTIP_FILL_INWARD)) return false; + if (!ButtonCreate(TradingTabList, m_BtnTPsOutward, multi_tp_button_start + leverage_edit_width + v_spacing, y, multi_tp_button_start + 2 * leverage_edit_width + v_spacing, y + element_height, "m_BtnTPsOutward", ">>", TRANSLATION_TOOLTIP_FILL_OUTWARD)) return false; + if (!ButtonCreate(TradingTabList, m_BtnTradingTPShare, third_trading_column_start, y, third_trading_column_start + normal_edit_width, y + element_height, "m_BtnTradingTPShare", TRANSLATION_LABEL_SHARE + ", %", TRANSLATION_TOOLTIP_SHARE)) return false; y += element_height + v_spacing; @@ -977,67 +989,73 @@ bool CPositionSizeCalculator::CreateObjects() ArrayResize(TradingTPShareEdits, sets.TakeProfitsNumber); for (int i = 0; i < sets.TakeProfitsNumber; i++) { - if (!LabelCreate(TradingTabList, TradingTPLabels[i], first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblTradingTPLabel" + IntegerToString(i + 1), "Take-profit " + IntegerToString(i + 1))) return false; + if (!LabelCreate(TradingTabList, TradingTPLabels[i], first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblTradingTPLabel" + IntegerToString(i + 1), TRANSLATION_LABEL_TAKEPROFIT + " " + IntegerToString(i + 1))) return false; if (!EditCreate(TradingTabList, TradingTPEdits[i], multi_tp_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtTradingTPEdit" + IntegerToString(i + 1), "")) return false; if (!EditCreate(TradingTabList, TradingTPShareEdits[i], third_trading_column_start, y, third_trading_column_start + leverage_edit_width, y + element_height, "m_EdtTradingTPShareEdit" + IntegerToString(i + 1), "")) return false; y += element_height + v_spacing; } } - if (!LabelCreate(TradingTabList, m_LblTradingPoints, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_LblTradingPoints", "Points", "")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxSlippage, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxSlippage", "Max slippage:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxSlippage, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxSlippage", "")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxSpread, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxSpread", "Max spread:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxSpread, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxSpread", "")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMaxEntrySLDistance, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxEntrySLDistance", "Max Entry/SL distance:")) return false; - if (!EditCreate(TradingTabList, m_EdtMaxEntrySLDistance, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxEntrySLDistance", "")) return false; - - y += element_height + v_spacing; - - if (!LabelCreate(TradingTabList, m_LblMinEntrySLDistance, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMinEntrySLDistance", "Min Entry/SL distance:")) return false; - if (!EditCreate(TradingTabList, m_EdtMinEntrySLDistance, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMinEntrySLDistance", "")) return false; - - y += element_height + v_spacing; - - if (PanelWidth > 350) + if (ShowFusesOnTrading) { - if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPositions, first_column_start, y, second_trading_column_start + 5 * h_spacing, y + element_height, "m_ChkSubtractPositions", "Subtract open positions volume", "The EA will subtract currently open trades' volume from the calculated position size before opening a trade.")) return false; - if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPendingOrders, second_trading_column_start + 6 * h_spacing, y, panel_end, y + element_height, "m_ChkSubtractPendingOrders", "Subtract pending orders volume", "The EA will subtract pending orders' volume from the calculated position size before opening a trade.")) return false; - + if (!LabelCreate(TradingTabList, m_LblTradingPoints, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_LblTradingPoints", TRANSLATION_LABEL_POINTS, "")) return false; + y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyStopLoss, first_column_start, y, second_trading_column_start + 5 * h_spacing, y + element_height, "m_ChkDoNotApplyStopLoss", "Do not apply stop-loss", "The EA won't apply stop-loss to the trade it opens.")) return false; - if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyTakeProfit, second_trading_column_start + 6 * h_spacing, y, panel_end, y + element_height, "m_ChkDoNotApplyTakeProfit", "Do not apply take-profit", "The EA won't apply take-prfoit to the trade it opens.")) return false; - } - else - { - if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPositions, first_column_start, y, panel_end, y + element_height, "m_ChkSubtractPositions", "Subtract open positions volume", "The EA will subtract currently open trades' volume from the calculated position size before opening a trade.")) return false; - + + if (!LabelCreate(TradingTabList, m_LblMaxSlippage, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxSlippage", TRANSLATION_LABEL_MAX_SLIPPAGE + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxSlippage, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxSlippage", "")) return false; + y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPendingOrders, first_column_start, y, panel_end, y + element_height, "m_ChkSubtractPendingOrders", "Subtract pending orders volume", "The EA will subtract pending orders' volume from the calculated position size before opening a trade.")) return false; - + + if (!LabelCreate(TradingTabList, m_LblMaxSpread, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxSpread", TRANSLATION_LABEL_MAX_SPREAD + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxSpread, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxSpread", "")) return false; + y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyStopLoss, first_column_start, y, panel_end, y + element_height, "m_ChkDoNotApplyStopLoss", "Do not apply stop-loss", "The EA won't apply stop-loss to the trade it opens.")) return false; - + + if (!LabelCreate(TradingTabList, m_LblMaxEntrySLDistance, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMaxEntrySLDistance", TRANSLATION_LABEL_MAX_ENTRY_SL_DISTANCE + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMaxEntrySLDistance, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMaxEntrySLDistance", "")) return false; + + y += element_height + v_spacing; + + if (!LabelCreate(TradingTabList, m_LblMinEntrySLDistance, first_column_start, y, first_column_start + normal_label_width, y + element_height, "m_LblMinEntrySLDistance", TRANSLATION_LABEL_MIN_ENTRY_SL_DISTANCE + ":")) return false; + if (!EditCreate(TradingTabList, m_EdtMinEntrySLDistance, second_trading_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, "m_EdtMinEntrySLDistance", "")) return false; + y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyTakeProfit, first_column_start, y, panel_end, y + element_height, "m_ChkDoNotApplyTakeProfit", "Do not apply take-profit", "The EA won't apply take-prfoit to the trade it opens.")) return false; } - y += element_height + v_spacing; - - if (!CheckBoxCreate(TradingTabList, m_ChkAskForConfirmation, first_column_start, y, second_trading_column_start + 5 * h_spacing, y + element_height, "m_ChkAskForConfirmation", "Ask for confirmation", "The EA will ask for confirmation before opening a trade.")) return false; + if (ShowCheckboxesOnTrading) + { + if (PanelWidth > 350) + { + if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPositions, first_column_start, y, second_trading_column_start + 5 * h_spacing, y + element_height, "m_ChkSubtractPositions", TRANSLATION_CHECKBOX_SUBTRACT_OPEN_POSITIONS_VOLUME, TRANSLATION_TOOLTIP_SUBTRACT_OPEN_POSITIONS_VOLUME)) return false; + if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPendingOrders, second_trading_column_start + 6 * h_spacing, y, panel_end, y + element_height, "m_ChkSubtractPendingOrders", TRANSLATION_CHECKBOX_SUBTRACT_PENDING_ORDERS_VOLUME, TRANSLATION_TOOLTIP_SUBTRACT_PENDING_ORDERS_VOLUME)) return false; + + y += element_height + v_spacing; + + if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyStopLoss, first_column_start, y, second_trading_column_start + 5 * h_spacing, y + element_height, "m_ChkDoNotApplyStopLoss", TRANSLATION_CHECKBOX_DO_NOT_APPLY_STOPLOSS, TRANSLATION_TOOLTIP_DO_NOT_APPLY_STOPLOSS)) return false; + if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyTakeProfit, second_trading_column_start + 6 * h_spacing, y, panel_end, y + element_height, "m_ChkDoNotApplyTakeProfit", TRANSLATION_CHECKBOX_DO_NOT_APPLY_TAKEPROFIT, TRANSLATION_TOOLTIP_DO_NOT_APPLY_TAKEPROFIT)) return false; + } + else + { + if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPositions, first_column_start, y, panel_end, y + element_height, "m_ChkSubtractPositions", TRANSLATION_CHECKBOX_SUBTRACT_OPEN_POSITIONS_VOLUME, TRANSLATION_TOOLTIP_SUBTRACT_OPEN_POSITIONS_VOLUME)) return false; + + y += element_height + v_spacing; + + if (!CheckBoxCreate(TradingTabList, m_ChkSubtractPendingOrders, first_column_start, y, panel_end, y + element_height, "m_ChkSubtractPendingOrders", TRANSLATION_CHECKBOX_SUBTRACT_PENDING_ORDERS_VOLUME, TRANSLATION_TOOLTIP_SUBTRACT_PENDING_ORDERS_VOLUME)) return false; + + y += element_height + v_spacing; + + if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyStopLoss, first_column_start, y, panel_end, y + element_height, "m_ChkDoNotApplyStopLoss", TRANSLATION_CHECKBOX_DO_NOT_APPLY_STOPLOSS, TRANSLATION_TOOLTIP_DO_NOT_APPLY_STOPLOSS)) return false; + + y += element_height + v_spacing; + + if (!CheckBoxCreate(TradingTabList, m_ChkDoNotApplyTakeProfit, first_column_start, y, panel_end, y + element_height, "m_ChkDoNotApplyTakeProfit", TRANSLATION_CHECKBOX_DO_NOT_APPLY_TAKEPROFIT, TRANSLATION_TOOLTIP_DO_NOT_APPLY_TAKEPROFIT)) return false; + } + + y += element_height + v_spacing; + } + + if (!CheckBoxCreate(TradingTabList, m_ChkAskForConfirmation, first_column_start, y, panel_end, y + element_height, "m_ChkAskForConfirmation", TRANSLATION_CHECKBOX_ASK_FOR_CONFIRMATION, TRANSLATION_TOOLTIP_ASK_FOR_CONFIRMATION)) return false; InitObjects(); @@ -1109,16 +1127,24 @@ bool CPositionSizeCalculator::InitObjects() if (!TradingTPShareEdits[i].TextAlign(align)) return false; } } - if (!m_EdtMaxSlippage.TextAlign(align)) return false; - if (!m_EdtMaxSpread.TextAlign(align)) return false; - if (!m_EdtMaxEntrySLDistance.TextAlign(align)) return false; - if (!m_EdtMinEntrySLDistance.TextAlign(align)) return false; - if (!m_EdtMaxPositionSize.TextAlign(align)) return false; + if (ShowFusesOnTrading) + { + if (!m_EdtMaxSlippage.TextAlign(align)) return false; + if (!m_EdtMaxSpread.TextAlign(align)) return false; + if (!m_EdtMaxEntrySLDistance.TextAlign(align)) return false; + if (!m_EdtMinEntrySLDistance.TextAlign(align)) return false; + } if (!m_EdtTrailingStopPoints.TextAlign(align)) return false; if (!m_EdtBreakEvenPoints.TextAlign(align)) return false; - if (!m_EdtMaxNumberOfTrades.TextAlign(align)) return false; - if (!m_EdtMaxTotalRisk.TextAlign(align)) return false; - + if (ShowMaxParametersOnTrading) + { + if (!m_EdtMaxNumberOfTradesTotal.TextAlign(align)) return false; + if (!m_EdtMaxNumberOfTradesPerSymbol.TextAlign(align)) return false; + if (!m_EdtMaxPositionSizeTotal.TextAlign(align)) return false; + if (!m_EdtMaxPositionSizePerSymbol.TextAlign(align)) return false; + if (!m_EdtMaxRiskTotal.TextAlign(align)) return false; + if (!m_EdtMaxRiskPerSymbol.TextAlign(align)) return false; + } if (sets.TPLockedOnSL) m_BtnTakeProfit.ColorBackground(CONTROLS_BUTTON_COLOR_ENABLE); else m_BtnTakeProfit.ColorBackground(CONTROLS_BUTTON_COLOR_BG); @@ -1142,24 +1168,24 @@ bool CPositionSizeCalculator::InitObjects() { if (!TPDistanceInPoints) { - if (!m_BtnTakeProfit.Text("TP x " + DoubleToString(TP_Multiplier, CountDecimalPlaces(TP_Multiplier)) + ":")) return false; + if (!m_BtnTakeProfit.Text(TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE + " x " + DoubleToString(TP_Multiplier, CountDecimalPlaces(TP_Multiplier)) + ":")) return false; } - else if (!m_BtnTakeProfit.Text("TP x " + DoubleToString(TP_Multiplier, CountDecimalPlaces(TP_Multiplier)) + ":")) return false; + else if (!m_BtnTakeProfit.Text(TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE + " x " + DoubleToString(TP_Multiplier, CountDecimalPlaces(TP_Multiplier)) + ":")) return false; } if (sets.EntryType == Pending) { - if (!m_BtnOrderType.Text("Pending")) return false; + if (!m_BtnOrderType.Text(TRANSLATION_BUTTON_ORDER_TYPE_PENDING)) return false; } else if (sets.EntryType == Instant) { - if (!m_BtnOrderType.Text("Instant")) return false; + if (!m_BtnOrderType.Text(TRANSLATION_BUTTON_ORDER_TYPE_INSTANT)) return false; m_EdtEntryLevel.ReadOnly(true); m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); } else if (sets.EntryType == StopLimit) { - if (!m_BtnOrderType.Text("Stop Limit")) return false; + if (!m_BtnOrderType.Text(TRANSLATION_BUTTON_ORDER_TYPE_STOPLIMIT)) return false; } // Hide Stop Limit fields. @@ -1178,7 +1204,7 @@ bool CPositionSizeCalculator::InitObjects() { default: case Balance: - if (!m_BtnAccount.Text("Account balance")) return false; + if (!m_BtnAccount.Text(TRANSLATION_BUTTON_ACCOUNT_BALANCE)) return false; // Custom balance. if (CustomBalance > 0) acc_val = CustomBalance; else acc_val = AccountInfoDouble(ACCOUNT_BALANCE); @@ -1187,14 +1213,14 @@ bool CPositionSizeCalculator::InitObjects() m_EdtAccount.ColorBackground(CONTROLS_EDIT_COLOR_ENABLE); break; case Equity: - if (!m_BtnAccount.Text("Account equity")) return false; + if (!m_BtnAccount.Text(TRANSLATION_BUTTON_ACCOUNT_EQUITY)) return false; acc_val = AccountInfoDouble(ACCOUNT_EQUITY); // Account balance uneditable. m_EdtAccount.ReadOnly(true); m_EdtAccount.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); break; case Balance_minus_Risk: - if (!m_BtnAccount.Text("Balance - CPR")) return false; + if (!m_BtnAccount.Text(TRANSLATION_BUTTON_BALANCE_MINUS_CPR)) return false; // Custom balance. if (CustomBalance > 0) acc_val = CustomBalance; else acc_val = AccountInfoDouble(ACCOUNT_BALANCE); @@ -1248,7 +1274,7 @@ bool CPositionSizeCalculator::InitObjects() if (!m_EdtATRMultiplierTP.Text(DoubleToString(sets.ATRMultiplierTP, 2))) return false; if (!m_ChkSpreadAdjustmentTP.Checked(sets.SpreadAdjustmentTP)) return false; if (sets.ATRTimeframe != PERIOD_CURRENT) m_BtnATRTimeframe.Text(EnumToString(sets.ATRTimeframe)); - else m_BtnATRTimeframe.Text("CURRENT"); + else m_BtnATRTimeframe.Text(TRANSLATION_BUTTON_ATR_PERIOD_CURRENT); } if (!m_ChkCountPendings.Checked(sets.CountPendingOrders)) return false; @@ -1276,18 +1302,30 @@ bool CPositionSizeCalculator::InitObjects() if (!m_EdtMagicNumber.Text(IntegerToString(sets.MagicNumber))) return false; if (!m_EdtCommentary.Text(sets.Commentary)) return false; if (!m_ChkCommentAutoSuffix.Checked(sets.CommentAutoSuffix)) return false; - if (!m_EdtMaxNumberOfTrades.Text(IntegerToString(sets.MaxNumberOfTrades))) return false; - if (!m_EdtMaxTotalRisk.Text(DoubleToString(sets.MaxTotalRisk, 2))) return false; - if (!m_ChkAllSymbols.Checked(sets.AllSymbols)) return false; + if (ShowMaxParametersOnTrading) + { + if (!m_EdtMaxNumberOfTradesTotal.Text(IntegerToString(sets.MaxNumberOfTradesTotal))) return false; + if (!m_EdtMaxNumberOfTradesPerSymbol.Text(IntegerToString(sets.MaxNumberOfTradesPerSymbol))) return false; + if (!m_EdtMaxPositionSizeTotal.Text(DoubleToString(sets.MaxPositionSizeTotal, 2))) return false; + if (!m_EdtMaxPositionSizePerSymbol.Text(DoubleToString(sets.MaxPositionSizeTotal, 2))) return false; + if (!m_EdtMaxRiskTotal.Text(DoubleToString(sets.MaxRiskTotal, 2))) return false; + if (!m_EdtMaxRiskPerSymbol.Text(DoubleToString(sets.MaxRiskPerSymbol, 2))) return false; + } if (!m_ChkDisableTradingWhenLinesAreHidden.Checked(sets.DisableTradingWhenLinesAreHidden)) return false; - if (!m_EdtMaxSlippage.Text(IntegerToString(sets.MaxSlippage))) return false; - if (!m_EdtMaxSpread.Text(IntegerToString(sets.MaxSpread))) return false; - if (!m_EdtMaxEntrySLDistance.Text(IntegerToString(sets.MaxEntrySLDistance))) return false; - if (!m_EdtMinEntrySLDistance.Text(IntegerToString(sets.MinEntrySLDistance))) return false; - if (!m_ChkSubtractPositions.Checked(sets.SubtractPositions)) return false; - if (!m_ChkSubtractPendingOrders.Checked(sets.SubtractPendingOrders)) return false; - if (!m_ChkDoNotApplyStopLoss.Checked(sets.DoNotApplyStopLoss)) return false; - if (!m_ChkDoNotApplyTakeProfit.Checked(sets.DoNotApplyTakeProfit)) return false; + if (ShowFusesOnTrading) + { + if (!m_EdtMaxSlippage.Text(IntegerToString(sets.MaxSlippage))) return false; + if (!m_EdtMaxSpread.Text(IntegerToString(sets.MaxSpread))) return false; + if (!m_EdtMaxEntrySLDistance.Text(IntegerToString(sets.MaxEntrySLDistance))) return false; + if (!m_EdtMinEntrySLDistance.Text(IntegerToString(sets.MinEntrySLDistance))) return false; + } + if (ShowCheckboxesOnTrading) + { + if (!m_ChkSubtractPositions.Checked(sets.SubtractPositions)) return false; + if (!m_ChkSubtractPendingOrders.Checked(sets.SubtractPendingOrders)) return false; + if (!m_ChkDoNotApplyStopLoss.Checked(sets.DoNotApplyStopLoss)) return false; + if (!m_ChkDoNotApplyTakeProfit.Checked(sets.DoNotApplyTakeProfit)) return false; + } if (!m_ChkAskForConfirmation.Checked(sets.AskForConfirmation)) return false; MoveAndResize(); @@ -1445,20 +1483,21 @@ bool CPositionSizeCalculator::DisplayValues() //=== Spread if (ShowSpread == Points) { - if (!Caption(PanelCaption + " Spread: " + IntegerToString(SymbolInfoInteger(Symbol(), SYMBOL_SPREAD)))) return false; + if (!Caption(PanelCaption + " " + TRANSLATION_LABEL_SPREAD + ": " + IntegerToString(SymbolInfoInteger(Symbol(), SYMBOL_SPREAD)))) return false; } else if (ShowSpread == Ratio) // Spread / SL ratio in percentage. { double SL; if (SLDistanceInPoints) SL = sets.StopLoss * _Point; else SL = MathAbs(sets.StopLossLevel - sets.EntryLevel); - if (SL != 0) if (!Caption(PanelCaption + " Spread: " + DoubleToString((SymbolInfoInteger(Symbol(), SYMBOL_SPREAD) * _Point / SL) * 100, 2) + "%")) return false; + if (SL != 0) if (!Caption(PanelCaption + " " + TRANSLATION_LABEL_SPREAD + ": " + DoubleToString((SymbolInfoInteger(Symbol(), SYMBOL_SPREAD) * _Point / SL) * 100, 2) + "%")) return false; } else if (!Caption(PanelCaption)) return false; //=== Levels /* Entry Level */ if (!m_EdtEntryLevel.Text(DoubleToString(sets.EntryLevel, _Digits))) return false; - if (!m_BtnEntry.Text(EnumToString(sets.TradeDirection))) return false; + if (sets.TradeDirection == Long) m_BtnEntry.Text(TRANSLATION_BUTTON_LONG); + else if (sets.TradeDirection == Short) m_BtnEntry.Text(TRANSLATION_BUTTON_SHORT); /* Entry Warning */ if (!m_LblEntryWarning.Text(WarningEntry)) return false; /* Stop-Loss */ if (!SLDistanceInPoints) @@ -1503,6 +1542,24 @@ bool CPositionSizeCalculator::DisplayValues() /* StopPrice Warning */ if (!m_LblStopPriceWarning.Text(WarningSP)) return false; } + /* Order type */ if (sets.EntryType == Instant) + { + m_BtnOrderType.Text(TRANSLATION_BUTTON_ORDER_TYPE_INSTANT); + m_EdtEntryLevel.ReadOnly(true); + m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); + } + else if (sets.EntryType == Pending) + { + m_BtnOrderType.Text(TRANSLATION_BUTTON_ORDER_TYPE_PENDING); + m_EdtEntryLevel.ReadOnly(false); + m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_ENABLE); + } + else if (sets.EntryType == StopLimit) + { + m_BtnOrderType.Text(TRANSLATION_BUTTON_ORDER_TYPE_STOPLIMIT); + m_EdtEntryLevel.ReadOnly(false); + m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_ENABLE); + } /* Account Value */ if (!HideAccSize) if (!m_EdtAccount.Text(FormatDouble(DoubleToString(AccSize, AccountCurrencyDigits), AccountCurrencyDigits))) return false; /* Account Asterisk */ @@ -1515,8 +1572,8 @@ bool CPositionSizeCalculator::DisplayValues() case Balance_minus_Risk: if (sets.CustomBalance > 0) { - m_LblAdditionalFundsAsterisk.Show(); - ObjectSetString(ChartID(), m_name + "m_LblAdditionalFundsAsterisk", OBJPROP_TOOLTIP, "Custom balance set"); + if (!m_minimized) m_LblAdditionalFundsAsterisk.Show(); + ObjectSetString(ChartID(), m_name + "m_LblAdditionalFundsAsterisk", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_CUSTOM); } else { @@ -1531,10 +1588,10 @@ bool CPositionSizeCalculator::DisplayValues() { if (AdditionalFunds != 0) { - m_LblAdditionalFundsAsterisk.Show(); + if (!m_minimized) m_LblAdditionalFundsAsterisk.Show(); string tooltip = ""; - if (AdditionalFunds > 0) tooltip = "+" + DoubleToString(AdditionalFunds, 2) + " additional funds"; - else if (AdditionalFunds < 0) tooltip = DoubleToString(-AdditionalFunds, 2) + " funds subtracted"; + if (AdditionalFunds > 0) tooltip = "+" + DoubleToString(AdditionalFunds, 2) + " " + TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_ADD; + else if (AdditionalFunds < 0) tooltip = DoubleToString(-AdditionalFunds, 2) + " " + TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_SUB; ObjectSetString(ChartID(), m_name + "m_LblAdditionalFundsAsterisk", OBJPROP_TOOLTIP, tooltip); } @@ -1543,11 +1600,11 @@ bool CPositionSizeCalculator::DisplayValues() /* Lines */ if (sets.ShowLines) { - if (!m_BtnLines.Text("Hide lines")) return false; + if (!m_BtnLines.Text(TRANSLATION_BUTTON_HIDE_LINES)) return false; } else { - if (!m_BtnLines.Text("Show lines")) return false; + if (!m_BtnLines.Text(TRANSLATION_BUTTON_SHOW_LINES)) return false; } //=== ATR SL and TP @@ -1556,12 +1613,12 @@ bool CPositionSizeCalculator::DisplayValues() double buf[1] = {0}; if (ATR_handle != INVALID_HANDLE) CopyBuffer(ATR_handle, 0, (int)ATRCandle, 1, buf); double atr = buf[0]; - m_LblATRValue.Text("ATR = " + DoubleToString(atr, _Digits)); + m_LblATRValue.Text(TRANSLATION_LABEL_ATR_VALUE + " = " + DoubleToString(atr, _Digits)); } //=== Commission, risk, position size /* Commission size*/ m_EdtCommissionSize.Text(DoubleToString(sets.CommissionPerLot, CommissionDecimals)); /* Risk In */ if (!m_EdtRiskPIn.Text(FormatDouble(DoubleToString(DisplayRisk, 2)))) return false; - /* Risk currency */ if (StringLen(AccountCurrency) > 0) if (!m_LblRiskM.Text("Risk, " + AccountCurrency + ":")) return false; + /* Risk currency */ if (StringLen(AccountCurrency) > 0) if (!m_LblRiskM.Text(TRANSLATION_LABEL_RISK + ", " + AccountCurrency + ":")) return false; /* Risk Money In */ if (!m_EdtRiskMIn.Text(FormatDouble(DoubleToString(RiskMoney, AccountCurrencyDigits), AccountCurrencyDigits))) return false; /* Risk Money Out */ if (!m_EdtRiskMRes.Text(FormatDouble(DoubleToString(OutputRiskMoney), AccountCurrencyDigits))) return false; if (OutputRiskMoney != 0) @@ -1573,11 +1630,11 @@ bool CPositionSizeCalculator::DisplayValues() else if (!m_EdtRiskPRes.Text("100")) return false; } else if (!m_EdtRiskPRes.Text("0")) return false; - /* Reward currency*/ if (StringLen(AccountCurrency) > 0) if (!m_LblReward.Text("Reward, " + AccountCurrency + ":")) return false; + /* Reward currency*/ if (StringLen(AccountCurrency) > 0) if (!m_LblReward.Text(TRANSLATION_LABEL_REWARD + ", " + AccountCurrency + ":")) return false; /* Reward 1 */ if (!m_EdtReward1.Text(FormatDouble(InputReward, AccountCurrencyDigits))) return false; /* Reward 2 */ if (!m_EdtReward2.Text(FormatDouble(DoubleToString(OutputReward, AccountCurrencyDigits), AccountCurrencyDigits))) return false; /* Risk/Reward 1 */ if (!m_EdtRR1.Text(InputRR)) return false; - if (InputRR == "Invalid TP") m_EdtRR1.Color(clrRed); + if (InputRR == TRANSLATION_LABEL_WARNING_INVALID_TP) m_EdtRR1.Color(clrRed); else m_EdtRR1.Color(m_EdtTP.Color()); if (StringToDouble(m_EdtTP.Text()) != 0) { @@ -1585,32 +1642,32 @@ bool CPositionSizeCalculator::DisplayValues() else if (m_EdtRR2.IsVisible()) m_EdtRR1.Show(); } /* Risk/Reward 2 */ if (!m_EdtRR2.Text(OutputRR)) return false; - if (OutputRR == "Invalid TP") m_EdtRR2.Color(clrRed); + if (OutputRR == TRANSLATION_LABEL_WARNING_INVALID_TP) m_EdtRR2.Color(clrRed); else m_EdtRR2.Color(m_EdtTP.Color()); - /* Position size */ if (!PosSizeEditing) if (!m_EdtPosSize.Text(FormatDouble(DoubleToString(OutputPositionSize, LotStep_digits), LotStep_digits))) return false; + /* Position size */ if (!m_EdtPosSize.Text(FormatDouble(DoubleToString(OutputPositionSize, LotStep_digits), LotStep_digits))) return false; if (OutputPositionSize > OutputMaxPositionSize) { m_EdtPosSize.Color(clrRed); // Calculated position size is greater than maximum position size by margin. - ObjectSetString(ChartID(), m_name + "m_EdtPosSize", OBJPROP_TOOLTIP, "Greater than maximum position size by margin!"); + ObjectSetString(ChartID(), m_name + "m_EdtPosSize", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_WARNING_PS); } else { m_EdtPosSize.Color(m_EdtTP.Color()); - ObjectSetString(ChartID(), m_name + "m_EdtPosSize", OBJPROP_TOOLTIP, "In lots"); + ObjectSetString(ChartID(), m_name + "m_EdtPosSize", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_MAX_PS_BY_MARGIN); } /* Point value */ if (ShowPointValue) { - if (StringLen(AccountCurrency) > 0) if (!m_LblPointValue.Text("Point value, " + AccountCurrency + ":")) return false; + if (StringLen(AccountCurrency) > 0) if (!m_LblPointValue.Text(TRANSLATION_LABEL_POINT_VALUE + ", " + AccountCurrency + ":")) return false; if (!m_EdtPointValue.Text(OutputPointValue)) return false; } //=== Show/hide risk /* Money label */ if (AccountCurrency != "") { - if (!m_LblCurrentRiskMoney.Text("Risk " + AccountCurrency)) return false; - if (!m_LblCurrentProfitMoney.Text("Reward " + AccountCurrency)) return false; - if (!m_LblPotentialRiskMoney.Text("Risk " + AccountCurrency)) return false; - if (!m_LblPotentialProfitMoney.Text("Reward " + AccountCurrency)) return false; + if (!m_LblCurrentRiskMoney.Text(TRANSLATION_LABEL_RISK + " " + AccountCurrency)) return false; + if (!m_LblCurrentProfitMoney.Text(TRANSLATION_LABEL_REWARD + " " + AccountCurrency)) return false; + if (!m_LblPotentialRiskMoney.Text(TRANSLATION_LABEL_RISK + " " + AccountCurrency)) return false; + if (!m_LblPotentialProfitMoney.Text(TRANSLATION_LABEL_REWARD + " " + AccountCurrency)) return false; } /* Current Portfolio Risk $ */ if (!m_EdtCurRiskM.Text(PLM)) return false; /* Current Portfolio Risk % */ if (!m_EdtCurRiskP.Text(CPR)) return false; @@ -1627,7 +1684,7 @@ bool CPositionSizeCalculator::DisplayValues() /* Position Margin */ if (!m_EdtPosMargin.Text(FormatDouble(DoubleToString(PositionMargin, AccountCurrencyDigits), AccountCurrencyDigits))) return false; if (MarginInUnconvertedMarginCurrency) { - m_LblPosMargin.Text("Position margin, " + MarginCurrency + ":"); + m_LblPosMargin.Text(TRANSLATION_LABEL_POSITION_MARGIN + ", " + MarginCurrency + ":"); m_EdtUsedMargin.Text("???"); m_EdtFreeMargin.Text("???"); SymbolLeverage = 0; @@ -1639,8 +1696,8 @@ bool CPositionSizeCalculator::DisplayValues() } /* Custom Leverage */ if (!m_EdtCustomLeverage.Text(DoubleToString(sets.CustomLeverage, CustomLeverageDecimals))) return false; string acc_lev = IntegerToString(AccountInfoInteger(ACCOUNT_LEVERAGE)); - /* Account Leverage */ if (StringLen(acc_lev) > 0) if (!m_LblAccLeverage.Text("(Default = 1:" + acc_lev + ")")) return false; - /* Symbol Leverage */ if (SymbolLeverage) if (!m_LblSymbolLeverage.Text("(Symbol = 1:" + DoubleToString(SymbolLeverage, SymbolLeverageDecimals) + ")")) return false; + /* Account Leverage */ if (StringLen(acc_lev) > 0) if (!m_LblAccLeverage.Text("(" + TRANSLATION_LABEL_DEFAULT + " = 1:" + acc_lev + ")")) return false; + /* Symbol Leverage */ if (SymbolLeverage) if (!m_LblSymbolLeverage.Text("(" + TRANSLATION_LABEL_SYMBOL + " = 1:" + DoubleToString(SymbolLeverage, SymbolLeverageDecimals) + ")")) return false; /* Max Position size */ if (!m_EdtMaxPositionSizeByMargin.Text(FormatDouble(DoubleToString(OutputMaxPositionSize, LotStep_digits), LotStep_digits))) return false; if (!StopOut) // Black { @@ -1681,16 +1738,21 @@ bool CPositionSizeCalculator::DisplayValues() if (sets.TakeProfitsNumber > 1) { sets.TP[0] = sets.TakeProfitLevel; // Always the main TP. + TradingTPEdits[0].Text(DoubleToString(sets.TP[0], _Digits)); if (AdditionalTPLineMoved) { - for (int i = 0; i < sets.TakeProfitsNumber; i++) + for (int i = 1; i < sets.TakeProfitsNumber; i++) { if (!TradingTPEdits[i].Text(DoubleToString(sets.TP[i], _Digits))) return false; } AdditionalTPLineMoved = false; } } - /* Maximum Position Size */ if (!m_EdtMaxPositionSize.Text(DoubleToString(sets.MaxPositionSize, LotStep_digits))) return false; + if (ShowMaxParametersOnTrading) + { + /* Maximum Position Size */ if (!m_EdtMaxPositionSizeTotal.Text(DoubleToString(sets.MaxPositionSizeTotal, LotStep_digits))) return false; + if (!m_EdtMaxPositionSizePerSymbol.Text(DoubleToString(sets.MaxPositionSizePerSymbol, LotStep_digits))) return false; + } return true; } @@ -1782,15 +1844,15 @@ void CPositionSizeCalculator::CalculateSettingsBasedOnLines() double read_value; if ((sets.ATRMultiplierSL == 0) || (!ShowATROptions)) { - if (ObjectGetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, 0, read_value)) sets.StopLossLevel = read_value; // Rewrite value only if line exists. + if (ObjectGetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, 0, read_value)) sets.StopLossLevel = NormalizeDouble(read_value, _Digits); // Rewrite value only if line exists. } if ((sets.ATRMultiplierTP == 0) || (!ShowATROptions)) { - if (ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, 0, read_value)) sets.TakeProfitLevel = read_value; // Rewrite value only if line exists. + if (ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, 0, read_value)) sets.TakeProfitLevel = NormalizeDouble(read_value, _Digits); // Rewrite value only if line exists. } for (int i = 1; i < sets.TakeProfitsNumber; i++) { - if (ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, 0, read_value)) sets.TP[i] = read_value; // Rewrite value only if line exists. + if (ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, 0, read_value)) sets.TP[i] = NormalizeDouble(read_value, _Digits); // Rewrite value only if line exists. } // Check and adjust for TickSize granularity. @@ -1799,7 +1861,7 @@ void CPositionSizeCalculator::CalculateSettingsBasedOnLines() sets.StopLossLevel = NormalizeDouble(MathRound(sets.StopLossLevel / TickSize) * TickSize, _Digits); if ((!StopLossLineIsBeingMoved) || (sets.ATRMultiplierSL == 0) || (!ShowATROptions)) ObjectSetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, sets.StopLossLevel); sets.TakeProfitLevel = NormalizeDouble(MathRound(sets.TakeProfitLevel / TickSize) * TickSize, _Digits); - if ((!TakeProfitLineIsBeingMoved) || (sets.ATRMultiplierTP == 0) || (!ShowATROptions)) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, sets.TakeProfitLevel); + if ((!TakeProfitLineIsBeingMoved[0]) || (sets.ATRMultiplierTP == 0) || (!ShowATROptions)) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, sets.TakeProfitLevel); if (sets.TakeProfitsNumber > 1) { for (int i = 0; i < sets.TakeProfitsNumber; i++) @@ -1854,7 +1916,7 @@ void CPositionSizeCalculator::CalculateSettingsBasedOnLines() { if (sets.TradeDirection == Long) sets.TakeProfitLevel = sets.EntryLevel + sets.TakeProfit * _Point; else sets.TakeProfitLevel = sets.EntryLevel - sets.TakeProfit * _Point; - if (!TakeProfitLineIsBeingMoved) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, sets.TakeProfitLevel); + if (!TakeProfitLineIsBeingMoved[0]) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, sets.TakeProfitLevel); } // Additional take-profits. if (sets.TakeProfitsNumber > 1) @@ -1863,10 +1925,10 @@ void CPositionSizeCalculator::CalculateSettingsBasedOnLines() { if (sets.TP[i] != 0) // With zero points TP, keep the TP lines at zero level - as with the main TP level. { - if (sets.TradeDirection == Long) sets.TP[i] = sets.EntryLevel + StringToDouble(AdditionalTPEdits[i - 1].Text()) * _Point; - else sets.TP[i] = sets.EntryLevel - StringToDouble(AdditionalTPEdits[i - 1].Text()) * _Point; + if (sets.TradeDirection == Long) sets.TP[i] = NormalizeDouble(sets.EntryLevel + StringToDouble(AdditionalTPEdits[i - 1].Text()) * _Point, _Digits); + else sets.TP[i] = NormalizeDouble(sets.EntryLevel - StringToDouble(AdditionalTPEdits[i - 1].Text()) * _Point, _Digits); } - if (!TakeProfitLineIsBeingMoved) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, sets.TP[i]); + if (!TakeProfitLineIsBeingMoved[i]) ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, sets.TP[i]); } } } @@ -1895,6 +1957,7 @@ void CPositionSizeCalculator::RefreshValues() CalculateSettingsBasedOnLines(); RecalculatePositionSize(); + DisplayValues(); if ((sets.SelectedTab == MainTab) && (((!m_LblStopPrice.IsVisible()) && (sets.EntryType == StopLimit)) || ((m_LblStopPrice.IsVisible()) && (sets.EntryType != StopLimit))) && (Height() > 26)) @@ -1918,6 +1981,8 @@ void CPositionSizeCalculator::RefreshValues() MoveAndResize(); } + DoBreakEven(); + LastRecalculationTime = GetTickCount(); } @@ -2018,12 +2083,7 @@ void CPositionSizeCalculator::ShowMain() m_EdtRiskMRes.Show(); if (sets.TakeProfitLevel != 0) { - m_LblReward.Show(); - m_EdtReward1.Show(); - m_EdtReward2.Show(); - m_LblRR.Show(); - if (InputRR != "") m_EdtRR1.Show(); - m_EdtRR2.Show(); + ShowTPRelatedEdits(); } m_LblPosSize.Show(); if (ShowMaxPSButton) m_BtnMaxPS.Show(); @@ -2218,12 +2278,7 @@ void CPositionSizeCalculator::ProcessTPChange(const bool tp_button_click) { if (sets.SelectedTab == MainTab) { - m_LblRR.Show(); - if (InputRR != "") m_EdtRR1.Show(); - m_EdtRR2.Show(); - m_LblReward.Show(); - m_EdtReward1.Show(); - m_EdtReward2.Show(); + ShowTPRelatedEdits(); } } if (sets.ShowLines) @@ -2370,30 +2425,29 @@ void CPositionSizeCalculator::OnClickBtnOrderType() { sets.WasSelectedEntryLine = ObjectGetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTED); sets.WasSelectedStopPriceLine = ObjectGetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTED); - if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTABLE, false); ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTED, false); - if (!m_EdtEntryLevel.ReadOnly(true)) return; - if (!m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE)) return; - m_BtnOrderType.Text("Instant"); m_BtnEntryIncrease.Hide(); m_BtnEntryDecrease.Hide(); m_BtnStopPriceIncrease.Hide(); m_BtnStopPriceDecrease.Hide(); ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); } else if (sets.EntryType == Pending) { ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTABLE, true); if ((sets.WasSelectedEntryLine) || (DefaultLinesSelected)) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTED, true); - if (!m_EdtEntryLevel.ReadOnly(false)) return; - if (!m_EdtEntryLevel.ColorBackground(CONTROLS_EDIT_COLOR_ENABLE)) return; - m_BtnOrderType.Text("Pending"); - m_BtnEntryIncrease.Show(); - m_BtnEntryDecrease.Show(); + if ((sets.SelectedTab == MainTab) && (!m_minimized)) + { + m_BtnEntryIncrease.Show(); + m_BtnEntryDecrease.Show(); + } m_BtnStopPriceIncrease.Hide(); m_BtnStopPriceDecrease.Hide(); ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + if ((sets.ShowLines) && (ShowLineLabels)) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); } else if (sets.EntryType == StopLimit) { @@ -2401,7 +2455,6 @@ void CPositionSizeCalculator::OnClickBtnOrderType() if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTABLE, true); if ((sets.WasSelectedStopPriceLine) || (DefaultLinesSelected)) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTED, true); - m_BtnOrderType.Text("Stop Limit"); if (sets.StopPriceLevel == 0) { if (sets.EntryLevel > sets.StopLossLevel) @@ -2416,10 +2469,14 @@ void CPositionSizeCalculator::OnClickBtnOrderType() } ObjectSetDouble(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_PRICE, sets.StopPriceLevel); } - m_BtnEntryIncrease.Show(); - m_BtnEntryDecrease.Show(); - m_BtnStopPriceIncrease.Show(); - m_BtnStopPriceDecrease.Show(); + if ((sets.SelectedTab == MainTab) && (!m_minimized)) + { + m_BtnEntryIncrease.Show(); + m_BtnEntryDecrease.Show(); + m_BtnStopPriceIncrease.Show(); + m_BtnStopPriceDecrease.Show(); + } + if ((sets.ShowLines) && (ShowLineLabels)) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); } RefreshValues(); } @@ -2431,7 +2488,7 @@ void CPositionSizeCalculator::OnClickBtnAccount() case Balance: // Switch to Equity. sets.AccountButton = Equity; - m_BtnAccount.Text("Account equity"); + m_BtnAccount.Text(TRANSLATION_BUTTON_ACCOUNT_EQUITY); // Account balance uneditable. m_EdtAccount.ReadOnly(true); m_EdtAccount.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); @@ -2439,7 +2496,7 @@ void CPositionSizeCalculator::OnClickBtnAccount() case Equity: // Switch to Balance minus Risk. sets.AccountButton = Balance_minus_Risk; - m_BtnAccount.Text("Balance - CPR"); + m_BtnAccount.Text(TRANSLATION_BUTTON_BALANCE_MINUS_CPR); // Account balance uneditable. m_EdtAccount.ReadOnly(true); m_EdtAccount.ColorBackground(CONTROLS_EDIT_COLOR_DISABLE); @@ -2448,7 +2505,7 @@ void CPositionSizeCalculator::OnClickBtnAccount() case Balance_minus_Risk: // Switch to Balance. sets.AccountButton = Balance; - m_BtnAccount.Text("Account balance"); + m_BtnAccount.Text(TRANSLATION_BUTTON_ACCOUNT_BALANCE); // Account balance editable. m_EdtAccount.ReadOnly(false); m_EdtAccount.ColorBackground(CONTROLS_EDIT_COLOR_ENABLE); @@ -2462,11 +2519,11 @@ void CPositionSizeCalculator::OnClickBtnLines() sets.ShowLines = !sets.ShowLines; if (sets.ShowLines) { - m_BtnLines.Text("Hide lines"); + m_BtnLines.Text(TRANSLATION_BUTTON_HIDE_LINES); } else { - m_BtnLines.Text("Show lines"); + m_BtnLines.Text(TRANSLATION_BUTTON_SHOW_LINES); } if (sets.ShowLines) { @@ -2489,6 +2546,11 @@ void CPositionSizeCalculator::OnClickBtnLines() ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_BACK, DrawTextAsBackground); } + if (sets.EntryType != Instant) + { + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_BACK, DrawTextAsBackground); + } if (StringToDouble(m_EdtTP.Text()) != 0) { ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -2550,6 +2612,7 @@ void CPositionSizeCalculator::OnClickBtnLines() ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); @@ -2634,7 +2697,7 @@ void SwitchEntryDirection() { if (sets.TP[i] == 0) continue; old_tp_distance = sets.TP[i] - sets.EntryLevel; - sets.TP[i] = sets.EntryLevel - old_tp_distance; + sets.TP[i] = NormalizeDouble(sets.EntryLevel - old_tp_distance, _Digits); ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, sets.TP[i]); } } @@ -2680,7 +2743,7 @@ void SwitchEntryDirection() { if (sets.TP[i] == 0) continue; old_tp_distance = sets.EntryLevel - sets.TP[i]; - sets.TP[i] = sets.EntryLevel + old_tp_distance; + sets.TP[i] = NormalizeDouble(sets.EntryLevel + old_tp_distance, _Digits); ObjectSetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, sets.TP[i]); } } @@ -2775,7 +2838,7 @@ void CPositionSizeCalculator::OnClickBtnATRTimeframe() break; } if (sets.ATRTimeframe != PERIOD_CURRENT) m_BtnATRTimeframe.Text(EnumToString(sets.ATRTimeframe)); - else m_BtnATRTimeframe.Text("CURRENT"); + else m_BtnATRTimeframe.Text(TRANSLATION_BUTTON_ATR_PERIOD_CURRENT); InitATR(); RefreshValues(); } @@ -2802,8 +2865,10 @@ void CPositionSizeCalculator::OnClickBtnMaxPS() { OutputPositionSize = OutputMaxPositionSize; sets.RiskFromPositionSize = true; - double d_val = StringToDouble(m_EdtPosSize.Text()); - if (OutputPositionSize != d_val) + string text = m_EdtPosSize.Text(); + StringReplace(text, ",", ""); // Remove commas that might appear as the thousands separator due to number formatting. + double field_value = StringToDouble(text); + if (OutputPositionSize != field_value) { m_EdtPosSize.Text(FormatDouble(DoubleToString(OutputPositionSize, LotStep_digits), LotStep_digits)); sets.PositionSize = OutputPositionSize; @@ -2881,6 +2946,11 @@ void CPositionSizeCalculator::OnClickBtnTradingTPShare() { TradingTPShareEdits[i].Text(IntegerToString(sets.TPShare[i])); // Display. } + // Switch color back to normal if it was red because the button results in correct shares. + for (int j = 0; j < sets.TakeProfitsNumber; j++) + { + TradingTPShareEdits[j].Color(m_EdtSL.Color()); // Normal color. + } RefreshValues(); } @@ -3048,7 +3118,7 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitIncrease() if (ArraySize(sets.TP) > 0) { sets.TP[0] = sets.TakeProfitLevel; - TradingTPEdits[0].Text(DoubleToString(sets.TP[0], _Digits)); + if (sets.TakeProfitsNumber > 1) TradingTPEdits[0].Text(DoubleToString(sets.TP[0], _Digits)); } ProcessLineObjectsAfterUpdatingMultipleTP(0); RefreshValues(); @@ -3091,7 +3161,7 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitDecrease() if (ArraySize(sets.TP) > 0) { sets.TP[0] = sets.TakeProfitLevel; - TradingTPEdits[0].Text(DoubleToString(sets.TP[0], _Digits)); + if (sets.TakeProfitsNumber > 1) TradingTPEdits[0].Text(DoubleToString(sets.TP[0], _Digits)); } ProcessLineObjectsAfterUpdatingMultipleTP(0); RefreshValues(); @@ -3106,6 +3176,7 @@ void CPositionSizeCalculator::ProcessAdditionalTPButtonsIncrease(int i) if (TickSize > 0) sets.TP[i] += TickSize; else sets.TP[i] += _Point; if ((sets.TradeDirection == Short) && (sets.TP[i] > sets.EntryLevel)) sets.TP[i] = sets.EntryLevel; // Don't go over the Entry. + sets.TP[i] = NormalizeDouble(sets.TP[i], _Digits); TradingTPEdits[i].Text(DoubleToString(sets.TP[i], _Digits)); } else // Since additional TPs are stored only in their level form, need to differentiate between + on the Long trade and + on the Short trade. @@ -3115,6 +3186,7 @@ void CPositionSizeCalculator::ProcessAdditionalTPButtonsIncrease(int i) { if (TickSize > 0) sets.TP[i] += TickSize; else sets.TP[i] += _Point; + sets.TP[i] = NormalizeDouble(sets.TP[i], _Digits); AdditionalTPEdits[i - 1].Text(DoubleToString(MathRound((sets.TP[i] - sets.EntryLevel) / _Point), 0)); TradingTPEdits[i].Text(AdditionalTPEdits[i - 1].Text()); } @@ -3123,6 +3195,7 @@ void CPositionSizeCalculator::ProcessAdditionalTPButtonsIncrease(int i) if (TickSize > 0) sets.TP[i] -= TickSize; else sets.TP[i] -= _Point; if (sets.TP[i] > sets.EntryLevel) sets.TP[i] = sets.EntryLevel; + sets.TP[i] = NormalizeDouble(sets.TP[i], _Digits); AdditionalTPEdits[i - 1].Text(DoubleToString(MathRound((sets.EntryLevel - sets.TP[i]) / _Point), 0)); TradingTPEdits[i].Text(AdditionalTPEdits[i - 1].Text()); } @@ -3140,6 +3213,7 @@ void CPositionSizeCalculator::ProcessAdditionalTPButtonsDecrease(int i) else sets.TP[i] -= _Point; if (sets.TP[i] < 0) sets.TP[i] = 0; if ((sets.TradeDirection == Long) && (sets.TP[i] < sets.EntryLevel)) sets.TP[i] = sets.EntryLevel; + sets.TP[i] = NormalizeDouble(sets.TP[i], _Digits); TradingTPEdits[i].Text(DoubleToString(sets.TP[i], _Digits)); } else // Since additional TPs are stored only in their level form, need to differentiate between - on the Long trade and - on the Short trade. @@ -3150,6 +3224,7 @@ void CPositionSizeCalculator::ProcessAdditionalTPButtonsDecrease(int i) else sets.TP[i] -= _Point; if (sets.TP[i] < 0) sets.TP[i] = 0; if (sets.TP[i] < sets.EntryLevel) sets.TP[i] = sets.EntryLevel; + sets.TP[i] = NormalizeDouble(sets.TP[i], _Digits); if (sets.TP[i] == sets.EntryLevel) // Got down to zero, should be removed. { sets.TP[i] = 0; @@ -3166,6 +3241,7 @@ void CPositionSizeCalculator::ProcessAdditionalTPButtonsDecrease(int i) if (TickSize > 0) sets.TP[i] += TickSize; else sets.TP[i] += _Point; if (sets.TP[i] > sets.EntryLevel) sets.TP[i] = sets.EntryLevel; + sets.TP[i] = NormalizeDouble(sets.TP[i], _Digits); if (sets.TP[i] == sets.EntryLevel) // Got down to zero, should be removed. { sets.TP[i] = 0; @@ -3235,23 +3311,24 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() ArrayResize(TradingTPEdits, sets.TakeProfitsNumber); ArrayResize(TradingTPShareEdits, sets.TakeProfitsNumber); } - string additional_tp_label_beginning = "Take-profit "; + string additional_tp_label_beginning = TRANSLATION_LABEL_TAKEPROFIT + " "; string additional_tp_label_end = ":"; if (TPDistanceInPoints) { - additional_tp_label_beginning = "TP "; - additional_tp_label_end = ", points:"; + additional_tp_label_beginning = TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE + " "; + additional_tp_label_end = ", " + TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_POINTS + ":"; } if (ArraySize(sets.TP) < sets.TakeProfitsNumber) // Resize only if required. Sometimes, when switching symbols, this won't be required. { ArrayResize(sets.TP, sets.TakeProfitsNumber); + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); sets.TP[sets.TakeProfitsNumber - 1] = 0; // Initialize ArrayResize(sets.TPShare, sets.TakeProfitsNumber); - if (sets.ShareVolumeMode == Increasing) // Do the previous method because sets.ShareVolumeMode gets switched over once you click the button. + if (sets.ShareVolumeMode == Decreasing) // Do the previous method because sets.ShareVolumeMode gets switched over once you click the button. { ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); } - else if (sets.ShareVolumeMode == Equal) + else if (sets.ShareVolumeMode == Increasing) { sets.TPShare[0] = 50; int remaining_volume = 50; @@ -3262,7 +3339,7 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() remaining_volume -= sets.TPShare[i]; } } - else if (sets.ShareVolumeMode == Decreasing) + else if (sets.ShareVolumeMode == Equal) { sets.TPShare[sets.TakeProfitsNumber - 1] = 50; int remaining_volume = 50; @@ -3277,7 +3354,7 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() ArrayResize(ArrayPositionSize, sets.TakeProfitsNumber); } - // Move everything on the Trading tab down by one line to insert the new take-profit. + // Move everything on the Main tab down by one line to insert the new take-profit. int col_height = (int)MathRound(24 * m_DPIScale); CStringForList * obj; bool start_moving = false; // Wait till the first panel object that has to be moved is found. @@ -3309,6 +3386,11 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (MaxTakeProfitsNumber == 1) { ButtonCreate(MainTabList, m_BtnTakeProfitsNumberRemove, first_column_start, y, first_column_start + v_spacing * 4 - 1, y + element_height, name, "x", "Remove Take-profit"); + if (DarkMode) + { + m_BtnTakeProfitsNumberRemove.ColorBackground(DARKMODE_BUTTON_BG_COLOR); + m_BtnTakeProfitsNumberRemove.ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } MainTabList.MoveListElementByName(name, index); } } @@ -3322,25 +3404,48 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (MaxTakeProfitsNumber < sets.TakeProfitsNumber) { int i = sets.TakeProfitsNumber - 2; - name = "AdditionalTPLabels" + IntegerToString(i + 2); + name = "m_LblAdditionalTPLabels" + IntegerToString(i + 2); LabelCreate(MainTabList, AdditionalTPLabels[i], first_column_start + v_spacing * 4, y, first_column_start + normal_label_width, y + element_height, name, additional_tp_label_beginning + IntegerToString(i + 2) + additional_tp_label_end); + if (DarkMode) + { + AdditionalTPLabels[i].Color(DARKMODE_TEXT_COLOR); + } MainTabList.MoveListElementByName(name, index); - name = "AdditionalTPEdits" + IntegerToString(i + 2); + name = "m_EdtAdditionalTPEdits" + IntegerToString(i + 2); EditCreate(MainTabList, AdditionalTPEdits[i], second_column_start, y, second_column_start + normal_edit_width, y + element_height, name, ""); AdditionalTPEdits[i].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + AdditionalTPEdits[i].ColorBackground(DARKMODE_EDIT_BG_COLOR); + AdditionalTPEdits[i].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } MainTabList.MoveListElementByName(name, index + 1); - name = "AdditionalTPButtonsIncrease" + IntegerToString(i + 2); - ButtonCreate(MainTabList, AdditionalTPButtonsIncrease[i], second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, name, "+", "Increase Take-profit #" + IntegerToString(i + 2) + " by 1 point"); + name = "m_BtnAdditionalTPButtonsIncrease" + IntegerToString(i + 2); + ButtonCreate(MainTabList, AdditionalTPButtonsIncrease[i], second_column_start + normal_edit_width + 1, y, second_column_start + normal_edit_width + v_spacing * 4, y + element_height / 2, name, "+", TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE_MULTIPLE + " #" + IntegerToString(i + 2) + " " + TRANSLATION_TOOLTIP_TAKEPROFIT_BY_ONE_POINT); + if (DarkMode) + { + AdditionalTPButtonsIncrease[i].ColorBackground(DARKMODE_BUTTON_BG_COLOR); + AdditionalTPButtonsIncrease[i].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } MainTabList.MoveListElementByName(name, index + 2); - name = "AdditionalTPButtonsDecrease" + IntegerToString(i + 2); - ButtonCreate(MainTabList, AdditionalTPButtonsDecrease[i], second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, name, "-", "Decrease Take-profit #" + IntegerToString(i + 2) + " by 1 point"); + name = "m_BtnAdditionalTPButtonsDecrease" + IntegerToString(i + 2); + ButtonCreate(MainTabList, AdditionalTPButtonsDecrease[i], second_column_start + normal_edit_width + 1, y + element_height / 2, second_column_start + normal_edit_width + v_spacing * 4, y + element_height, name, "-", TRANSLATION_TOOLTIP_TAKEPROFIT_DECREASE_MULTIPLE + " #" + IntegerToString(i + 2) + " " + TRANSLATION_TOOLTIP_TAKEPROFIT_BY_ONE_POINT); + if (DarkMode) + { + AdditionalTPButtonsDecrease[i].ColorBackground(DARKMODE_BUTTON_BG_COLOR); + AdditionalTPButtonsDecrease[i].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } MainTabList.MoveListElementByName(name, index + 3); - name = "AdditionalTPWarnings" + IntegerToString(i + 2); + name = "m_LblAdditionalTPWarnings" + IntegerToString(i + 2); LabelCreate(MainTabList, AdditionalTPWarnings[i], third_column_start, y, third_column_start + narrow_label_width, y + element_height, name, " "); + if (DarkMode) + { + AdditionalTPWarnings[i].Color(DARKMODE_TEXT_COLOR); + } MainTabList.MoveListElementByName(name, index + 4); } @@ -3355,8 +3460,8 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() { if (!start_moving) { - // The "Points" label on the Trading tab. - if (obj.Name == "m_LblTradingPoints") + // The "Points" label on the Trading tab. If it is absent, then the "Subtract position volume" checkbox. If it is absent, "Ask for confimration" checkbox. + if (((ShowFusesOnTrading) && (obj.Name == "m_LblTradingPoints")) || ((ShowCheckboxesOnTrading) && (obj.Name == "m_ChkSubtractPositions")) || (obj.Name == "m_ChkAskForConfirmation")) { start_moving = true; // From now on everything below should be moved down. y = obj.Obj.Top() - col_height - remember_top; // Remember the y where the new TP fields will be inserted. Relative measurement. @@ -3379,19 +3484,38 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (MaxTakeProfitsNumber == 1) { name = "m_LblTradingTP"; - LabelCreate(TradingTabList, m_LblTradingTP, multi_tp_column_start, y, multi_tp_column_start + multi_tp_label_width, y + element_height, name, "TP"); + LabelCreate(TradingTabList, m_LblTradingTP, multi_tp_column_start, y, multi_tp_column_start + multi_tp_label_width, y + element_height, name, TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE); + if (DarkMode) + { + m_LblTradingTP.Color(DARKMODE_TEXT_COLOR); + } TradingTabList.MoveListElementByName(name, index); name = "m_BtnTPsInward"; - ButtonCreate(TradingTabList, m_BtnTPsInward, multi_tp_button_start, y, multi_tp_button_start + leverage_edit_width, y + element_height, name, "<<", "Fill additional TPs equidistantly between Entry and Main TP."); + ButtonCreate(TradingTabList, m_BtnTPsInward, multi_tp_button_start, y, multi_tp_button_start + leverage_edit_width, y + element_height, name, "<<", TRANSLATION_TOOLTIP_FILL_INWARD); + if (DarkMode) + { + m_BtnTPsInward.ColorBackground(DARKMODE_BUTTON_BG_COLOR); + m_BtnTPsInward.ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 1); name = "m_BtnTPsOutward"; - ButtonCreate(TradingTabList, m_BtnTPsOutward, multi_tp_button_start + leverage_edit_width + v_spacing, y, multi_tp_button_start + 2 * leverage_edit_width + v_spacing, y + element_height, name, ">>", "Place additional TPs beyond the Main TP using the same distance."); + ButtonCreate(TradingTabList, m_BtnTPsOutward, multi_tp_button_start + leverage_edit_width + v_spacing, y, multi_tp_button_start + 2 * leverage_edit_width + v_spacing, y + element_height, name, ">>", TRANSLATION_TOOLTIP_FILL_OUTWARD); + if (DarkMode) + { + m_BtnTPsOutward.ColorBackground(DARKMODE_BUTTON_BG_COLOR); + m_BtnTPsOutward.ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 2); name = "m_BtnTradingTPShare"; - ButtonCreate(TradingTabList, m_BtnTradingTPShare, third_trading_column_start, y, third_trading_column_start + normal_edit_width, y + element_height, name, "Share, %", "Automatically fill the volume shares"); + ButtonCreate(TradingTabList, m_BtnTradingTPShare, third_trading_column_start, y, third_trading_column_start + normal_edit_width, y + element_height, name, TRANSLATION_LABEL_SHARE + ", %", TRANSLATION_TOOLTIP_SHARE); + if (DarkMode) + { + m_BtnTradingTPShare.ColorBackground(DARKMODE_BUTTON_BG_COLOR); + m_BtnTradingTPShare.ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 3); y += col_height; @@ -3400,17 +3524,31 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() // First (main) TP: name = "m_LblTradingTPLabel1"; - LabelCreate(TradingTabList, TradingTPLabels[0], first_column_start, y, first_column_start + normal_label_width, y + element_height, name, "Take-profit 1"); + LabelCreate(TradingTabList, TradingTPLabels[0], first_column_start, y, first_column_start + normal_label_width, y + element_height, name, TRANSLATION_LABEL_TAKEPROFIT + " 1"); + if (DarkMode) + { + TradingTPLabels[0].Color(DARKMODE_TEXT_COLOR); + } TradingTabList.MoveListElementByName(name, index); name = "m_EdtTradingTPEdit1"; EditCreate(TradingTabList, TradingTPEdits[0], multi_tp_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, name, ""); TradingTPEdits[0].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + TradingTPEdits[0].ColorBackground(DARKMODE_EDIT_BG_COLOR); + TradingTPEdits[0].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 1); name = "m_EdtTradingTPShareEdit1"; EditCreate(TradingTabList, TradingTPShareEdits[0], third_trading_column_start, y, third_trading_column_start + leverage_edit_width, y + element_height, name, ""); TradingTPShareEdits[0].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + TradingTPShareEdits[0].ColorBackground(DARKMODE_EDIT_BG_COLOR); + TradingTPShareEdits[0].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 2); } else @@ -3436,17 +3574,31 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (MaxTakeProfitsNumber < sets.TakeProfitsNumber) { name = "m_LblTradingTPLabel" + IntegerToString(sets.TakeProfitsNumber); - LabelCreate(TradingTabList, TradingTPLabels[sets.TakeProfitsNumber - 1], first_column_start, y, first_column_start + normal_label_width, y + element_height, name, "Take-profit " + IntegerToString(sets.TakeProfitsNumber)); + LabelCreate(TradingTabList, TradingTPLabels[sets.TakeProfitsNumber - 1], first_column_start, y, first_column_start + normal_label_width, y + element_height, name, TRANSLATION_LABEL_TAKEPROFIT + " " + IntegerToString(sets.TakeProfitsNumber)); + if (DarkMode) + { + TradingTPLabels[sets.TakeProfitsNumber - 1].Color(DARKMODE_TEXT_COLOR); + } TradingTabList.MoveListElementByName(name, index); name = "m_EdtTradingTPEdit" + IntegerToString(sets.TakeProfitsNumber); EditCreate(TradingTabList, TradingTPEdits[sets.TakeProfitsNumber - 1], multi_tp_column_start, y, second_trading_column_start + normal_edit_width, y + element_height, name, ""); TradingTPEdits[sets.TakeProfitsNumber - 1].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + TradingTPEdits[sets.TakeProfitsNumber - 1].ColorBackground(DARKMODE_EDIT_BG_COLOR); + TradingTPEdits[sets.TakeProfitsNumber - 1].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 1); name = "m_EdtTradingTPShareEdit" + IntegerToString(sets.TakeProfitsNumber); EditCreate(TradingTabList, TradingTPShareEdits[sets.TakeProfitsNumber - 1], third_trading_column_start, y, third_trading_column_start + leverage_edit_width, y + element_height, name, ""); TradingTPShareEdits[sets.TakeProfitsNumber - 1].TextAlign(ALIGN_RIGHT); + if (DarkMode) + { + TradingTPShareEdits[sets.TakeProfitsNumber - 1].ColorBackground(DARKMODE_EDIT_BG_COLOR); + TradingTPShareEdits[sets.TakeProfitsNumber - 1].ColorBorder(DARKMODE_CONTROL_BRODER_COLOR); + } TradingTabList.MoveListElementByName(name, index + 2); } else @@ -3458,6 +3610,17 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() if (MaxTakeProfitsNumber < sets.TakeProfitsNumber) MaxTakeProfitsNumber = sets.TakeProfitsNumber; + if (sets.TakeProfitLevel != 0) // If added a new TP when the first TP was already set, set some value to the new one too. + { + if (!TPDistanceInPoints) sets.TP[sets.TakeProfitsNumber - 1] = NormalizeDouble(sets.EntryLevel + (sets.TakeProfitLevel - sets.EntryLevel) * sets.TakeProfitsNumber, _Digits); + else + { + if (sets.TradeDirection == Short) sets.TP[sets.TakeProfitsNumber - 1] = NormalizeDouble(sets.EntryLevel - sets.TakeProfit * _Point * sets.TakeProfitsNumber, _Digits); + else if (sets.TradeDirection == Long) sets.TP[sets.TakeProfitsNumber - 1] = NormalizeDouble(sets.EntryLevel + sets.TakeProfit * _Point * sets.TakeProfitsNumber, _Digits); + AdditionalTPEdits[sets.TakeProfitsNumber - 2].Text(IntegerToString(sets.TakeProfit * sets.TakeProfitsNumber)); + } + } + if ((ShowLineLabels) || (ShowAdditionalTPLabel)) Initialization(); // Creates necessary line labels. HideShowMaximize(); // For panel resizing. RefreshValues(); // For some value to appear inside the TP edit field. @@ -3472,7 +3635,7 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberAdd() // Removed TPs should still be deleted from the TabList lists of names and probably hidden? void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberRemove() { - // Move everything on the Trading tab up by one line as the bottom-most take-profit is removed. + // Move everything on the Main tab up by one line as the bottom-most take-profit is removed. int col_height = (int)MathRound(24 * m_DPIScale); CStringForList * obj; bool start_moving = false; // Wait till the first panel object that has to be moved is found. @@ -3519,8 +3682,8 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberRemove() { if (!start_moving) { - // The "Points" label on the Trading tab. - if (obj.Name == "m_LblTradingPoints") + // The "Points" label on the Trading tab. If it is absent, then the "Subtract position volume" checkbox. If it is absent, "Ask for confimration" checkbox. + if (((ShowFusesOnTrading) && (obj.Name == "m_LblTradingPoints")) || ((ShowCheckboxesOnTrading) && (obj.Name == "m_ChkSubtractPositions")) || (obj.Name == "m_ChkAskForConfirmation")) { start_moving = true; // From now on everything below should be moved up. if (sets.TakeProfitsNumber == 2) m = 3; // Will be moving three rows up: headers + main TP + first secondary TP. @@ -3554,12 +3717,13 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberRemove() // Clean up data of the delted TP. sets.TakeProfitsNumber--; ArrayResize(sets.TP, sets.TakeProfitsNumber); + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); ArrayResize(sets.TPShare, sets.TakeProfitsNumber); - if (sets.ShareVolumeMode == Increasing) // Do the previous method because sets.ShareVolumeMode gets switched over once you click the button. + if (sets.ShareVolumeMode == Decreasing) // Do the previous method because sets.ShareVolumeMode gets switched over once you click the button. { ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); } - else if (sets.ShareVolumeMode == Equal) + else if (sets.ShareVolumeMode == Increasing) { sets.TPShare[0] = 50; int remaining_volume = 50; @@ -3570,7 +3734,7 @@ void CPositionSizeCalculator::OnClickBtnTakeProfitsNumberRemove() remaining_volume -= sets.TPShare[j]; } } - else if (sets.ShareVolumeMode == Decreasing) + else if (sets.ShareVolumeMode == Equal) { sets.TPShare[sets.TakeProfitsNumber - 1] = 50; int remaining_volume = 50; @@ -3619,7 +3783,7 @@ void CPositionSizeCalculator::OnEndEditEdtSL() { if ((int)StringToInteger(m_EdtSL.Text()) <= 0) { - Print("StopLoss should be positive."); + Print(TRANSLATION_MESSAGE_SL_SHOULD_BE_POSITIVE); m_EdtSL.Text(IntegerToString(sets.StopLoss)); } else @@ -3694,7 +3858,7 @@ void CPositionSizeCalculator::OnEndEditEdtTP() ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_STYLE, takeprofit_line_style); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_COLOR, takeprofit_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_WIDTH, takeprofit_line_width); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TOOLTIP, "Take-Profit"); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TOOLTIP, TRANSLATION_LABEL_TAKEPROFIT); // Create multiple TP lines. for (int i = 1; i < sets.TakeProfitsNumber; i++) { @@ -3702,7 +3866,7 @@ void CPositionSizeCalculator::OnEndEditEdtTP() ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_STYLE, takeprofit_line_style); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_COLOR, takeprofit_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_WIDTH, takeprofit_line_width); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_TOOLTIP, "Take-Profit #" + IntegerToString(i + 1)); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_TOOLTIP, TRANSLATION_LABEL_TAKEPROFIT + " #" + IntegerToString(i + 1)); } } else @@ -3743,12 +3907,7 @@ void CPositionSizeCalculator::OnEndEditEdtTP() else // Show. { DummyObjectSelect(); - m_LblRR.Show(); - if (InputRR != "") m_EdtRR1.Show(); - m_EdtRR2.Show(); - m_LblReward.Show(); - m_EdtReward1.Show(); - m_EdtReward2.Show(); + ShowTPRelatedEdits(); if (sets.ShowLines) { ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -3797,6 +3956,17 @@ void CPositionSizeCalculator::OnEndEditEdtTP() } } +// A public function to be run from event processing and from member functions. +void CPositionSizeCalculator::ShowTPRelatedEdits() +{ + m_LblRR.Show(); + if (InputRR != "") m_EdtRR1.Show(); + m_EdtRR2.Show(); + m_LblReward.Show(); + m_EdtReward1.Show(); + m_EdtReward2.Show(); +} + void CPositionSizeCalculator::OnEndEditEdtStopPrice() { sets.StopPriceLevel = StringToDouble(m_EdtStopPrice.Text()); @@ -3838,7 +4008,9 @@ void CPositionSizeCalculator::OnEndEditEdtCommissionSize() void CPositionSizeCalculator::OnEndEditEdtAccount() { - double field_value = StringToDouble(m_EdtAccount.Text()); + string text = m_EdtAccount.Text(); + StringReplace(text, ",", ""); // Remove commas that might appear as the thousands separator due to number formatting. + double field_value = StringToDouble(text); if (sets.CustomBalance != field_value) { if (field_value >= 0) sets.CustomBalance = field_value; @@ -3849,11 +4021,14 @@ void CPositionSizeCalculator::OnEndEditEdtAccount() void CPositionSizeCalculator::OnEndEditEdtRiskPIn() { + string text = m_EdtRiskPIn.Text(); + StringReplace(text, ",", ""); // Remove commas that might appear as the thousands separator due to number formatting. + double field_value = StringToDouble(text); sets.UseMoneyInsteadOfPercentage = false; sets.RiskFromPositionSize = false; - if (sets.Risk != StringToDouble(m_EdtRiskPIn.Text())) + if (sets.Risk != field_value) { - sets.Risk = StringToDouble(m_EdtRiskPIn.Text()); + sets.Risk = field_value; CalculateRiskAndPositionSize(); DisplayValues(); } @@ -3861,45 +4036,39 @@ void CPositionSizeCalculator::OnEndEditEdtRiskPIn() void CPositionSizeCalculator::OnEndEditEdtRiskMIn() { - string s_val = m_EdtRiskMIn.Text(); - StringReplace(s_val, ",", ""); + string text = m_EdtRiskMIn.Text(); + StringReplace(text, ",", ""); + double field_value = StringToDouble(text); sets.UseMoneyInsteadOfPercentage = true; sets.RiskFromPositionSize = false; - if (sets.MoneyRisk != StringToDouble(s_val)) + if (sets.MoneyRisk != field_value) { - sets.MoneyRisk = StringToDouble(s_val); + sets.MoneyRisk = field_value; CalculateRiskAndPositionSize(); DisplayValues(); } } -void CPositionSizeCalculator::OnStartEdtPosSize() -{ - PosSizeEditing = true; -} - void CPositionSizeCalculator::OnEndEditEdtPosSize() { - sets.RiskFromPositionSize = true; - double d_val = StringToDouble(m_EdtPosSize.Text()); - if (d_val >= 0) + string text = m_EdtPosSize.Text(); + StringReplace(text, ",", ""); + double field_value = StringToDouble(text); + if (field_value >= 0) { - if (OutputPositionSize != d_val) + if (OutputPositionSize != field_value) { - OutputPositionSize = d_val; + OutputPositionSize = field_value; sets.PositionSize = OutputPositionSize; + sets.RiskFromPositionSize = true; CalculateRiskAndPositionSize(); - PosSizeEditing = false; DisplayValues(); } - else sets.RiskFromPositionSize = false; } else { m_EdtPosSize.Text(FormatDouble(DoubleToString(OutputPositionSize, LotStep_digits), LotStep_digits)); - PosSizeEditing = false; } - } void CPositionSizeCalculator::OnEndEditATRPeriod() @@ -3971,12 +4140,7 @@ void CPositionSizeCalculator::OnEndEditATRMultiplierTP() } else if (sets.ATRMultiplierTP == 0) // Was zero. { - m_LblRR.Show(); - if (InputRR != "") m_EdtRR1.Show(); - m_EdtRR2.Show(); - m_LblReward.Show(); - m_EdtReward1.Show(); - m_EdtReward2.Show(); + ShowTPRelatedEdits(); sets.ATRMultiplierTP = d_val; RefreshValues(); MoveAndResize(); @@ -4092,10 +4256,20 @@ void CPositionSizeCalculator::OnEndEditEdtMinEntrySLDistance() sets.MinEntrySLDistance = (int)StringToInteger(m_EdtMinEntrySLDistance.Text()); } -void CPositionSizeCalculator::OnEndEditEdtMaxPositionSize() +void CPositionSizeCalculator::OnEndEditEdtMaxPositionSizeTotal() { - sets.MaxPositionSize = (double)StringToDouble(m_EdtMaxPositionSize.Text()); - m_EdtMaxPositionSize.Text(DoubleToString(sets.MaxPositionSize, LotStep_digits)); + sets.MaxPositionSizeTotal = (double)StringToDouble(m_EdtMaxPositionSizeTotal.Text()); + // Only allow changing the total value to be no lower than the per symbol value. Zero is an exception. + if ((sets.MaxPositionSizeTotal < sets.MaxPositionSizePerSymbol) && (sets.MaxPositionSizeTotal != 0)) sets.MaxPositionSizeTotal = sets.MaxPositionSizePerSymbol; + m_EdtMaxPositionSizeTotal.Text(DoubleToString(sets.MaxPositionSizeTotal, LotStep_digits)); +} + +void CPositionSizeCalculator::OnEndEditEdtMaxPositionSizePerSymbol() +{ + sets.MaxPositionSizePerSymbol = (double)StringToDouble(m_EdtMaxPositionSizePerSymbol.Text()); + // Only allow changing the per symbol value to be no greater than the per symbol value. Zero is an exception. + if ((sets.MaxPositionSizePerSymbol > sets.MaxPositionSizeTotal) && (sets.MaxPositionSizeTotal != 0)) sets.MaxPositionSizePerSymbol = sets.MaxPositionSizeTotal; + m_EdtMaxPositionSizePerSymbol.Text(DoubleToString(sets.MaxPositionSizePerSymbol, LotStep_digits)); } void CPositionSizeCalculator::OnChangeChkSubtractPositions() @@ -4140,21 +4314,36 @@ void CPositionSizeCalculator::OnEndEditEdtBreakEvenPoints() m_EdtBreakEvenPoints.Text(IntegerToString(sets.BreakEvenPoints)); } -void CPositionSizeCalculator::OnEndEditEdtMaxNumberOfTrades() +void CPositionSizeCalculator::OnEndEditEdtMaxNumberOfTradesTotal() +{ + sets.MaxNumberOfTradesTotal = (int)StringToInteger(m_EdtMaxNumberOfTradesTotal.Text()); + // Only allow changing the total value to be no lower than the per symbol value. Zero is an exception. + if ((sets.MaxNumberOfTradesTotal < sets.MaxNumberOfTradesPerSymbol) && (sets.MaxNumberOfTradesTotal != 0)) sets.MaxNumberOfTradesTotal = sets.MaxNumberOfTradesPerSymbol; + m_EdtMaxNumberOfTradesTotal.Text(IntegerToString(sets.MaxNumberOfTradesTotal)); +} + +void CPositionSizeCalculator::OnEndEditEdtMaxNumberOfTradesPerSymbol() { - sets.MaxNumberOfTrades = (int)StringToInteger(m_EdtMaxNumberOfTrades.Text()); - m_EdtMaxNumberOfTrades.Text(IntegerToString(sets.MaxNumberOfTrades)); + sets.MaxNumberOfTradesPerSymbol = (int)StringToInteger(m_EdtMaxNumberOfTradesPerSymbol.Text()); + // Only allow changing the per symbol value to be no greater than the per symbol value. Zero is an exception. + if ((sets.MaxNumberOfTradesPerSymbol > sets.MaxNumberOfTradesTotal) && (sets.MaxNumberOfTradesTotal != 0)) sets.MaxNumberOfTradesPerSymbol = sets.MaxNumberOfTradesTotal; + m_EdtMaxNumberOfTradesPerSymbol.Text(IntegerToString(sets.MaxNumberOfTradesPerSymbol)); } -void CPositionSizeCalculator::OnEndEditEdtMaxTotalRisk() +void CPositionSizeCalculator::OnEndEditEdtMaxRiskTotal() { - sets.MaxTotalRisk = StringToDouble(m_EdtMaxTotalRisk.Text()); - m_EdtMaxTotalRisk.Text(DoubleToString(sets.MaxTotalRisk, 2)); + sets.MaxRiskTotal = StringToDouble(m_EdtMaxRiskTotal.Text()); + // Only allow changing the total value to be no lower than the per symbol value. Zero is an exception. + if ((sets.MaxRiskTotal < sets.MaxRiskPerSymbol) && (sets.MaxRiskTotal != 0)) sets.MaxRiskTotal = sets.MaxRiskPerSymbol; + m_EdtMaxRiskTotal.Text(DoubleToString(sets.MaxRiskTotal, 2)); } -void CPositionSizeCalculator::OnChangeChkAllSymbols() +void CPositionSizeCalculator::OnEndEditEdtMaxRiskPerSymbol() { - sets.AllSymbols = m_ChkAllSymbols.Checked(); + sets.MaxRiskPerSymbol = StringToDouble(m_EdtMaxRiskPerSymbol.Text()); + // Only allow changing the per symbol value to be no greater than the per symbol value. Zero is an exception. + if ((sets.MaxRiskPerSymbol > sets.MaxRiskTotal) && (sets.MaxRiskTotal != 0)) sets.MaxRiskPerSymbol = sets.MaxRiskTotal; + m_EdtMaxRiskPerSymbol.Text(DoubleToString(sets.MaxRiskPerSymbol, 2)); } //+-----------------------+ @@ -4162,13 +4351,13 @@ void CPositionSizeCalculator::OnChangeChkAllSymbols() //|+----------------------+ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") { - Print("Trying to save settings to file: " + m_FileName + "."); + Print(TRANSLATION_MESSAGE_TRYING_TO_SAVE_FILE + ": " + m_FileName + "."); int fh; fh = FileOpen(m_FileName, FILE_CSV | FILE_WRITE); if (fh == INVALID_HANDLE) { - Print("Failed to open file for writing: " + m_FileName + ". Error: " + IntegerToString(GetLastError())); + Print(TRANSLATION_MESSAGE_FAILED_TO_OPEN_FOR_WRITING + ": " + m_FileName + ". " + TRANSLATION_MESSAGE_ERROR + ": " + IntegerToString(GetLastError())); return false; } @@ -4251,8 +4440,6 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(sets.MaxEntrySLDistance)); FileWrite(fh, "MinEntrySLDistance"); FileWrite(fh, IntegerToString(sets.MinEntrySLDistance)); - FileWrite(fh, "MaxPositionSize"); - FileWrite(fh, DoubleToString(sets.MaxPositionSize, LotStep_digits)); FileWrite(fh, "StopLoss"); FileWrite(fh, IntegerToString(sets.StopLoss)); FileWrite(fh, "TakeProfit"); @@ -4304,12 +4491,18 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(sets.TrailingStopPoints)); FileWrite(fh, "BreakEvenPoints"); FileWrite(fh, IntegerToString(sets.BreakEvenPoints)); - FileWrite(fh, "MaxNumberOfTrades"); - FileWrite(fh, IntegerToString(sets.MaxNumberOfTrades)); - FileWrite(fh, "MaxTotalRisk"); - FileWrite(fh, DoubleToString(sets.MaxTotalRisk, 2)); - FileWrite(fh, "AllSymbols"); - FileWrite(fh, IntegerToString(sets.AllSymbols)); + FileWrite(fh, "MaxNumberOfTradesTotal"); + FileWrite(fh, IntegerToString(sets.MaxNumberOfTradesTotal)); + FileWrite(fh, "MaxNumberOfTradesPerSymbol"); + FileWrite(fh, IntegerToString(sets.MaxNumberOfTradesPerSymbol)); + FileWrite(fh, "MaxPositionSizeTotal"); + FileWrite(fh, DoubleToString(sets.MaxPositionSizeTotal, LotStep_digits)); + FileWrite(fh, "MaxPositionSizePerSymbol"); + FileWrite(fh, DoubleToString(sets.MaxPositionSizePerSymbol, LotStep_digits)); + FileWrite(fh, "MaxRiskTotal"); + FileWrite(fh, DoubleToString(sets.MaxRiskTotal, 2)); + FileWrite(fh, "MaxRiskPerSymbol"); + FileWrite(fh, DoubleToString(sets.MaxRiskPerSymbol, 2)); FileWrite(fh, "IsPanelMinimized"); FileWrite(fh, IntegerToString(sets.IsPanelMinimized)); FileWrite(fh, "TPLockedOnSL"); @@ -4320,9 +4513,9 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(sets.TemplateChanged)); // These are not part of settings but are panel-related input parameters. - // When indicator is reloaded due to its input parameters change, these should be compared to the new values. + // When the EA is reloaded due to its input parameters change, these should be compared to the new values. // If the value is changed, it should be updated in the panel too. - // Is indicator reloading due to the input parameters change? + // Is the EA reloading due to the input parameters change? if (GlobalVariableGet("PS-" + IntegerToString(ChartID()) + "-Parameters") > 0) { FileWrite(fh, "Parameter_DefaultTradeDirection"); @@ -4385,8 +4578,10 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(DefaultMaxEntrySLDistance)); FileWrite(fh, "Parameter_DefaultMinEntrySLDistance"); FileWrite(fh, IntegerToString(DefaultMinEntrySLDistance)); - FileWrite(fh, "Parameter_DefaultMaxPositionSize"); - FileWrite(fh, DoubleToString(DefaultMaxPositionSize, AccountCurrencyDigits)); + FileWrite(fh, "Parameter_DefaultMaxPositionSizeTotal"); + FileWrite(fh, DoubleToString(DefaultMaxPositionSizeTotal, LotStep_digits)); + FileWrite(fh, "Parameter_DefaultMaxPositionSizePerSymbol"); + FileWrite(fh, DoubleToString(DefaultMaxPositionSizePerSymbol, LotStep_digits)); FileWrite(fh, "Parameter_DefaultSubtractOPV"); FileWrite(fh, IntegerToString(DefaultSubtractOPV)); FileWrite(fh, "Parameter_DefaultSubtractPOV"); @@ -4413,12 +4608,14 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileWrite(fh, IntegerToString(DefaultSpreadAdjustmentSL)); FileWrite(fh, "Parameter_DefaultSpreadAdjustmentTP"); FileWrite(fh, IntegerToString(DefaultSpreadAdjustmentTP)); - FileWrite(fh, "Parameter_DefaultMaxNumberOfTrades"); - FileWrite(fh, IntegerToString(DefaultMaxNumberOfTrades)); - FileWrite(fh, "Parameter_DefaultMaxTotalRisk"); - FileWrite(fh, DoubleToString(DefaultMaxTotalRisk)); - FileWrite(fh, "Parameter_DefaultAllSymbols"); - FileWrite(fh, IntegerToString(DefaultAllSymbols)); + FileWrite(fh, "Parameter_DefaultMaxNumberOfTradesTotal"); + FileWrite(fh, IntegerToString(DefaultMaxNumberOfTradesTotal)); + FileWrite(fh, "Parameter_DefaultMaxNumberOfTradesPerSymbol"); + FileWrite(fh, IntegerToString(DefaultMaxNumberOfTradesPerSymbol)); + FileWrite(fh, "Parameter_DefaultMaxRiskTotal"); + FileWrite(fh, DoubleToString(DefaultMaxRiskTotal)); + FileWrite(fh, "Parameter_DefaultMaxRiskPerSymbol"); + FileWrite(fh, DoubleToString(DefaultMaxRiskPerSymbol)); // Not a part of sets, but needed for proper deletion of unnecessary additional TP lines. FileWrite(fh, "Parameter_DefaultTakeProfitsNumber"); FileWrite(fh, IntegerToString(DefaultTakeProfitsNumber)); @@ -4426,17 +4623,17 @@ bool CPositionSizeCalculator::SaveSettingsOnDisk(string symbol = "") FileClose(fh); - Print("Saved settings successfully."); + Print(TRANSLATION_MESSAGE_SAVED_SETTINGS); return true; } bool CPositionSizeCalculator::LoadSettingsFromDisk() { - Print("Trying to load settings from file."); + Print(TRANSLATION_MESSAGE_TRYING_TO_LOAD_FILE); if (!FileIsExist(m_FileName)) { - Print("No settings file to load."); + Print(TRANSLATION_MESSAGE_NO_SETTINGS_FILE_TO_LOAD); return false; } @@ -4445,7 +4642,7 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() if (fh == INVALID_HANDLE) { - Print("Failed to open file for reading: " + m_FileName + ". Error: " + IntegerToString(GetLastError())); + Print(TRANSLATION_MESSAGE_FAILED_TO_OPEN_FOR_READING + ": " + m_FileName + ". " + TRANSLATION_MESSAGE_ERROR + ": " + IntegerToString(GetLastError())); return false; } @@ -4473,6 +4670,7 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); ArrayResize(sets.WasSelectedAdditionalTakeProfitLine, sets.TakeProfitsNumber - 1); // -1 because the flag for the main TP is saved elsewhere. } + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); } else if (var_name == "StopPriceLevel") sets.StopPriceLevel = StringToDouble(var_content); @@ -4521,12 +4719,18 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() sets.TrailingStopPoints = (int)StringToInteger(var_content); else if (var_name == "BreakEvenPoints") sets.BreakEvenPoints = (int)StringToInteger(var_content); - else if (var_name == "MaxNumberOfTrades") - sets.MaxNumberOfTrades = (int)StringToInteger(var_content); - else if (var_name == "MaxTotalRisk") - sets.MaxTotalRisk = StringToDouble(var_content); - else if (var_name == "AllSymbols") - sets.AllSymbols = (bool)StringToInteger(var_content); + else if (var_name == "MaxNumberOfTradesTotal") + sets.MaxNumberOfTradesTotal = (int)StringToInteger(var_content); + else if (var_name == "MaxNumberOfTradesPerSymbol") + sets.MaxNumberOfTradesPerSymbol = (int)StringToInteger(var_content); + else if (var_name == "MaxPositionSizeTotal") + sets.MaxPositionSizeTotal = StringToDouble(var_content); + else if (var_name == "MaxPositionSizePerSymbol") + sets.MaxPositionSizePerSymbol = StringToDouble(var_content); + else if (var_name == "MaxRiskTotal") + sets.MaxRiskTotal = StringToDouble(var_content); + else if (var_name == "MaxRiskPerSymbol") + sets.MaxRiskPerSymbol = StringToDouble(var_content); else if (var_name == "DisableTradingWhenLinesAreHidden") sets.DisableTradingWhenLinesAreHidden = (bool)StringToInteger(var_content); // Multiple TPs. @@ -4534,7 +4738,7 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() { int i = (int)StringToInteger(StringSubstr(var_name, 3)); // This TP's number. if (i > sets.TakeProfitsNumber - 1) continue; // Cannot accommodate so many. - sets.TP[i] = StringToDouble(var_content); + sets.TP[i] = NormalizeDouble(StringToDouble(var_content), _Digits); } else if ((sets.TakeProfitsNumber > 1) && (StringSubstr(var_name, 0, 8) == "TPShare_")) { @@ -4550,8 +4754,6 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() sets.MaxEntrySLDistance = (int)StringToInteger(var_content); else if (var_name == "MinEntrySLDistance") sets.MinEntrySLDistance = (int)StringToInteger(var_content); - else if (var_name == "MaxPositionSize") - sets.MaxPositionSize = StringToDouble(var_content); else if (var_name == "TradeDirection") sets.TradeDirection = (TRADE_DIRECTION)StringToInteger(var_content); else if (var_name == "StopLoss") @@ -4604,11 +4806,11 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() else if (var_name == "TemplateChanged") sets.TemplateChanged = (bool)StringToInteger(var_content); - // Is indicator reloading due to the input parameters change? - if (GlobalVariableGet("PS-" + IntegerToString(ChartID()) + "-Parameters") > 0) + // Is expert advisor reloading due to the input parameters change? + else if (GlobalVariableGet("PS-" + IntegerToString(ChartID()) + "-Parameters") > 0) { // These are not part of settings but are panel-related input parameters. - // When indicator is reloaded due to its input parameters change, these should be compared to the new values. + // When the expert advisor is reloaded due to its input parameters change, these should be compared to the new values. // If the value is changed, it should be updated in the panel too. if (var_name == "Parameter_DefaultTradeDirection") { @@ -4688,10 +4890,10 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() } else if (var_name == "Parameter_DefaultMoneyRisk") { - if ((StringToDouble(var_content) != DefaultMoneyRisk) && (DefaultMoneyRisk > 0)) + if (DefaultMoneyRisk > 0) { - sets.MoneyRisk = DefaultMoneyRisk; - sets.UseMoneyInsteadOfPercentage = true; + sets.UseMoneyInsteadOfPercentage = true; // Should be set to true whenever the DefaultMoneyRisk is non-zero. + if (StringToDouble(var_content) != DefaultMoneyRisk) sets.MoneyRisk = DefaultMoneyRisk; } else sets.UseMoneyInsteadOfPercentage = false; } @@ -4760,9 +4962,13 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() { if (StringToInteger(var_content) != DefaultMinEntrySLDistance) sets.MinEntrySLDistance = DefaultMinEntrySLDistance; } - else if (var_name == "Parameter_DefaultMaxPositionSize") + else if (var_name == "Parameter_DefaultMaxPositionSizeTotal") { - if (StringToDouble(var_content) != DefaultMaxPositionSize) sets.MaxPositionSize = DefaultMaxPositionSize; + if (StringToDouble(var_content) != DefaultMaxPositionSizeTotal) sets.MaxPositionSizeTotal = DefaultMaxPositionSizeTotal; + } + else if (var_name == "Parameter_DefaultMaxPositionSizePerSymbol") + { + if (StringToDouble(var_content) != DefaultMaxPositionSizePerSymbol) sets.MaxPositionSizePerSymbol = DefaultMaxPositionSizePerSymbol; } else if (var_name == "Parameter_DefaultSubtractOPV") { @@ -4809,25 +5015,29 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() { if (StringToInteger(var_content) != DefaultBreakEven) sets.BreakEvenPoints = DefaultBreakEven; } - else if (var_name == "Parameter_DefaultMaxNumberOfTrades") + else if (var_name == "Parameter_DefaultSpreadAdjustmentSL") { - if (StringToInteger(var_content) != DefaultMaxNumberOfTrades) sets.MaxNumberOfTrades = DefaultMaxNumberOfTrades; + if ((bool)StringToInteger(var_content) != DefaultSpreadAdjustmentSL) sets.SpreadAdjustmentSL = DefaultSpreadAdjustmentSL; } - else if (var_name == "Parameter_DefaultMaxTotalRisk") + else if (var_name == "Parameter_DefaultSpreadAdjustmentTP") { - if (StringToDouble(var_content) != DefaultMaxTotalRisk) sets.MaxTotalRisk = DefaultMaxTotalRisk; + if ((bool)StringToInteger(var_content) != DefaultSpreadAdjustmentTP) sets.SpreadAdjustmentTP = DefaultSpreadAdjustmentTP; } - else if (var_name == "Parameter_DefaultAllSymbols") + else if (var_name == "Parameter_DefaultMaxNumberOfTradesTotal") { - if ((bool)StringToInteger(var_content) != DefaultAllSymbols) sets.AllSymbols = DefaultAllSymbols; + if (StringToInteger(var_content) != DefaultMaxNumberOfTradesTotal) sets.MaxNumberOfTradesTotal = DefaultMaxNumberOfTradesTotal; } - else if (var_name == "Parameter_DefaultSpreadAdjustmentSL") + else if (var_name == "Parameter_DefaultMaxNumberOfTradesPerSymbol") { - if ((bool)StringToInteger(var_content) != DefaultSpreadAdjustmentSL) sets.SpreadAdjustmentSL = DefaultSpreadAdjustmentSL; + if (StringToInteger(var_content) != DefaultMaxNumberOfTradesPerSymbol) sets.MaxNumberOfTradesPerSymbol = DefaultMaxNumberOfTradesPerSymbol; } - else if (var_name == "Parameter_DefaultSpreadAdjustmentTP") + else if (var_name == "Parameter_DefaultMaxRiskTotal") { - if ((bool)StringToInteger(var_content) != DefaultSpreadAdjustmentTP) sets.SpreadAdjustmentTP = DefaultSpreadAdjustmentTP; + if (StringToDouble(var_content) != DefaultMaxRiskTotal) sets.MaxRiskTotal = DefaultMaxRiskTotal; + } + else if (var_name == "Parameter_DefaultMaxRiskPerSymbol") + { + if (StringToDouble(var_content) != DefaultMaxRiskPerSymbol) sets.MaxRiskPerSymbol = DefaultMaxRiskPerSymbol; } else if (var_name == "Parameter_DefaultTakeProfitsNumber") { @@ -4850,15 +5060,21 @@ bool CPositionSizeCalculator::LoadSettingsFromDisk() ArrayInitialize(sets.TPShare, 100 / sets.TakeProfitsNumber); ArrayResize(sets.WasSelectedAdditionalTakeProfitLine, sets.TakeProfitsNumber - 1); // -1 because the flag for the main TP is saved elsewhere. } + ArrayResize(TakeProfitLineIsBeingMoved, sets.TakeProfitsNumber); } } } } + // Make sure total and per symbol values do not contradict each other. + if ((sets.MaxPositionSizeTotal < sets.MaxPositionSizePerSymbol) && (sets.MaxPositionSizeTotal != 0)) sets.MaxPositionSizeTotal = sets.MaxPositionSizePerSymbol; + if ((sets.MaxNumberOfTradesTotal < sets.MaxNumberOfTradesPerSymbol) && (sets.MaxNumberOfTradesTotal != 0)) sets.MaxNumberOfTradesTotal = sets.MaxNumberOfTradesPerSymbol; + if ((sets.MaxRiskTotal < sets.MaxRiskPerSymbol) && (sets.MaxRiskTotal != 0)) sets.MaxRiskTotal = sets.MaxRiskPerSymbol; + FileClose(fh); - Print("Loaded settings successfully."); + Print(TRANSLATION_MESSAGE_LOADED_SETTINGS); - // Is indicator reloading due to the input parameters change? Delete the flag variable. + // Is expert advisor reloading due to the input parameters change? Delete the flag variable. if (GlobalVariableGet("PS-" + IntegerToString(ChartID()) + "-Parameters") > 0) GlobalVariableDel("PS-" + IntegerToString(ChartID()) + "-Parameters"); return true; @@ -4868,16 +5084,16 @@ bool CPositionSizeCalculator::DeleteSettingsFile() { if (!FileIsExist(m_FileName)) { - Print("No settings file to delete."); + Print(TRANSLATION_MESSAGE_NO_SETTINGS_FILE_TO_DELETE); return false; } - Print("Trying to delete settings file."); + Print(TRANSLATION_MESSAGE_TRYING_TO_DELETE_FILE); if (!FileDelete(m_FileName)) { - Print("Failed to delete file: " + m_FileName + ". Error: " + IntegerToString(GetLastError())); + Print(TRANSLATION_MESSAGE_FAILED_TO_DELETE_FILE + ": " + m_FileName + ". " + TRANSLATION_MESSAGE_ERROR + ": " + IntegerToString(GetLastError())); return false; } - Print("Deleted settings file successfully."); + Print(TRANSLATION_MESSAGE_DELETED_SETTINGS); return true; } @@ -4897,7 +5113,7 @@ void CPositionSizeCalculator::HideShowMaximize() void CPositionSizeCalculator::InitATR() { ATR_handle = iATR(Symbol(), sets.ATRTimeframe, sets.ATRPeriod); - if (ATR_handle == INVALID_HANDLE) Print("Failed to create ATR handle: ", GetLastError()); + if (ATR_handle == INVALID_HANDLE) Print(TRANSLATION_MESSAGE_FAILED_TO_CREATE_ATR + ": ", GetLastError()); } //+------------------------------------------------------------------+ @@ -4979,7 +5195,7 @@ void CPositionSizeCalculator::UpdateAdditionalFixedTP(int i) { double read_value; if (!ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_PRICE, 0, read_value)) return; // Update only if line exists. - else sets.TP[i] = read_value; + else sets.TP[i] = NormalizeDouble(read_value, _Digits); // Check and adjust for TickSize granularity. if (TickSize > 0) @@ -5008,7 +5224,7 @@ void CPositionSizeCalculator::UpdateTradingTPEdit(int i) TradingTPEdits[i].Text(s); // Remember the value. new_value = StringToDouble(s); - sets.TP[i] = new_value; + sets.TP[i] = NormalizeDouble(new_value, _Digits); if (i > 0) { if (!TPDistanceInPoints) AdditionalTPEdits[i - 1].Text(s); // TP as level. @@ -5062,7 +5278,7 @@ void CPositionSizeCalculator::UpdateAdditionalTPEdit(int i) // Remember the value. new_value = StringToDouble(s); - sets.TP[i] = new_value; + sets.TP[i] = NormalizeDouble(new_value, _Digits); } // TP as distance. else @@ -5203,7 +5419,7 @@ void CPositionSizeCalculator::CheckAndRestoreLines() ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_COLOR, stoploss_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_WIDTH, stoploss_line_width); ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_SELECTABLE, true); - ObjectSetString(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_TOOLTIP, "Stop-Loss"); + ObjectSetString(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_TOOLTIP, TRANSLATION_LABEL_STOPLOSS); if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_SELECTED, true); if (!sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); RestoredSomething = true; @@ -5218,7 +5434,7 @@ void CPositionSizeCalculator::CheckAndRestoreLines() ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_COLOR, takeprofit_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_WIDTH, takeprofit_line_width); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_SELECTABLE, true); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TOOLTIP, "Take-Profit"); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TOOLTIP, TRANSLATION_LABEL_TAKEPROFIT); if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_SELECTED, true); // Only for new lines. Old lines retain their selected status unless default parameter value changed. RestoredSomething = true; } @@ -5235,23 +5451,26 @@ void CPositionSizeCalculator::CheckAndRestoreLines() ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_COLOR, takeprofit_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_WIDTH, takeprofit_line_width); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_SELECTABLE, true); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_TOOLTIP, "Take-Profit #" + IntegerToString(i + 1)); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_TOOLTIP, TRANSLATION_LABEL_TAKEPROFIT + " #" + IntegerToString(i + 1)); if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_SELECTED, true); // Only for new lines. Old lines retain their selected status unless default parameter value changed. RestoredSomething = true; } } - if (ObjectFind(ChartID(), ObjectPrefix + "StopPriceLine") == -1) + if (!DisableStopLimit) { - ObjectCreate(0, ObjectPrefix + "StopPriceLine", OBJ_HLINE, 0, TimeCurrent(), sets.StopPriceLevel); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_STYLE, stopprice_line_style); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_COLOR, stopprice_line_color); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_WIDTH, stopprice_line_width); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTABLE, true); - ObjectSetString(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TOOLTIP, "Stop Price (for Stop Limit orders)"); - if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTED, true); - if (!sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); - RestoredSomething = true; + if (ObjectFind(ChartID(), ObjectPrefix + "StopPriceLine") == -1) + { + ObjectCreate(0, ObjectPrefix + "StopPriceLine", OBJ_HLINE, 0, TimeCurrent(), sets.StopPriceLevel); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_STYLE, stopprice_line_style); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_COLOR, stopprice_line_color); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_WIDTH, stopprice_line_width); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTABLE, true); + ObjectSetString(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_STOP_PRICE_LINE); + if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTED, true); + if ((!sets.ShowLines) || (sets.EntryType != StopLimit)) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + RestoredSomething = true; + } } // Put panel on top of the lines that were created later. @@ -5286,7 +5505,7 @@ void CPositionSizeCalculator::SeekAndDestroyDuplicatePanels() // Reset object counter. ot = ObjectsTotal(ChartID()); i = ot; - Print("Deleted duplicate panel objects with prefix = ", prefix, "."); + Print(TRANSLATION_MESSAGE_DELETED_DUPLICATE_PANEL + " = ", prefix, "."); continue; } } @@ -5311,6 +5530,7 @@ double PreCustomLeverage = -1; // For remembering the leverage that was before w string AccountCurrency, MarginCurrency, ProfitCurrency, BaseCurrency; string CurrencyPairsList[]; bool MarginInUnconvertedMarginCurrency; // This flag is set to true if margin currency could not be converted. +int WarnedAboutZeroUnitCost = 0; // Was there already a warning? long AccStopoutMode; int LotStep_digits, AccountCurrencyDigits = 2; @@ -5331,13 +5551,14 @@ double DisplayRisk, RiskMoney, PositionMargin, UsedMargin, FutureMargin, PreHedg string InputRR, OutputRR, MainOutputRR, PLM, CPR, PRM, CPRew, PPMR, PPR, PPMRew, PPRew, CPL, PPL, AdditionalOutputRR[]; string InputReward; double OutputReward, AdditionalOutputReward[], MainOutputReward; -string OutputPointValue = "", OutputSwapsType = "Unknown", SwapsTripleDay = "?", +string OutputPointValue = "", OutputSwapsType = TRANSLATION_LABEL_UNKNOWN, SwapsTripleDay = "?", OutputSwapsDailyLongLot = "?", OutputSwapsDailyShortLot = "?", OutputSwapsDailyLongPS = "?", OutputSwapsDailyShortPS = "?", OutputSwapsYearlyLongLot = "?", OutputSwapsYearlyShortLot = "?", OutputSwapsYearlyLongPS = "?", OutputSwapsYearlyShortPS = "?", OutputSwapsCurrencyDailyLot = "", OutputSwapsCurrencyDailyPS = "", OutputSwapsCurrencyYearlyLot = "", OutputSwapsCurrencyYearlyPS = ""; int LinesSelectedStatus; // 0 - no change, 1 - flip to selected, 2 - flip to unselected. double ArrayPositionSize[]; // PS for each trade with multiple TPs. int TotalVolumeShare = 100; // Holds the sum of volume shares for multiple TPs. Used by UpdateTradingTPShareEdit() and Trade(). +string WarnedSymbols[]; // CCY1 + CCY2 + Symbol. Used to store currency combinations and symbols that have already warning on them triggered. //================================================================================================================== //+----------------------+ @@ -5400,7 +5621,7 @@ void Initialization() if ((TPDistanceInPoints) && (sets.TakeProfit == 0) && (sets.TakeProfitLevel != 0)) sets.TakeProfit = (int)MathRound(MathAbs((sets.TakeProfitLevel - sets.EntryLevel) / _Point)); if (sets.EntryLevel - sets.StopLossLevel == 0) { - Alert("Entry and Stop-Loss levels should be different and non-zero."); + Alert(TRANSLATION_MESSAGE_ENTRY_SL_DIFFERENT_NON_ZERO); return; } @@ -5448,7 +5669,7 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_STYLE, entry_line_style); ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_COLOR, entry_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_WIDTH, entry_line_width); - ObjectSetString(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_TOOLTIP, "Entry"); + ObjectSetString(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_TOOLTIP, TRANSLATION_LABEL_ENTRY); if (sets.EntryType == Instant) ObjectSetInteger(0, ObjectPrefix + "EntryLine", OBJPROP_SELECTABLE, false); else { @@ -5480,7 +5701,7 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_COLOR, stoploss_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_WIDTH, stoploss_line_width); ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_SELECTABLE, true); - ObjectSetString(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_TOOLTIP, "Stop-Loss"); + ObjectSetString(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_TOOLTIP, TRANSLATION_LABEL_STOPLOSS); if (!line_existed) { if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_SELECTED, true); // Only for new lines. Old lines retain their selected status unless default parameter value changed. @@ -5501,7 +5722,7 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLabel", OBJPROP_BACK, DrawTextAsBackground); ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLabel", OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "StopLossLabel", OBJPROP_TOOLTIP, "SL Distance, points"); + ObjectSetString(ChartID(), ObjectPrefix + "StopLossLabel", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_SL_LABEL); if ((ShowAdditionalSLLabel) && (ObjectFind(0, ObjectPrefix + "SLAdditionalLabel") == -1)) { ObjectCreate(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJ_LABEL, 0, 0, 0); @@ -5512,8 +5733,18 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_HIDDEN, false); ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TOOLTIP, "Risk, % ($)"); + ObjectSetString(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TOOLTIP, TRANSLATION_LABEL_RISK + ", % ($)"); } + + ObjectCreate(ChartID(), ObjectPrefix + "EntryLabel", OBJ_LABEL, 0, 0, 0); + if ((sets.ShowLines) && (sets.EntryType != Instant)) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_COLOR, clrNONE); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_SELECTABLE, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_HIDDEN, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); + ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_BACK, DrawTextAsBackground); + ObjectSetString(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_ENTRY_LABEL); } if (ObjectFind(ChartID(), ObjectPrefix + "TakeProfitLine") == -1) @@ -5533,7 +5764,7 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_COLOR, takeprofit_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_WIDTH, takeprofit_line_width); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_SELECTABLE, true); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TOOLTIP, "Take-Profit"); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TOOLTIP, TRANSLATION_LABEL_TAKEPROFIT); if (!line_existed) { if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_SELECTED, true); // Only for new lines. Old lines retain their selected status unless default parameter value changed. @@ -5545,19 +5776,16 @@ void Initialization() } if (ShowLineLabels) { - if (ObjectFind(ChartID(), ObjectPrefix + "TakeProfitLabel") == -1) - { - ObjectCreate(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJ_LABEL, 0, 0, 0); - if ((sets.TakeProfitLevel > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); - else ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_COLOR, clrNONE); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_SELECTABLE, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_HIDDEN, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TOOLTIP, "TP Distance, points"); - } - if ((ShowAdditionalTPLabel) && (ObjectFind(ChartID(), ObjectPrefix + "TPAdditionalLabel") == -1)) + ObjectCreate(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJ_LABEL, 0, 0, 0); + if ((sets.TakeProfitLevel > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_COLOR, clrNONE); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_SELECTABLE, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_HIDDEN, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_BACK, DrawTextAsBackground); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLabel", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_TP_LABEL); + if (ShowAdditionalTPLabel) { ObjectCreate(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJ_LABEL, 0, 0, 0); if ((sets.TakeProfitLevel > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -5567,25 +5795,25 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_HIDDEN, false); ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_TOOLTIP, "Reward, % ($), R/R"); + ObjectSetString(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_TOOLTIP, TRANSLATION_LABEL_REWARD + ", % ($), R/R"); } } - if (ObjectFind(ChartID(), ObjectPrefix + "StopPriceLine") == -1) + if (!DisableStopLimit) { - ObjectCreate(ChartID(), ObjectPrefix + "StopPriceLine", OBJ_HLINE, 0, TimeCurrent(), sets.StopPriceLevel); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_HIDDEN, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); - } - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_STYLE, stopprice_line_style); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_COLOR, stopprice_line_color); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_WIDTH, stopprice_line_width); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTABLE, true); - ObjectSetString(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TOOLTIP, "Stop Price (for Stop Limit orders)"); - if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTED, true); - if (ShowLineLabels) - { - if (ObjectFind(ChartID(), ObjectPrefix + "StopPriceLabel") == -1) + if (ObjectFind(ChartID(), ObjectPrefix + "StopPriceLine") == -1) + { + ObjectCreate(ChartID(), ObjectPrefix + "StopPriceLine", OBJ_HLINE, 0, TimeCurrent(), sets.StopPriceLevel); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_HIDDEN, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + } + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_STYLE, stopprice_line_style); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_COLOR, stopprice_line_color); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_WIDTH, stopprice_line_width); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTABLE, true); + ObjectSetString(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_STOP_PRICE_LINE); + if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTED, true); + if (ShowLineLabels) { ObjectCreate(ChartID(), ObjectPrefix + "StopPriceLabel", OBJ_LABEL, 0, 0, 0); if ((sets.EntryType == StopLimit) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -5595,9 +5823,14 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_HIDDEN, false); ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_TOOLTIP, "Stop Price Distance, points"); + ObjectSetString(ChartID(), ObjectPrefix + "StopPriceLabel", OBJPROP_TOOLTIP, TRANSLATION_TOOLTIP_STOP_PRICE_LABEL); } } + else + { + ObjectDelete(ChartID(), ObjectPrefix + "StopPriceLine"); + if (sets.EntryType == StopLimit) sets.EntryType = Pending; + } if (sets.ShowLines == false) { @@ -5615,8 +5848,8 @@ void Initialization() if (sets.EntryType == StopLimit) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); else { - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTED, true); + ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); } } @@ -5639,7 +5872,7 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_COLOR, takeprofit_line_color); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_WIDTH, takeprofit_line_width); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_SELECTABLE, true); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_TOOLTIP, "Take-Profit #" + IntegerToString(i + 1)); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_TOOLTIP, TRANSLATION_LABEL_TAKEPROFIT + " #" + IntegerToString(i + 1)); if (!line_existed) { if (DefaultLinesSelected) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_SELECTED, true); // Only for new lines. Old lines retain their selected status unless default parameter value changed. @@ -5651,19 +5884,16 @@ void Initialization() } if (ShowLineLabels) { - if (ObjectFind(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i)) == -1) - { - ObjectCreate(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJ_LABEL, 0, 0, 0); - if ((sets.TP[i] > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); - else ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_COLOR, clrNONE); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_SELECTABLE, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_HIDDEN, false); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_CORNER, CORNER_LEFT_UPPER); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TOOLTIP, "TP #" + IntegerToString(i + 1) + " Distance, points"); - } - if ((ShowAdditionalTPLabel) && (ObjectFind(0, ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i)) == -1)) + ObjectCreate(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJ_LABEL, 0, 0, 0); + if ((sets.TP[i] > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_COLOR, clrNONE); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_SELECTABLE, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_HIDDEN, false); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_CORNER, CORNER_LEFT_UPPER); + ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_BACK, DrawTextAsBackground); + ObjectSetString(ChartID(), ObjectPrefix + "TakeProfitLabel" + IntegerToString(i), OBJPROP_TOOLTIP, TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE + " #" + IntegerToString(i + 1) + ", " + TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_POINTS); + if (ShowAdditionalTPLabel) { ObjectCreate(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJ_LABEL, 0, 0, 0); if ((sets.TP[i] > 0) && (sets.ShowLines)) ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -5673,7 +5903,7 @@ void Initialization() ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_HIDDEN, false); ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_CORNER, CORNER_LEFT_UPPER); ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_BACK, DrawTextAsBackground); - ObjectSetString(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_TOOLTIP, "Reward #" + IntegerToString(i + 1) + ", $ (%), R/R"); + ObjectSetString(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_TOOLTIP, TRANSLATION_LABEL_REWARD + " #" + IntegerToString(i + 1) + ", $ (%), R/R"); } } } @@ -5698,10 +5928,6 @@ void Initialization() if (sets.ShowLines == false) { - ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); for (int i = 1; i < sets.TakeProfitsNumber; i++) { ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); @@ -5709,10 +5935,6 @@ void Initialization() } else { - ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); - ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); for (int i = 1; i < sets.TakeProfitsNumber; i++) { ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -5726,6 +5948,7 @@ void Initialization() if (sets.EntryType != Instant) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLine", OBJPROP_SELECTED, true); ObjectSetInteger(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_SELECTED, true); ObjectSetInteger(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_SELECTED, true); + if (sets.EntryType == StopLimit) ObjectSetInteger(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_SELECTED, true); // Process multiple TP lines. for (int i = 1; i < sets.TakeProfitsNumber; i++) { @@ -5772,7 +5995,7 @@ void RecalculatePositionSize() // If could not find account currency, probably not connected. Also check for symbol availability. if ((AccountInfoString(ACCOUNT_CURRENCY) == "") || (!TerminalInfoInteger(TERMINAL_CONNECTED) || (!SymbolInfoInteger(Symbol(), SYMBOL_SELECT)))) return; - else if (TickSize == -1) + else if ((TickSize == -1) || (TickValue == 0)) { GetSymbolAndAccountData(); } @@ -5784,11 +6007,14 @@ void RecalculatePositionSize() tEntryLevel = Round(read_tEntryLevel, _Digits); if (!ObjectGetDouble(ChartID(), ObjectPrefix + "StopLossLine", OBJPROP_PRICE, 0, read_tStopLossLevel)) return; tStopLossLevel = Round(read_tStopLossLevel, _Digits); - if (!ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, 0, read_tTakeProfitLevel)) return; - tTakeProfitLevel = Round(read_tTakeProfitLevel, _Digits); - if (!ObjectGetDouble(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_PRICE, 0, read_tStopPriceLevel)) return; - tStopPriceLevel = Round(read_tStopPriceLevel, _Digits); - + if (ObjectGetDouble(ChartID(), ObjectPrefix + "TakeProfitLine", OBJPROP_PRICE, 0, read_tTakeProfitLevel)) tTakeProfitLevel = Round(read_tTakeProfitLevel, _Digits); + else tTakeProfitLevel = 0; + if (!DisableStopLimit) + { + if (!ObjectGetDouble(ChartID(), ObjectPrefix + "StopPriceLine", OBJPROP_PRICE, 0, read_tStopPriceLevel)) return; + tStopPriceLevel = Round(read_tStopPriceLevel, _Digits); + } + double StopLevel = SymbolInfoInteger(Symbol(), SYMBOL_TRADE_STOPS_LEVEL) * _Point; WarningEntry = ""; WarningSL = ""; @@ -5797,7 +6023,7 @@ void RecalculatePositionSize() double AskBid = 0; if (sets.EntryType == Instant) { - if ((tStopLossLevel < Ask) && (tStopLossLevel > Bid)) WarningSL = " (Wrong value!)"; + if ((tStopLossLevel < Ask) && (tStopLossLevel > Bid)) WarningSL = " " + TRANSLATION_LABEL_WARNING_WRONG_VALUE; else if (tStopLossLevel < Ask) AskBid = Ask; else if (tStopLossLevel > Bid) AskBid = Bid; } @@ -5807,9 +6033,9 @@ void RecalculatePositionSize() else if (tStopLossLevel > tEntryLevel) AskBid = Bid; if (AskBid) { - if (MathAbs(AskBid - tEntryLevel) < StopLevel) WarningEntry = " (Too close!)"; + if (MathAbs(AskBid - tEntryLevel) < StopLevel) WarningEntry = " " + TRANSLATION_LABEL_WARNING_TOO_CLOSE; } - else WarningSL = " (Wrong value!)"; + else WarningSL = " " + TRANSLATION_LABEL_WARNING_WRONG_VALUE; } else if (sets.EntryType == StopLimit) { @@ -5817,30 +6043,30 @@ void RecalculatePositionSize() { AskBid = Ask; // Check if Stop price is above current price for Longs. - if (tStopPriceLevel <= AskBid) WarningSP = " (Wrong value!)"; + if (tStopPriceLevel <= AskBid) WarningSP = " " + TRANSLATION_LABEL_WARNING_WRONG_VALUE; } else if (tStopLossLevel > tEntryLevel) { AskBid = Bid; // Check if Stop price is below current price for Shorts. - if (tStopPriceLevel >= AskBid) WarningSP = " (Wrong value!)"; + if (tStopPriceLevel >= AskBid) WarningSP = " " + TRANSLATION_LABEL_WARNING_WRONG_VALUE; } if (AskBid) { // Check whether Stop price isn't too close to the current price. - if (MathAbs(AskBid - tStopPriceLevel) < StopLevel) WarningSP = " (Too close!)"; + if (MathAbs(AskBid - tStopPriceLevel) < StopLevel) WarningSP = " " + TRANSLATION_LABEL_WARNING_TOO_CLOSE; // Check whether Limit price isn't too close to the Stop price. - if (MathAbs(tEntryLevel - tStopPriceLevel) < StopLevel) WarningEntry = " (Too close!)"; + if (MathAbs(tEntryLevel - tStopPriceLevel) < StopLevel) WarningEntry = " " + TRANSLATION_LABEL_WARNING_TOO_CLOSE; } - else WarningSL = " (Wrong value!)"; + else WarningSL = " " + TRANSLATION_LABEL_WARNING_WRONG_VALUE; } - if (MathAbs(tStopLossLevel - tEntryLevel) < StopLevel) WarningSL = " (Too close!)"; + if (MathAbs(tStopLossLevel - tEntryLevel) < StopLevel) WarningSL = " " + TRANSLATION_LABEL_WARNING_TOO_CLOSE; if (tTakeProfitLevel > 0) { - if (MathAbs(tTakeProfitLevel - tEntryLevel) < StopLevel) WarningTP = " (Too close!)"; + if (MathAbs(tTakeProfitLevel - tEntryLevel) < StopLevel) WarningTP = " " + TRANSLATION_LABEL_WARNING_TOO_CLOSE; } for (int i = 1; i < sets.TakeProfitsNumber; i++) @@ -5850,7 +6076,7 @@ void RecalculatePositionSize() add_tTakeProfitLevel = Round(add_tTakeProfitLevel, _Digits); if (add_tTakeProfitLevel > 0) { - if (MathAbs(add_tTakeProfitLevel - tEntryLevel) < StopLevel) AdditionalWarningTP[i - 1] = "(Too close!)"; + if (MathAbs(add_tTakeProfitLevel - tEntryLevel) < StopLevel) AdditionalWarningTP[i - 1] = " " + TRANSLATION_LABEL_WARNING_TOO_CLOSE; } } @@ -5901,6 +6127,12 @@ void RecalculatePositionSize() if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); else ObjectSetInteger(ChartID(), ObjectPrefix + "SLAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); } + if (sets.EntryType != Instant) + { + DrawLineLabel(ObjectPrefix + "EntryLabel", IntegerToString((int)MathRound((MathAbs(tEntryLevel - AskBid) / _Point))), tEntryLevel, entry_label_font_color); + if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); + else ObjectSetInteger(ChartID(), ObjectPrefix + "EntryLabel", OBJPROP_TIMEFRAMES, OBJ_NO_PERIODS); + } if (tTakeProfitLevel > 0) { DrawLineLabel(ObjectPrefix + "TakeProfitLabel", IntegerToString((int)MathRound((MathAbs(tTakeProfitLevel - tEntryLevel) / _Point))), tTakeProfitLevel, tp_label_font_color); @@ -5910,7 +6142,7 @@ void RecalculatePositionSize() if (ShowAdditionalTPLabel) { string label_text; - if ((WarningTP == "") && (MainOutputRR != "Invalid TP")) + if ((WarningTP == "") && (MainOutputRR != TRANSLATION_LABEL_WARNING_INVALID_TP)) { string perc_risk; if (AccSize > 0) perc_risk = FormatDouble(DoubleToString(Round(MainOutputReward / AccSize * 100, 2, RoundDown), 2)); @@ -5922,7 +6154,7 @@ void RecalculatePositionSize() else { label_text = WarningTP; - if (MainOutputRR == "Invalid TP") label_text += MainOutputRR; + if (MainOutputRR == TRANSLATION_LABEL_WARNING_INVALID_TP) label_text += MainOutputRR; } DrawLineLabel(ObjectPrefix + "TPAdditionalLabel", label_text, tTakeProfitLevel, tp_label_font_color, true); if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel", OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -5939,7 +6171,7 @@ void RecalculatePositionSize() if (ShowAdditionalTPLabel) { string label_text; - if ((AdditionalWarningTP[i - 1] == "") && (AdditionalOutputRR[i - 1] != "Invalid TP")) + if ((AdditionalWarningTP[i - 1] == "") && (AdditionalOutputRR[i - 1] != TRANSLATION_LABEL_WARNING_INVALID_TP)) { string perc_risk; if (AccSize > 0) perc_risk = FormatDouble(DoubleToString(Round(AdditionalOutputReward[i - 1] / AccSize * 100, 2, RoundDown), 2)); @@ -5949,7 +6181,7 @@ void RecalculatePositionSize() else { label_text = AdditionalWarningTP[i - 1]; - if (AdditionalOutputRR[i - 1] == "Invalid TP") label_text += AdditionalOutputRR[i - 1]; + if (AdditionalOutputRR[i - 1] == TRANSLATION_LABEL_WARNING_INVALID_TP) label_text += AdditionalOutputRR[i - 1]; } DrawLineLabel(ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), label_text, add_tTakeProfitLevel, tp_label_font_color, true); if (sets.ShowLines) ObjectSetInteger(ChartID(), ObjectPrefix + "TPAdditionalLabel" + IntegerToString(i), OBJPROP_TIMEFRAMES, OBJ_ALL_PERIODS); @@ -5966,7 +6198,7 @@ void RecalculatePositionSize() if (StopLoss == 0) { - Print("Stop-loss should be different from Entry."); + Print(TRANSLATION_MESSAGE_ENTRY_SL_DIFFERENT); return; } @@ -6011,13 +6243,9 @@ void GetSymbolAndAccountData() MaintenanceMargin = SymbolInfoDouble(Symbol(), SYMBOL_MARGIN_MAINTENANCE); if (MaintenanceMargin == 0) MaintenanceMargin = InitialMargin; - SwapsTripleDay = EnumToString((ENUM_DAY_OF_WEEK)SymbolInfoInteger(Symbol(), SYMBOL_SWAP_ROLLOVER3DAYS)); - string lowercase_part = StringSubstr(SwapsTripleDay, 1); - StringToLower(lowercase_part); - SwapsTripleDay = CharToString((uchar)SwapsTripleDay[0]) + lowercase_part; + SwapsTripleDay = WeekdayToString((int)SymbolInfoInteger(Symbol(), SYMBOL_SWAP_ROLLOVER3DAYS)); } - //+------------------------------------------------------------------+ //| Calculates risk size and position size. Sets object values. | //+------------------------------------------------------------------+ @@ -6169,7 +6397,7 @@ void CalculateRiskAndPositionSize() } else { - InputRR = "Invalid TP"; + InputRR = TRANSLATION_LABEL_WARNING_INVALID_TP; MainOutputRR = InputRR; } if (MainOutputRR == InputRR) InputRR = ""; @@ -6210,7 +6438,7 @@ void CalculateRiskAndPositionSize() } else { - AdditionalOutputRR[i - 1] = "Invalid TP"; + AdditionalOutputRR[i - 1] = TRANSLATION_LABEL_WARNING_INVALID_TP; } } else AdditionalOutputRR[i - 1] = ""; @@ -6233,12 +6461,12 @@ void CalculateRiskAndPositionSize() for (int i = 1; i < sets.TakeProfitsNumber; i++) { OutputReward += AdditionalOutputReward[i - 1]; - if ((AdditionalOutputRR[i - 1] == "Invalid TP") || (MainOutputRR == "Invalid TP")) OutputRR = "Invalid TP"; // At least one Invalid TP means that total RR is also invalid. + if ((AdditionalOutputRR[i - 1] == TRANSLATION_LABEL_WARNING_INVALID_TP) || (MainOutputRR == TRANSLATION_LABEL_WARNING_INVALID_TP)) OutputRR = TRANSLATION_LABEL_WARNING_INVALID_TP; // At least one Invalid TP means that total RR is also invalid. if ((OutputPositionSize > 0) && (ArrayPositionSize[i] > 0)) TotalOutputRisk += (OutputRiskMoney / OutputPositionSize * ArrayPositionSize[i]); TotalInputRisk += (RiskMoney * (double)sets.TPShare[i] / 100.0); InputReward = DoubleToString(StringToDouble(InputReward) + Round(RiskMoney * (double)sets.TPShare[i] / 100.0 * MathAbs(sets.TP[i] - tEntryLevel) / StopLoss, AccountCurrencyDigits, RoundDown), AccountCurrencyDigits); } - if (OutputRR != "Invalid TP") + if (OutputRR != TRANSLATION_LABEL_WARNING_INVALID_TP) { if (TotalOutputRisk != 0) OutputRR = DoubleToString(Round(OutputReward / TotalOutputRisk, 2, RoundDown), 2); else OutputRR = ""; @@ -6278,12 +6506,9 @@ double BrokerizePositionSize(const double position_size) return position_size; } -//+------------------------------------------------------------------+ -//| Calculates risk size and position size. Sets object values. | -//| Trading tab mode lets calculate quickly calculate percentage | -//| risk based on sets.AllSymbols to use when executing a trade. | -//+------------------------------------------------------------------+ -void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) +// Calculates risk size and position size. Sets object values. +// Trading tab mode lets calculate quickly calculate percentage risk either as total or for a given symbol to use when executing a trade. +void CalculatePortfolioRisk(const CALCULATE_RISK_FOR_TRADING_TAB calculate_risk_for_trading_tab = CALCULATE_RISK_FOR_TRADING_TAB_NO) { PortfolioLossMoney = 0; double PortfolioRewardMoney = 0; @@ -6303,7 +6528,7 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) { if ((OrderGetString(ORDER_SYMBOL) != Symbol()) && (sets.IgnoreOtherSymbols)) continue; } - else if ((OrderGetString(ORDER_SYMBOL) != Symbol()) && (!sets.AllSymbols)) continue; + else if ((OrderGetString(ORDER_SYMBOL) != Symbol()) && (calculate_risk_for_trading_tab == CALCULATE_RISK_FOR_TRADING_TAB_PER_SYMBOL)) continue; // Buy orders. if ((OrderGetInteger(ORDER_TYPE) == ORDER_TYPE_BUY_LIMIT) || (OrderGetInteger(ORDER_TYPE) == ORDER_TYPE_BUY_STOP)) @@ -6373,7 +6598,7 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) ENUM_POSITION_TYPE dir = POSITION_TYPE_BUY; if ((order_type == ORDER_TYPE_BUY_LIMIT) || (order_type == ORDER_TYPE_BUY_STOP) || (order_type == ORDER_TYPE_BUY_STOP_LIMIT)) dir = POSITION_TYPE_BUY; else if ((order_type == ORDER_TYPE_SELL_LIMIT) || (order_type == ORDER_TYPE_SELL_STOP) || (order_type == ORDER_TYPE_SELL_STOP_LIMIT)) dir = POSITION_TYPE_SELL; - double CCC = CalculateAdjustment(Loss, symbol_profit_currency, AccountCurrency); + double CCC = CalculateAdjustment(Loss, symbol_profit_currency, AccountCurrency, Symbol_order); // Adjust the unit cost. UnitCost *= CCC; } @@ -6383,7 +6608,7 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) double TickSize_local = SymbolInfoDouble(Symbol_order, SYMBOL_TRADE_TICK_SIZE); if (TickSize_local == 0) { - Print("Cannot retrieve tick size for ", Symbol_order, ". Looks like the instrument is no longer available. Calculation may not be accurate."); + Print(TRANSLATION_MESSAGE_CANNOT_RETRIEVE_TICKSIZE, Symbol_order, ". " + TRANSLATION_MESSAGE_LOOKS_LIKE); } else { @@ -6427,7 +6652,7 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) ENUM_POSITION_TYPE dir = POSITION_TYPE_BUY; if ((order_type == ORDER_TYPE_BUY_LIMIT) || (order_type == ORDER_TYPE_BUY_STOP) || (order_type == ORDER_TYPE_BUY_STOP_LIMIT)) dir = POSITION_TYPE_BUY; else if ((order_type == ORDER_TYPE_SELL_LIMIT) || (order_type == ORDER_TYPE_SELL_STOP) || (order_type == ORDER_TYPE_SELL_STOP_LIMIT)) dir = POSITION_TYPE_SELL; - double CCC = CalculateAdjustment(Profit, symbol_profit_currency, AccountCurrency); + double CCC = CalculateAdjustment(Profit, symbol_profit_currency, AccountCurrency, Symbol_order); // Adjust the unit cost. UnitCost *= CCC; } @@ -6437,7 +6662,7 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) double TickSize_local = SymbolInfoDouble(Symbol_order, SYMBOL_TRADE_TICK_SIZE); if (TickSize_local == 0) { - Print("Cannot retrieve tick size for ", Symbol_order, ". Looks like the instrument is no longer available. Calculation may not be accurate."); + Print(TRANSLATION_MESSAGE_CANNOT_RETRIEVE_TICKSIZE, Symbol_order, ". " + TRANSLATION_MESSAGE_LOOKS_LIKE); } else { @@ -6466,14 +6691,12 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) // Infinite profit. PortfolioRewardMoney = DBL_MAX; } - //if ((PortfolioLossMoney == DBL_MAX) && (PortfolioRewardMoney == DBL_MAX)) break; Can't do it - there is volume calculation to be done. } } int total = PositionsTotal(); for (int i = 0; i < total; i++) { - //if ((PortfolioLossMoney == DBL_MAX) && (PortfolioRewardMoney == DBL_MAX)) break; Can't do it - there is volume calculation to be done. double PointsLoss = 0; double PointsReward = 0; // Works with hedging and netting. @@ -6484,8 +6707,8 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) { if ((PositionGetString(POSITION_SYMBOL) != Symbol()) && (sets.IgnoreOtherSymbols)) continue; } - else if ((PositionGetString(POSITION_SYMBOL) != Symbol()) && (!sets.AllSymbols)) continue; - + else if ((PositionGetString(POSITION_SYMBOL) != Symbol()) && (calculate_risk_for_trading_tab == CALCULATE_RISK_FOR_TRADING_TAB_PER_SYMBOL)) continue; + // Buy position. if (PositionGetInteger(POSITION_TYPE) == POSITION_TYPE_BUY) { @@ -6551,7 +6774,7 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) if (symbol_profit_currency != AccountCurrency) { ENUM_POSITION_TYPE dir = (ENUM_POSITION_TYPE)PositionGetInteger(POSITION_TYPE); - double CCC = CalculateAdjustment(Loss, symbol_profit_currency, AccountCurrency); + double CCC = CalculateAdjustment(Loss, symbol_profit_currency, AccountCurrency, Symbol_position); // Adjust the unit cost. UnitCost *= CCC; } @@ -6596,7 +6819,7 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) if (symbol_profit_currency != AccountCurrency) { ENUM_POSITION_TYPE dir = (ENUM_POSITION_TYPE)PositionGetInteger(POSITION_TYPE); - double CCC = CalculateAdjustment(Profit, symbol_profit_currency, AccountCurrency); + double CCC = CalculateAdjustment(Profit, symbol_profit_currency, AccountCurrency, Symbol_position); // Adjust the unit cost. UnitCost *= CCC; } @@ -6635,28 +6858,28 @@ void CalculatePortfolioRisk(const bool calculate_risk_for_trading_tab = false) // If account size did not load yet. if (AccSize == 0) return; - if (PortfolioLossMoney == DBL_MAX) PLM = " Infinity"; + if (PortfolioLossMoney == DBL_MAX) PLM = "\x221E"; else PLM = FormatDouble(DoubleToString(PortfolioLossMoney, AccountCurrencyDigits), AccountCurrencyDigits); - if (PortfolioLossMoney == DBL_MAX) CPR = " Infinity"; + if (PortfolioLossMoney == DBL_MAX) CPR = "\x221E"; else CPR = FormatDouble(DoubleToString(PortfolioLossMoney / AccSize * 100, 2)); - if (PortfolioLossMoney == DBL_MAX) PPMR = " Infinity"; + if (PortfolioLossMoney == DBL_MAX) PPMR = "\x221E"; else PPMR = FormatDouble(DoubleToString(PortfolioLossMoney + OutputRiskMoney, AccountCurrencyDigits), AccountCurrencyDigits); - if (PortfolioLossMoney == DBL_MAX) PPR = " Infinity"; + if (PortfolioLossMoney == DBL_MAX) PPR = "\x221E"; else PPR = FormatDouble(DoubleToString((PortfolioLossMoney + OutputRiskMoney) / AccSize * 100, 2)); - if (PortfolioRewardMoney == DBL_MAX) PRM = " Infinity"; + if (PortfolioRewardMoney == DBL_MAX) PRM = "\x221E"; else PRM = FormatDouble(DoubleToString(PortfolioRewardMoney, AccountCurrencyDigits), AccountCurrencyDigits); - if (PortfolioRewardMoney == DBL_MAX) CPRew = " Infinity"; + if (PortfolioRewardMoney == DBL_MAX) CPRew = "\x221E"; else CPRew = FormatDouble(DoubleToString(PortfolioRewardMoney / AccSize * 100, 2)); - if ((PortfolioRewardMoney == DBL_MAX) || (OutputReward == 0)) PPMRew = " Infinity"; + if ((PortfolioRewardMoney == DBL_MAX) || (OutputReward == 0)) PPMRew = "\x221E"; else PPMRew = FormatDouble(DoubleToString(PortfolioRewardMoney + OutputReward, AccountCurrencyDigits), AccountCurrencyDigits); - if ((PortfolioRewardMoney == DBL_MAX) || (OutputReward == 0)) PPRew = " Infinity"; + if ((PortfolioRewardMoney == DBL_MAX) || (OutputReward == 0)) PPRew = "\x221E"; else PPRew = FormatDouble(DoubleToString((PortfolioRewardMoney + OutputReward) / AccSize * 100, 2)); CPL = FormatDouble(DoubleToString(volume, LotStep_digits), LotStep_digits); @@ -6710,7 +6933,7 @@ void CalculateMargin() PositionMargin = (OutputPositionSize * ContractSize * PriceCorrectionCoefficient / Leverage) * maintenance_margin_rate; // Otherwise, no need to adjust margin. - if (AccountCurrency != MarginCurrency) CurrencyCorrectionCoefficient = CalculateAdjustment(Loss, MarginCurrency, AccountCurrency); + if (AccountCurrency != MarginCurrency) CurrencyCorrectionCoefficient = CalculateAdjustment(Loss, MarginCurrency, AccountCurrency, Symbol()); if (CurrencyCorrectionCoefficient == 0) // Couldn't calculate correction coefficient due to the lack of the required currency pair. { CurrencyCorrectionCoefficient = 1; @@ -6939,8 +7162,9 @@ void CalculateMargin() //+-----------------------------------------------------------------------------------+ //| Calculates necessary adjustments for cases when GivenCurrency != AccountCurrency. | //| Used in two cases: profit adjustment and margin adjustment. | +//| symbol is used only to store information about warnings. | //+-----------------------------------------------------------------------------------+ -double CalculateAdjustment(PROFIT_LOSS calc_mode, const string CCY1, const string CCY2) +double CalculateAdjustment(PROFIT_LOSS calc_mode, const string CCY1, const string CCY2, const string symbol) { MqlTick tick; string ReferencePair = NULL; @@ -6983,10 +7207,28 @@ double CalculateAdjustment(PROFIT_LOSS calc_mode, const string CCY1, const strin } } - // Get the cross rate through US dollar. - return CalculateAdjustment(calc_mode, CCY1, "USD") * CalculateAdjustment(calc_mode, "USD", CCY2); + // Get the cross rate through US dollar, but only if it's not USD it is trying to find the rate for. + if ((CCY1 != "USD") && (CCY2 != "USD")) return CalculateAdjustment(calc_mode, CCY1, "USD", symbol) * CalculateAdjustment(calc_mode, "USD", CCY2, symbol); } - return 0; + // Check if there has already been a warning about this case and warn if there hasn't been one. + bool already_warned = false; + int array_size = ArraySize(WarnedSymbols); + string combination = CCY1 + CCY2 + symbol; + for (int i = 0; i < array_size; i++) + { + if (WarnedSymbols[i] == combination) // Already warned. + { + already_warned = true; + break; + } + } + if (!already_warned) // Warn. + { + Print(TRANSLATION_MESSAGE_CANNOT_CONVERT, " ", CCY1, " ", TRANSLATION_MESSAGE_CANNOT_CONVERT_TO, " ", CCY2, ". ", TRANSLATION_MESSAGE_CANNOT_CONVERT_CALCULATION, " ", symbol); + ArrayResize(WarnedSymbols, array_size + 1); // Increase the array size. + WarnedSymbols[array_size] = combination; // Remember the symbol/currencies combination. + } + return 1; } //+---------------------------------------------------------------------------+ @@ -7063,14 +7305,14 @@ void GetSwapData() { // Disabled case SYMBOL_SWAP_MODE_DISABLED: - OutputSwapsType = "Disabled"; + OutputSwapsType = TRANSLATION_LABEL_DISABLED; swap_long_1_lot = 0; swap_short_1_lot = 0; break; // Points case SYMBOL_SWAP_MODE_POINTS: { - OutputSwapsType = "Points"; + OutputSwapsType = TRANSLATION_LABEL_POINTS; double UnitCost_long, UnitCost_short; @@ -7100,12 +7342,12 @@ void GetSwapData() if (swap_mode == SYMBOL_SWAP_MODE_CURRENCY_SYMBOL) { base_or_margin_currency = SymbolInfoString(Symbol(), SYMBOL_CURRENCY_BASE); - OutputSwapsType = "Base currency (" + base_or_margin_currency + ")"; + OutputSwapsType = TRANSLATION_LABEL_BASE_CURRENCY + " (" + base_or_margin_currency + ")"; } else { base_or_margin_currency = SymbolInfoString(Symbol(), SYMBOL_CURRENCY_MARGIN); - OutputSwapsType = "Margin currency (" + base_or_margin_currency + ")"; + OutputSwapsType = TRANSLATION_LABEL_MARGIN_CURRENCY + " (" + base_or_margin_currency + ")"; } // Simple case: if (AccountCurrency == base_or_margin_currency) @@ -7126,11 +7368,9 @@ void GetSwapData() // Go through Market Watch trying to find the currency pair with both base_currency and account_currency in it. else { - double CCC = CalculateAdjustment(Profit, base_or_margin_currency, AccountCurrency); + double CCC = CalculateAdjustment(Profit, base_or_margin_currency, AccountCurrency, Symbol()); swap_long_1_lot = swap_long * CCC; swap_short_1_lot = swap_short * CCC; - - } } } @@ -7140,8 +7380,8 @@ void GetSwapData() case SYMBOL_SWAP_MODE_INTEREST_CURRENT: { if (TickSize == 0) return; - if (swap_mode == SYMBOL_SWAP_MODE_INTEREST_OPEN) OutputSwapsType = "Interest (Open)"; - else if (swap_mode == SYMBOL_SWAP_MODE_INTEREST_CURRENT) OutputSwapsType = "Interest (Current)"; + if (swap_mode == SYMBOL_SWAP_MODE_INTEREST_OPEN) OutputSwapsType = TRANSLATION_LABEL_INTEREST_OPEN; + else if (swap_mode == SYMBOL_SWAP_MODE_INTEREST_CURRENT) OutputSwapsType = TRANSLATION_LABEL_INTEREST_CURRENT; double symbol_cost_1_lot_profit, symbol_cost_1_lot_loss; // CFD. @@ -7155,8 +7395,8 @@ void GetSwapData() symbol_cost_1_lot_profit = symbol_cost_1_lot_loss; if (ProfitCurrency != AccountCurrency) { - double CCC_loss = CalculateAdjustment(Loss, ProfitCurrency, AccountCurrency); - double CCC_profit = CalculateAdjustment(Profit, ProfitCurrency, AccountCurrency); + double CCC_loss = CalculateAdjustment(Loss, ProfitCurrency, AccountCurrency, Symbol()); + double CCC_profit = CalculateAdjustment(Profit, ProfitCurrency, AccountCurrency, Symbol()); // Adjust the unit cost. symbol_cost_1_lot_profit = symbol_cost_1_lot_loss * CCC_profit; symbol_cost_1_lot_loss = symbol_cost_1_lot_loss * CCC_loss; @@ -7205,7 +7445,7 @@ void GetSwapData() // Reopen - impossible to predict case SYMBOL_SWAP_MODE_REOPEN_CURRENT: case SYMBOL_SWAP_MODE_REOPEN_BID: - OutputSwapsType = "Reopening"; + OutputSwapsType = TRANSLATION_LABEL_REOPENING; break; default: break; @@ -7214,17 +7454,17 @@ void GetSwapData() { OutputSwapsDailyLongLot = FormatDouble(DoubleToString(swap_long_1_lot, AccountCurrencyDigits), AccountCurrencyDigits); OutputSwapsDailyShortLot = FormatDouble(DoubleToString(swap_short_1_lot, AccountCurrencyDigits), AccountCurrencyDigits); - OutputSwapsCurrencyDailyLot = AccountCurrency + " per lot"; + OutputSwapsCurrencyDailyLot = AccountCurrency + " " + TRANSLATION_LABEL_PER_LOT; OutputSwapsDailyLongPS = FormatDouble(DoubleToString(swap_long_1_lot * OutputPositionSize, AccountCurrencyDigits), AccountCurrencyDigits); OutputSwapsDailyShortPS = FormatDouble(DoubleToString(swap_short_1_lot * OutputPositionSize, AccountCurrencyDigits), AccountCurrencyDigits); - OutputSwapsCurrencyDailyPS = AccountCurrency + " per PS (" + DoubleToString(OutputPositionSize, 2) + ")"; + OutputSwapsCurrencyDailyPS = AccountCurrency + " " + TRANSLATION_LABEL_PER_PS + " (" + DoubleToString(OutputPositionSize, 2) + ")"; OutputSwapsYearlyLongLot = FormatDouble(DoubleToString(swap_long_1_lot * 360, AccountCurrencyDigits), AccountCurrencyDigits); OutputSwapsYearlyShortLot = FormatDouble(DoubleToString(swap_short_1_lot * 360, AccountCurrencyDigits), AccountCurrencyDigits); - OutputSwapsCurrencyYearlyLot = AccountCurrency + " per lot"; + OutputSwapsCurrencyYearlyLot = AccountCurrency + " " + TRANSLATION_LABEL_PER_LOT; OutputSwapsYearlyLongPS = FormatDouble(DoubleToString(swap_long_1_lot * 360 * OutputPositionSize, AccountCurrencyDigits), AccountCurrencyDigits); OutputSwapsYearlyShortPS = FormatDouble(DoubleToString(swap_short_1_lot * 360 * OutputPositionSize, AccountCurrencyDigits), AccountCurrencyDigits); - OutputSwapsCurrencyYearlyPS = AccountCurrency + " per PS (" + DoubleToString(OutputPositionSize, 2) + ")"; + OutputSwapsCurrencyYearlyPS = AccountCurrency + " " + TRANSLATION_LABEL_PER_PS + " (" + DoubleToString(OutputPositionSize, 2) + ")"; } } @@ -7286,7 +7526,7 @@ int CountDecimalPlaces(double number) //+------------------------------------------------------------------+ //| Draws a label for a line with a geiven text. | //+------------------------------------------------------------------+ -void DrawLineLabel(const string label, const string text, const double price, const color col, bool above = false) +void DrawLineLabel(const string label, const string text, const double price, const color col, bool above = false, int font_size_modifier = 0) { // Data not loaded yet. if (Bars(Symbol(), Period()) <= 0) return; @@ -7296,18 +7536,19 @@ void DrawLineLabel(const string label, const string text, const double price, co uint w, h; ObjectSetString(0, label, OBJPROP_TEXT, text); - ObjectSetInteger(0, label, OBJPROP_FONTSIZE, font_size); + ObjectSetInteger(0, label, OBJPROP_FONTSIZE, font_size + font_size_modifier); ObjectSetString(0, label, OBJPROP_FONT, font_face); ObjectSetInteger(0, label, OBJPROP_COLOR, col); real_x = ChartGetInteger(0, CHART_WIDTH_IN_PIXELS) - 2; // Needed only for y, x is derived from the chart width. ChartTimePriceToXY(0, 0, iTime(Symbol(), Period(), 0), price, x, y); // Get the width of the text based on font and its size. Negative because OS-dependent, *10 because set in 1/10 of pt. - TextSetFont(font_face, font_size * -10); + TextSetFont(font_face, (font_size + font_size_modifier) * -10); TextGetSize(text, w, h); ObjectSetInteger(0, label, OBJPROP_XDISTANCE, real_x - w); if (above) y -= int(h + 1); ObjectSetInteger(0, label, OBJPROP_YDISTANCE, y); + ChartRedraw(); } @@ -7345,10 +7586,10 @@ void CalculateUnitCost(double &UnitCost_loss, double &UnitCost_profit) // If profit currency is different from account currency. if (ProfitCurrency != AccountCurrency) { - double CCC = CalculateAdjustment(Loss, ProfitCurrency, AccountCurrency); + double CCC = CalculateAdjustment(Loss, ProfitCurrency, AccountCurrency, Symbol()); // Adjust the unit cost. UnitCost_loss *= CCC; - CCC = CalculateAdjustment(Profit, ProfitCurrency, AccountCurrency); + CCC = CalculateAdjustment(Profit, ProfitCurrency, AccountCurrency, Symbol()); UnitCost_profit *= CCC; } } @@ -7437,9 +7678,13 @@ void DissectHotKeyCombination(const string hotkey, bool &shift_required, bool &c void WarnAboutZeroUnitCost() { - static bool was_alert = false; - if (!was_alert) Alert("Misconfigured symbol on trading server - zero unit cost."); - was_alert = true; + if (WarnedAboutZeroUnitCost == 1) // Issue the actual alert only after the first dry run, to avoid sending an alert when symbol data is still loading. + { + if (WarnedAboutZeroUnitCost != 2) Alert(TRANSLATION_MESSAGE_MISCONFIGURED_SYMBOL); + WarnedAboutZeroUnitCost = 2; + return; + } + if (WarnedAboutZeroUnitCost != 2) WarnedAboutZeroUnitCost = 1; } double CalculateCommission() @@ -7465,7 +7710,7 @@ double CalculateCommission() else // E.g., GBP/JPY. { // Conversion needed: - double ccc = CalculateAdjustment(Loss, BaseCurrency, AccountCurrency); + double ccc = CalculateAdjustment(Loss, BaseCurrency, AccountCurrency, Symbol()); ContractValue = contract_size * ccc; } } @@ -7480,7 +7725,7 @@ double CalculateCommission() else // E.g., trading Nikkei on a USD account. { // Conversion needed: - double ccc = CalculateAdjustment(Loss, BaseCurrency, AccountCurrency); + double ccc = CalculateAdjustment(Loss, BaseCurrency, AccountCurrency, Symbol()); ContractValue = contract_size * ccc; } } @@ -7488,4 +7733,19 @@ double CalculateCommission() } return commission; } + +string WeekdayToString(int weekday) +{ + switch(weekday) + { + case 0: return TRANSLATION_EDIT_WEEKDAY_SUNDAY; + case 1: return TRANSLATION_EDIT_WEEKDAY_MONDAY; + case 2: return TRANSLATION_EDIT_WEEKDAY_TUESDAY; + case 3: return TRANSLATION_EDIT_WEEKDAY_WEDNESDAY; + case 4: return TRANSLATION_EDIT_WEEKDAY_THURSDAY; + case 5: return TRANSLATION_EDIT_WEEKDAY_FRIDAY; + case 6: return TRANSLATION_EDIT_WEEKDAY_SATURDAY; + } + return TRANSLATION_MESSAGE_ERROR; +} //+------------------------------------------------------------------+ \ No newline at end of file diff --git a/MQL5/Experts/Position Sizer/Translations/English.mqh b/MQL5/Experts/Position Sizer/Translations/English.mqh new file mode 100644 index 0000000..9ac3a89 --- /dev/null +++ b/MQL5/Experts/Position Sizer/Translations/English.mqh @@ -0,0 +1,303 @@ +// Tabs +#define TRANSLATION_TAB_BUTTON_MAIN "Main" +#define TRANSLATION_TAB_BUTTON_RISK "Risk" +#define TRANSLATION_TAB_BUTTON_MARGIN "Margin" +#define TRANSLATION_TAB_BUTTON_SWAPS "Swaps" +#define TRANSLATION_TAB_BUTTON_TRADING "Trading" + +// Caption +#define TRANSLATION_LABEL_SPREAD "Spread" + +// Main tab +// Entry +#define TRANSLATION_LABEL_ENTRY "Entry" +#define TRANSLATION_BUTTON_LONG "Long" +#define TRANSLATION_BUTTON_SHORT "Short" + +#define TRANSLATION_TOOLTIP_BUTTON_LONG_SHORT "Switch between Long and Short" + +#define TRANSLATION_TOOLTIP_ENTRY_INCREASE "Increase Entry by 1 point" +#define TRANSLATION_TOOLTIP_ENTRY_DECREASE "Decrease Entry by 1 point" + +// Stop-loss +#define TRANSLATION_LABEL_STOPLOSS "Stop-loss" +#define TRANSLATION_BUTTON_SL "SL, points" + +#define TRANSLATION_TOOLTIP_STOPLOSS_INCREASE "Increase Stop-loss by 1 point" +#define TRANSLATION_TOOLTIP_STOPLOSS_DECREASE "Decrease Stop-loss by 1 point" + +// Take-profit +#define TRANSLATION_LABEL_TAKEPROFIT "Take-profit" +#define TRANSLATION_BUTTON_TP "TP, points" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_ADD "Add a take-profit level" +#define TRANSLATION_TOOLTIP_BUTTON_TP "Set TP based on SL or enable locked TP mode" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE "Increase Take-profit by 1 point" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_DECREASE "Decrease Take-profit by 1 point" + +#define TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE "TP" +#define TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_POINTS "points" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_REMOVE "Remove Take-profit" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE_MULTIPLE "Increase Take-profit" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_DECREASE_MULTIPLE "Decrease Take-profit" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_BY_ONE_POINT "by 1 point" + +// Stop price +#define TRANSLATION_LABEL_STOPPRICE "Stop price" + +#define TRANSLATION_TOOLTIP_STOPPRICE_INCREASE "Increase Stop price by 1 point" +#define TRANSLATION_TOOLTIP_STOPPRICE_DECREASE "Decrease Stop price by 1 point" + +// ATR options +#define TRANSLATION_LABEL_ATR_PERIOD "ATR period" +#define TRANSLATION_BUTTON_ATR_PERIOD_CURRENT "CURRENT" +#define TRANSLATION_LABEL_ATR_SL_MULTIPLIER "SL multiplier" +#define TRANSLATION_LABEL_ATR_TP_MULTIPLIER "TP multiplier" + +#define TRANSLATION_CHECKBOX_ATR_SA "SA" +#define TRANSLATION_TOOLTIP_ATR_SA_SL "Apply spread adjustment to stop-loss" +#define TRANSLATION_TOOLTIP_ATR_SA_TP "Apply spread adjustment to take-profit" + +#define TRANSLATION_LABEL_ATR_TIMEFRAME "ATR timeframe" +#define TRANSLATION_LABEL_ATR_VALUE "ATR" + +// Order type +#define TRANSLATION_LABEL_ORDER_TYPE "Order type" +#define TRANSLATION_BUTTON_ORDER_TYPE_INSTANT "Instant" +#define TRANSLATION_BUTTON_ORDER_TYPE_PENDING "Pending" +#define TRANSLATION_BUTTON_ORDER_TYPE_STOPLIMIT "Stop Limit" +#define TRANSLATION_TOOLTIP_ORDER_TYPE "Switch between Instant, Pending, and Stop Limit" + +// Hide/show lines +#define TRANSLATION_BUTTON_HIDE_LINES "Hide lines" +#define TRANSLATION_BUTTON_SHOW_LINES "Show lines" + +// Commission +#define TRANSLATION_LABEL_COMMISSION "Commission (one-way) per lot" +#define TRANSLATION_TOOLTIP_COMMISSION "In account currency or %, per 1 standard lot" +#define TRANSLATION_TOOLTIP_COMMISSION_TYPE "Click to switch" + +// Account size +#define TRANSLATION_BUTTON_ACCOUNT_BALANCE "Account balance" +#define TRANSLATION_BUTTON_ACCOUNT_EQUITY "Account equity" +#define TRANSLATION_BUTTON_BALANCE_MINUS_CPR "Balance - CPR" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE "Switch between balance, equity, and balance minus current portfolio risk" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_CUSTOM "Custom balance set" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_ADD "additional funds" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_SUB "funds subtracted" + +// Calculations +#define TRANSLATION_LABEL_INPUT "Input" +#define TRANSLATION_LABEL_RESULT "Result" +#define TRANSLATION_LABEL_RISK "Risk" +#define TRANSLATION_LABEL_MONEY "money" +#define TRANSLATION_LABEL_REWARD "Reward" +#define TRANSLATION_LABEL_REWARD_RISK "Reward/risk" +#define TRANSLATION_LABEL_POSITION_SIZE "Position size" +#define TRANSLATION_BUTTON_MAX_PS "Max PS" +#define TRANSLATION_LABEL_POINT_VALUE "Point value" + + +// Risk tab +#define TRANSLATION_CHECKBOX_COUNT_PENDING_ORDERS "Count pending orders" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_WO_SL "Ignore orders without stop-loss" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_WO_TP "Ignore orders without take-profit" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_IN_OTHER_SYMBOLS "Ignore orders in other symbols" +#define TRANSLATION_LABEL_LOTS "Lots" +#define TRANSLATION_LABEL_CURRENT_PORTFOLIO "Current portfolio" +#define TRANSLATION_TOOLTIP_CURRENT_PORTFOLIO "Trades that are currently open" +#define TRANSLATION_LABEL_POTENTIAL_PORTFOLIO "Potential portfolio" +#define TRANSLATION_TOOLTIP_POTENTIAL_PORTFOLIO "Including the position being calculated" + + +// Margin tab +#define TRANSLATION_LABEL_POSITION_MARGIN "Position margin" +#define TRANSLATION_LABEL_FUTURE_USED_MARGIN "Future used margin" +#define TRANSLATION_LABEL_FUTURE_FREE_MARGIN "Future free margin" +#define TRANSLATION_LABEL_CUSTOM_LEVERAGE "Custom leverage" +#define TRANSLATION_LABEL_DEFAULT "Default" +#define TRANSLATION_LABEL_SYMBOL "Symbol" +#define TRANSLATION_LABEL_MAX_PS_BY_MARGIN "Maximum position size by margin" +#define TRANSLATION_TOOLTIP_MAX_PS_BY_MARGIN "In lots" + + +// Swaps tab +#define TRANSLATION_LABEL_TYPE "Type" +#define TRANSLATION_LABEL_UNKNOWN "Unknown" +#define TRANSLATION_LABEL_DISABLED "Disabled" +#define TRANSLATION_LABEL_INTEREST_OPEN "Interest (Open)" +#define TRANSLATION_LABEL_INTEREST_CURRENT "Interest (Current)" +#define TRANSLATION_LABEL_REOPENING "Reopening" +#define TRANSLATION_LABEL_TRIPLE_SWAP "Triple swap" +#define TRANSLATION_EDIT_WEEKDAY_SUNDAY "Sunday" +#define TRANSLATION_EDIT_WEEKDAY_MONDAY "Monday" +#define TRANSLATION_EDIT_WEEKDAY_TUESDAY "Tuesday" +#define TRANSLATION_EDIT_WEEKDAY_WEDNESDAY "Wednesday" +#define TRANSLATION_EDIT_WEEKDAY_THURSDAY "Thursday" +#define TRANSLATION_EDIT_WEEKDAY_FRIDAY "Friday" +#define TRANSLATION_EDIT_WEEKDAY_SATURDAY "Saturday" +#define TRANSLATION_LABEL_NOMINAL "Nominal" +#define TRANSLATION_LABEL_DAILY "Daily" +#define TRANSLATION_LABEL_YEARLY "Yearly" +#define TRANSLATION_LABEL_PER_LOT "per lot" +#define TRANSLATION_LABEL_PER_PS "per PS" +#define TRANSLATION_LABEL_BASE_CURRENCY "Base currency" +#define TRANSLATION_LABEL_MARGIN_CURRENCY "Margin currency" + + +// Trading tab +#define TRANSLATION_BUTTON_TRADE "Trade" +#define TRANSLATION_LABEL_TRAILING_STOP "Trailing stop" +#define TRANSLATION_LABEL_BREAKEVEN "Breakeven" +#define TRANSLATION_LABEL_MAGIC_NUMBER "Magic number" +#define TRANSLATION_LABEL_ORDER_COMMENTARY "Order commentary" +#define TRANSLATION_LABEL_ORDER_AUTOSUFFIX "Auto-suffix" +#define TRANSLATION_TOOLTIP_ORDER_AUTOSUFFIX "Add an automatically incremented number to a commentary of each new trade?" +#define TRANSLATION_LABEL_MAX_NUMBER_OF_TRADES "Max # of trades" +#define TRANSLATION_LABEL_TOTAL "Total" +#define TRANSLATION_LABEL_PER_SYMBOL "Per symbol" +#define TRANSLATION_LABEL_MAX_VOLUME "Max volume" +#define TRANSLATION_LABEL_MAX_RISK "Max risk" +#define TRANSLATION_CHECKBOX_DISABLE_TRADING_LINES_HIDDEN "Disable trading when lines are hidden" +#define TRANSLATION_TOOLTIP_FILL_INWARD "Fill additional TPs equidistantly between Entry and Main TP." +#define TRANSLATION_TOOLTIP_FILL_OUTWARD "Place additional TPs beyond the Main TP using the same distance." +#define TRANSLATION_LABEL_SHARE "Share" +#define TRANSLATION_TOOLTIP_SHARE "Automatically fill the volume shares" +#define TRANSLATION_LABEL_POINTS "Points" +#define TRANSLATION_LABEL_MAX_SLIPPAGE "Max slippage" +#define TRANSLATION_LABEL_MAX_SPREAD "Max spread" +#define TRANSLATION_LABEL_MAX_ENTRY_SL_DISTANCE "Max Entry/SL distance" +#define TRANSLATION_LABEL_MIN_ENTRY_SL_DISTANCE "Min Entry/SL distance" +#define TRANSLATION_CHECKBOX_SUBTRACT_OPEN_POSITIONS_VOLUME "Subtract open positions volume" +#define TRANSLATION_CHECKBOX_SUBTRACT_PENDING_ORDERS_VOLUME "Subtract pending orders volume" +#define TRANSLATION_CHECKBOX_DO_NOT_APPLY_STOPLOSS "Do not apply stop-loss" +#define TRANSLATION_CHECKBOX_DO_NOT_APPLY_TAKEPROFIT "Do not apply take-profit" +#define TRANSLATION_TOOLTIP_SUBTRACT_OPEN_POSITIONS_VOLUME "The EA will subtract currently open trades' volume from the calculated position size before opening a trade." +#define TRANSLATION_TOOLTIP_SUBTRACT_PENDING_ORDERS_VOLUME "The EA will subtract pending orders' volume from the calculated position size before opening a trade." +#define TRANSLATION_TOOLTIP_DO_NOT_APPLY_STOPLOSS "The EA won't apply stop-loss to the trade it opens." +#define TRANSLATION_TOOLTIP_DO_NOT_APPLY_TAKEPROFIT "The EA won't apply take-profit to the trade it opens." +#define TRANSLATION_CHECKBOX_ASK_FOR_CONFIRMATION "Ask for confirmation" +#define TRANSLATION_TOOLTIP_ASK_FOR_CONFIRMATION "The EA will ask for confirmation before opening a trade." + + +// Chart objects +#define TRANSLATION_TOOLTIP_STOP_PRICE_LINE "Stop Price (for Stop Limit orders)" +#define TRANSLATION_TOOLTIP_SL_LABEL "SL Distance, points" +#define TRANSLATION_TOOLTIP_TP_LABEL "TP Distance, points" +#define TRANSLATION_TOOLTIP_ENTRY_LABEL "Entry Distance, points" +#define TRANSLATION_TOOLTIP_STOP_PRICE_LABEL "Stop Price Distance, points" + + +// Warnings +#define TRANSLATION_LABEL_WARNING_TOO_CLOSE "(Too close!)" +#define TRANSLATION_LABEL_WARNING_WRONG_VALUE "(Wrong value!)" +#define TRANSLATION_LABEL_WARNING_INVALID_TP "Invalid TP" +#define TRANSLATION_TOOLTIP_WARNING_PS "Greater than maximum position size by margin!" + +// Messages +#define TRANSLATION_MESSAGE_SL_SHOULD_BE_POSITIVE "Stop-loss should be positive." +#define TRANSLATION_MESSAGE_TRYING_TO_SAVE_FILE "Trying to save settings to file" +#define TRANSLATION_MESSAGE_FAILED_TO_OPEN_FOR_WRITING "Failed to open file for writing" +#define TRANSLATION_MESSAGE_ERROR "Error" +#define TRANSLATION_MESSAGE_SAVED_SETTINGS "Saved settings successfully." +#define TRANSLATION_MESSAGE_TRYING_TO_LOAD_FILE "Trying to load settings from file." +#define TRANSLATION_MESSAGE_NO_SETTINGS_FILE_TO_LOAD "No settings file to load." +#define TRANSLATION_MESSAGE_FAILED_TO_OPEN_FOR_READING "Failed to open file for reading" +#define TRANSLATION_MESSAGE_LOADED_SETTINGS "Loaded settings successfully." +#define TRANSLATION_MESSAGE_NO_SETTINGS_FILE_TO_DELETE "No settings file to delete." +#define TRANSLATION_MESSAGE_TRYING_TO_DELETE_FILE "Trying to delete settings file." +#define TRANSLATION_MESSAGE_FAILED_TO_DELETE_FILE "Failed to delete file" +#define TRANSLATION_MESSAGE_DELETED_SETTINGS "Deleted settings file successfully." +#define TRANSLATION_MESSAGE_DELETED_DUPLICATE_PANEL "Deleted duplicate panel objects with prefix" +#define TRANSLATION_MESSAGE_FAILED_TO_CREATE_ATR "Failed to create ATR handle" +#define TRANSLATION_MESSAGE_ENTRY_SL_DIFFERENT_NON_ZERO "Entry and Stop-Loss levels should be different and non-zero." +#define TRANSLATION_MESSAGE_ENTRY_SL_DIFFERENT "Stop-loss should be different from Entry." +#define TRANSLATION_MESSAGE_CANNOT_RETRIEVE_TICKSIZE "Cannot retrieve tick size for " +#define TRANSLATION_MESSAGE_LOOKS_LIKE "Looks like the instrument is no longer available. Calculation may not be accurate." +#define TRANSLATION_MESSAGE_MISCONFIGURED_SYMBOL "Misconfigured symbol on trading server - zero unit cost." +#define TRANSLATION_MESSAGE_ALGO_TRADING_DISABLED "Algo Trading disabled! Please enable Algo Trading." +#define TRANSLATION_MESSAGE_STOPLOSS_PROBLEM "Stop-loss problem" +#define TRANSLATION_MESSAGE_WRONG_POSITION_SIZE_VALUE "Wrong position size value!" +#define TRANSLATION_MESSAGE_MULTIPLE_TP_VOLUME_SHARE_SUM "Multiple TP volume share sum" +#define TRANSLATION_MESSAGE_INCORRECT_VOLUME_SUM "Incorrect volume sum for multiple TPs - not taking any trades." +#define TRANSLATION_MESSAGE_NETTING_MODE_DETECTED "Netting mode detected. Multiple TPs won't work. Setting one TP at 100% volume." +#define TRANSLATION_MESSAGE_NOT_TAKING_A_TRADE "Not taking a trade" +#define TRANSLATION_MESSAGE_NTAT_LINES "lines are hidden and panel is set not to trade when they are hidden." +#define TRANSLATION_MESSAGE_NTAT_SPREAD "current spread" +#define TRANSLATION_MESSAGE_MAXIMUM_SPREAD "maximum spread" +#define TRANSLATION_MESSAGE_NTAT_ENTRY_SL_DISTANCE "current Entry/SL distance" +#define TRANSLATION_MESSAGE_NTAT_TOTAL_NUMBER "current total # of trades" +#define TRANSLATION_MESSAGE_NUMBER_OF_TRADES_IN_EXECUTION "number of trades in execution" +#define TRANSLATION_MESSAGE_MAXIMUM_TOTAL_NUMBER_OF_TRADES_ALLOWED "maximum total number of trades allowed" +#define TRANSLATION_MESSAGE_NTAT_PER_SYMBOL_NUMBER "current # of trades per symbol" +#define TRANSLATION_MESSAGE_MAXIMUM_PER_SYMBOL_NUMBER_OF_TRADES_ALLOWED "maximum number of trades per symbol allowed" +#define TRANSLATION_MESSAGE_TOTAL_POTENTIAL_RISK "total potential risk" +#define TRANSLATION_MESSAGE_MAXIUMUM_TOTAL_RISK "maximum total risk allowed" +#define TRANSLATION_MESSAGE_INFINITE_TOTAL_POTENTIAL_RISK "infinite total potential risk" +#define TRANSLATION_MESSAGE_PER_SYMBOL_POTENTIAL_RISK "potential risk per symbol" +#define TRANSLATION_MESSAGE_MAXIMUM_PER_SYMBOL_RISK "maximum risk per symbol allowed" +#define TRANSLATION_MESSAGE_INFINITE_PER_SYMBOL_POTENTIAL_RISK "infinite potential risk per symbol" +#define TRANSLATION_MESSAGE_IGNORE_MARKET_EXECUTION_MODE_WARNING ", but IgnoreMarketExecutionMode = true. Switch to false if trades aren't executing." +#define TRANSLATION_MESSAGE_EXECUTION_MODE "Execution mode" +#define TRANSLATION_MESSAGE_ORDER_FILLING_MODE "Order filling mode" +#define TRANSLATION_MESSAGE_FILL_OR_KILL "Fill or Kill" +#define TRANSLATION_MESSAGE_IMMEDIATE_OR_CANCEL "Immediate or Cancel" +#define TRANSLATION_MESSAGE_FOUND_EXISTING_BUY_VOLUME "Found existing buy volume" +#define TRANSLATION_MESSAGE_FOUND_EXISTING_SELL_VOLUME "Found existing sell volume" +#define TRANSLATION_MESSAGE_ADJUSTED_POSITION_SIZE "Adjusted position size" +#define TRANSLATION_MESSAGE_ADJUSTED_POSITION_SIZE_LESS_THAN_ZERO "Adjusted position size is less than zero. Not executing any trade." +#define TRANSLATION_MESSAGE_NTAT_TOTAL_VOLUME "current total volume" +#define TRANSLATION_MESSAGE_NTAT_NEW_POSITION_VOLUME "new position volume" +#define TRANSLATION_MESSAGE_NTAT_MAXIMUM_TOTAL_VOLUME "maximum total volume allowed" +#define TRANSLATION_MESSAGE_NTAT_PER_SYMBOL_VOLUME "current volume per symbol" +#define TRANSLATION_MESSAGE_NTAT_MAXIMUM_PER_SYMBOL_VOLUME "maximum volume allowed per symbol" +#define TRANSLATION_MESSAGE_BROKER_MINIMUM "broker's minimum position size. Not executing the trade." +#define TRANSLATION_MESSAGE_BROKER_MAXIMUM "broker's maximum position size. Reducing it." +#define TRANSLATION_MESSAGE_ERROR_SENDING_ORDER "Error sending order" +#define TRANSLATION_MESSAGE_ORDER_EXECUTED "Order executed." +#define TRANSLATION_MESSAGE_TICKET "Ticket" +#define TRANSLATION_MESSAGE_ORDER "Order" +#define TRANSLATION_MESSAGE_EXECUTED "executed" +#define TRANSLATION_MESSAGE_ERROR_OPENING_POSITION "Error opening a position" +#define TRANSLATION_MESSAGE_RETURN_CODE "Return code" +#define TRANSLATION_MESSAGE_INITIAL_RETURN_CODE "Initial return code" +#define TRANSLATION_MESSAGE_ORDER_ID "Order ID" +#define TRANSLATION_MESSAGE_DEAL_ID "Deal ID" +#define TRANSLATION_MESSAGE_POSITION_ID "Position ID" +#define TRANSLATION_MESSAGE_ERROR_MODIFYING_POSITION "Error modifying position" +#define TRANSLATION_MESSAGE_SL_TP_APPLIED "SL/TP applied successfully." +#define TRANSLATION_MESSAGE_ERROR_SELECTING_DEAL "Error selecting deal" +#define TRANSLATION_MESSAGE_ERROR_SELECTING_DEAL_HISTORY "Error selecting deal history" +#define TRANSLATION_MESSAGE_WAITING "Waiting..." +#define TRANSLATION_MESSAGE_ERROR_SELECTING_POSITIONS "Error selecting positions" +#define TRANSLATION_MESSAGE_POSITION_SIZER_ON "Position Sizer on " +#define TRANSLATION_MESSAGE_EXECUTE_TRADE "Execute the trade?" +#define TRANSLATION_MESSAGE_BUY "Buy" +#define TRANSLATION_MESSAGE_BUY_STOP "Buy Stop" +#define TRANSLATION_MESSAGE_BUY_LIMIT "Buy Limit" +#define TRANSLATION_MESSAGE_BUY_STOP_LIMIT "Buy Stop Limit" +#define TRANSLATION_MESSAGE_SELL "Sell" +#define TRANSLATION_MESSAGE_SELL_STOP "Sell Stop" +#define TRANSLATION_MESSAGE_SELL_LIMIT "Sell Limit" +#define TRANSLATION_MESSAGE_SELL_STOP_LIMIT "Sell Stop Limit" +#define TRANSLATION_MESSAGE_SIZE "Size" +#define TRANSLATION_MESSAGE_MULTIPLE "multiple" +#define TRANSLATION_MESSAGE_TRADE_CANCELED "Trade canceled." +#define TRANSLATION_MESSAGE_POSITIONGETTICKET_FAILED "PositionGetTicket failed" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_BUY_TSL "PositionModify failed for Buy trailing stop" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_SELL_TSL "PositionModify failed for Sell trailing stop" +#define TRANSLATION_MESSAGE_TSL_APPLIED "Trailing stop was applied to position" +#define TRANSLATION_MESSAGE_SL_WAS_MOVED_FROM "Stop-Loss was moved from" +#define TRANSLATION_MESSAGE_SL_WAS_MOVED_TO "to" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_BUY_BE "PositionModify failed for Buy breakeven" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_SELL_BE "PositionModify failed for Sell breakeven" +#define TRANSLATION_MESSAGE_BE_APPLIED "Breakeven was applied to position" +#define TRANSLATION_MESSAGE_BE_FOR "Breakeven for " +#define TRANSLATION_MESSAGE_ERROR_SETTING_TIMER "Error setting timer" +#define TRANSLATION_MESSAGE_FAILED_DELETE_INI "Failed to delete the PS panel's .ini file" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT "Cannot convert" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT_TO "to" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT_CALCULATION "Calculations might be wrong for" \ No newline at end of file diff --git a/MQL5/Experts/Position Sizer/Translations/Russian.mqh b/MQL5/Experts/Position Sizer/Translations/Russian.mqh new file mode 100644 index 0000000..d05a3fa --- /dev/null +++ b/MQL5/Experts/Position Sizer/Translations/Russian.mqh @@ -0,0 +1,298 @@ +// Tabs +#define TRANSLATION_TAB_BUTTON_MAIN "Основн." +#define TRANSLATION_TAB_BUTTON_RISK "Риск" +#define TRANSLATION_TAB_BUTTON_MARGIN "Маржа" +#define TRANSLATION_TAB_BUTTON_SWAPS "Свопы" +#define TRANSLATION_TAB_BUTTON_TRADING "Торг" + +// Entry +#define TRANSLATION_LABEL_ENTRY "Вход" +#define TRANSLATION_BUTTON_LONG "Покупка" +#define TRANSLATION_BUTTON_SHORT "Продажа" + +#define TRANSLATION_TOOLTIP_BUTTON_LONG_SHORT "Переключение между Покупкой и Продажей" + +#define TRANSLATION_TOOLTIP_ENTRY_INCREASE "Увеличить Вход на 1 пункт" +#define TRANSLATION_TOOLTIP_ENTRY_DECREASE "Уменьшить Вход на 1 пункт" + +// Stop-loss +#define TRANSLATION_LABEL_STOPLOSS "Стоп-лосс" +#define TRANSLATION_BUTTON_SL "СЛ, пункты" + +#define TRANSLATION_TOOLTIP_STOPLOSS_INCREASE "Увеличить Стоп-лосс на 1 пункт" +#define TRANSLATION_TOOLTIP_STOPLOSS_DECREASE "Уменьшить Стоп-лосс на 1 пункт" + +// Take-profit +#define TRANSLATION_LABEL_TAKEPROFIT "Тейк-профит" +#define TRANSLATION_BUTTON_TP "ТП, пункты" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_ADD "Добавить уровень тейк-профита" +#define TRANSLATION_TOOLTIP_BUTTON_TP "Установить ТП на основе СЛ или включить режим слежения за уровнем СЛ" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE "Увеличить Тейк-профит на 1 пункт" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_DECREASE "Уменьшить Тейк-профит на 1 пункт" + +#define TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE "ТП" +#define TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_POINTS "пункты" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_REMOVE "Убрать Тейк-профит" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE_MULTIPLE "Увеличить Тейк-профит" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_DECREASE_MULTIPLE "Уменьшить Тейк-профит" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_BY_ONE_POINT "на 1 пункт" + +// Stop price +#define TRANSLATION_LABEL_STOPPRICE "Стоп-цена" + +#define TRANSLATION_TOOLTIP_STOPPRICE_INCREASE "Увеличить Стоп-цену на 1 пункт" +#define TRANSLATION_TOOLTIP_STOPPRICE_DECREASE "Уменьшить Стоп-цену на 1 пункт" + +// ATR options +#define TRANSLATION_LABEL_ATR_PERIOD "Период ATR" +#define TRANSLATION_BUTTON_ATR_PERIOD_CURRENT "ТЕКУЩИЙ" +#define TRANSLATION_LABEL_ATR_SL_MULTIPLIER "Множ. СЛ" +#define TRANSLATION_LABEL_ATR_TP_MULTIPLIER "Множ. ТП" + +#define TRANSLATION_CHECKBOX_ATR_SA "ПС" +#define TRANSLATION_TOOLTIP_ATR_SA_SL "Применять поправку по спреду к стоп-лоссу" +#define TRANSLATION_TOOLTIP_ATR_SA_TP "Применять поправку по спреду к тейк-профиту" + +#define TRANSLATION_LABEL_ATR_TIMEFRAME "Таймфрейм ATR" +#define TRANSLATION_LABEL_ATR_VALUE "ATR" + +// Order type +#define TRANSLATION_LABEL_ORDER_TYPE "Тип ордера" +#define TRANSLATION_BUTTON_ORDER_TYPE_INSTANT "Рыночный" +#define TRANSLATION_BUTTON_ORDER_TYPE_PENDING "Отложенный" +#define TRANSLATION_BUTTON_ORDER_TYPE_STOPLIMIT "Стоп-лимит" +#define TRANSLATION_TOOLTIP_ORDER_TYPE "Переключение между Рыночным, Отложенным и Стоп-лимитом" + +// Hide/show lines +#define TRANSLATION_BUTTON_HIDE_LINES "Убрать линии" +#define TRANSLATION_BUTTON_SHOW_LINES "Показ. линии" + +// Commission +#define TRANSLATION_LABEL_COMMISSION "Комиссия (1-сторон.) за лот" +#define TRANSLATION_TOOLTIP_COMMISSION "В валюте счета или %, за 1 стандартный лот" +#define TRANSLATION_TOOLTIP_COMMISSION_TYPE "Кликните, чтобы поменять" + +// Account size +#define TRANSLATION_BUTTON_ACCOUNT_BALANCE "Баланс счета" +#define TRANSLATION_BUTTON_ACCOUNT_EQUITY "Средства счета" +#define TRANSLATION_BUTTON_BALANCE_MINUS_CPR "Баланс - ТРП" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE "Переключайте между балансом, средствами и балансом минус текущий риск по портфолио" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_CUSTOM "Задан пользовательский баланс" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_ADD "дополнительные средства" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_SUB "вычтенные средства" + +// Calculations +#define TRANSLATION_LABEL_INPUT "Вход. данные" +#define TRANSLATION_LABEL_RESULT "Результат" +#define TRANSLATION_LABEL_RISK "Риск" +#define TRANSLATION_LABEL_MONEY "деньги" +#define TRANSLATION_LABEL_REWARD "Прибыль" +#define TRANSLATION_LABEL_REWARD_RISK "Прибыль/риск" +#define TRANSLATION_LABEL_POSITION_SIZE "Размер позиции" +#define TRANSLATION_BUTTON_MAX_PS "Макс РП" +#define TRANSLATION_LABEL_POINT_VALUE "Цена пункта" + + +// Risk tab +#define TRANSLATION_CHECKBOX_COUNT_PENDING_ORDERS "Считать отложенные ордеры" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_WO_SL "Игнорировать ордеры без стоп-лосса" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_WO_TP "Игнорировать ордеры без тейк-профита" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_IN_OTHER_SYMBOLS "Игнорировать ордеры по другим символам" +#define TRANSLATION_LABEL_LOTS "Лоты" +#define TRANSLATION_LABEL_CURRENT_PORTFOLIO "Тек. портфолио" +#define TRANSLATION_TOOLTIP_CURRENT_PORTFOLIO "Сделки, которые сейчас открыты" +#define TRANSLATION_LABEL_POTENTIAL_PORTFOLIO "Потенц. портфол." +#define TRANSLATION_TOOLTIP_POTENTIAL_PORTFOLIO "Включая позицию в расчете" + + +// Margin tab +#define TRANSLATION_LABEL_POSITION_MARGIN "Маржа позиции" +#define TRANSLATION_LABEL_FUTURE_USED_MARGIN "Будущ. использ. маржа" +#define TRANSLATION_LABEL_FUTURE_FREE_MARGIN "Будущ. свобод. маржа" +#define TRANSLATION_LABEL_CUSTOM_LEVERAGE "Свое плечо " +#define TRANSLATION_LABEL_DEFAULT "По умолчанию" +#define TRANSLATION_LABEL_SYMBOL "Символ" +#define TRANSLATION_LABEL_MAX_PS_BY_MARGIN "Макс размер позиции по марже" +#define TRANSLATION_TOOLTIP_MAX_PS_BY_MARGIN "В лотах" + + +// Swaps tab +#define TRANSLATION_LABEL_TYPE "Тип" +#define TRANSLATION_LABEL_UNKNOWN "Неизвестно" +#define TRANSLATION_LABEL_DISABLED "Отключен" +#define TRANSLATION_LABEL_INTEREST_OPEN "Процент (откр.)" +#define TRANSLATION_LABEL_INTEREST_CURRENT "Процент (текущ.)" +#define TRANSLATION_LABEL_REOPENING "Переоткрытие" +#define TRANSLATION_LABEL_TRIPLE_SWAP "Своп × 3" +#define TRANSLATION_EDIT_WEEKDAY_SUNDAY "Воскресенье" +#define TRANSLATION_EDIT_WEEKDAY_MONDAY "Понедельник" +#define TRANSLATION_EDIT_WEEKDAY_TUESDAY "Вторник" +#define TRANSLATION_EDIT_WEEKDAY_WEDNESDAY "Среда" +#define TRANSLATION_EDIT_WEEKDAY_THURSDAY "Четверг" +#define TRANSLATION_EDIT_WEEKDAY_FRIDAY "Пятница" +#define TRANSLATION_EDIT_WEEKDAY_SATURDAY "Суббота" +#define TRANSLATION_LABEL_NOMINAL "Знач." +#define TRANSLATION_LABEL_DAILY "В день" +#define TRANSLATION_LABEL_YEARLY "В год" +#define TRANSLATION_LABEL_PER_LOT "за лот" +#define TRANSLATION_LABEL_PER_PS "за РП" +#define TRANSLATION_LABEL_BASE_CURRENCY "Базовая валюта" +#define TRANSLATION_LABEL_MARGIN_CURRENCY "Валюта маржи" + + +// Trading tab +#define TRANSLATION_BUTTON_TRADE "Откр." +#define TRANSLATION_LABEL_TRAILING_STOP "Трейлинг" +#define TRANSLATION_LABEL_BREAKEVEN "Безубыток" +#define TRANSLATION_LABEL_MAGIC_NUMBER "Мэджик" +#define TRANSLATION_LABEL_ORDER_COMMENTARY "Комментарий" +#define TRANSLATION_LABEL_ORDER_AUTOSUFFIX "Автосуф." +#define TRANSLATION_TOOLTIP_ORDER_AUTOSUFFIX "Добавлять автоматически инкрементируемое число к комментарию каждой следующей сделки?" +#define TRANSLATION_LABEL_MAX_NUMBER_OF_TRADES "Макс № сделок" +#define TRANSLATION_LABEL_TOTAL "Всего" +#define TRANSLATION_LABEL_PER_SYMBOL "На символ" +#define TRANSLATION_LABEL_MAX_VOLUME "Макс объем" +#define TRANSLATION_LABEL_MAX_RISK "Макс риск" +#define TRANSLATION_CHECKBOX_DISABLE_TRADING_LINES_HIDDEN "Не разрешать торговлю, когда линии спрятаны" +#define TRANSLATION_TOOLTIP_FILL_INWARD "Заполнить дополнительные ТП равномерно между Входом и основным ТП." +#define TRANSLATION_TOOLTIP_FILL_OUTWARD "Разместить дополнительные ТП за основным ТП, используя то же расстояние." +#define TRANSLATION_LABEL_SHARE "Доля" +#define TRANSLATION_TOOLTIP_SHARE "Автоматически заполнить доли объема" +#define TRANSLATION_LABEL_POINTS "Пункты" +#define TRANSLATION_LABEL_MAX_SLIPPAGE "Макс проскальз." +#define TRANSLATION_LABEL_MAX_SPREAD "Макс спред" +#define TRANSLATION_LABEL_MAX_ENTRY_SL_DISTANCE "Макс расст. Вход/СЛ" +#define TRANSLATION_LABEL_MIN_ENTRY_SL_DISTANCE "Мин расст. Вход/СЛ" +#define TRANSLATION_CHECKBOX_SUBTRACT_OPEN_POSITIONS_VOLUME "Выч. об. откр. позиций" +#define TRANSLATION_CHECKBOX_SUBTRACT_PENDING_ORDERS_VOLUME "Выч. об. отлож. ордеров" +#define TRANSLATION_CHECKBOX_DO_NOT_APPLY_STOPLOSS "Не примен. стоп-лосс" +#define TRANSLATION_CHECKBOX_DO_NOT_APPLY_TAKEPROFIT "Не примен. тейк-профит" +#define TRANSLATION_TOOLTIP_SUBTRACT_OPEN_POSITIONS_VOLUME "Советник вычтет текущий объем по открытым сделкам из рассчитанного размера позиции перед тем, как ее открыть." +#define TRANSLATION_TOOLTIP_SUBTRACT_PENDING_ORDERS_VOLUME "Советник вычтет текущий объем по отложенным ордерам из рассчитанного размера позиции перед тем, как ее открыть." +#define TRANSLATION_TOOLTIP_DO_NOT_APPLY_STOPLOSS "Советник откроет сделку без стоп-лосса." +#define TRANSLATION_TOOLTIP_DO_NOT_APPLY_TAKEPROFIT "Советник откроет сделку без тейк-профита." +#define TRANSLATION_CHECKBOX_ASK_FOR_CONFIRMATION "Спрашивать подтверждение" +#define TRANSLATION_TOOLTIP_ASK_FOR_CONFIRMATION "Советник будет спрашивать подтверждение перед открытием сделки." + + +// Chart objects +#define TRANSLATION_TOOLTIP_STOP_PRICE_LINE "Стоп-цена (для ордеров стоп-лимит)" +#define TRANSLATION_TOOLTIP_SL_LABEL "Расстояние до СЛ, пункты" +#define TRANSLATION_TOOLTIP_TP_LABEL "Расстояние до ТП, пункты" +#define TRANSLATION_TOOLTIP_ENTRY_LABEL "Расстояние до Входа, пункты" +#define TRANSLATION_TOOLTIP_STOP_PRICE_LABEL "Расстояние до стоп-цены, пункты" + +// Warnings +#define TRANSLATION_LABEL_WARNING_TOO_CLOSE "(Близко!)" +#define TRANSLATION_LABEL_WARNING_WRONG_VALUE "(Значение!)" +#define TRANSLATION_LABEL_WARNING_INVALID_TP "Неправ. ТП" +#define TRANSLATION_TOOLTIP_WARNING_PS "Больше, чем максимальный размер позиции по марже!" + +// Messages +#define TRANSLATION_MESSAGE_SL_SHOULD_BE_POSITIVE "Стоп-лосс должен быть положительным." +#define TRANSLATION_MESSAGE_TRYING_TO_SAVE_FILE "Попытка сохранения настроек в файл" +#define TRANSLATION_MESSAGE_FAILED_TO_OPEN_FOR_WRITING "Не удалось открыть файл для записи" +#define TRANSLATION_MESSAGE_ERROR "Ошибка" +#define TRANSLATION_MESSAGE_SAVED_SETTINGS "Настройки сохранены успешно." +#define TRANSLATION_MESSAGE_TRYING_TO_LOAD_FILE "Попытка загрузки настроек из файла." +#define TRANSLATION_MESSAGE_NO_SETTINGS_FILE_TO_LOAD "Нет файла для загрузки." +#define TRANSLATION_MESSAGE_FAILED_TO_OPEN_FOR_READING "Не удалось открыть файл для чтения" +#define TRANSLATION_MESSAGE_LOADED_SETTINGS "Настройки загружены успешно." +#define TRANSLATION_MESSAGE_NO_SETTINGS_FILE_TO_DELETE "Нет файла для удаления." +#define TRANSLATION_MESSAGE_TRYING_TO_DELETE_FILE "Попытка удаления файла с настройками." +#define TRANSLATION_MESSAGE_FAILED_TO_DELETE_FILE "Не удалось удалить файл" +#define TRANSLATION_MESSAGE_DELETED_SETTINGS "Файл с настройками удален успешно." +#define TRANSLATION_MESSAGE_DELETED_DUPLICATE_PANEL "Удалены объекты панели-дубликата с префиксом" +#define TRANSLATION_MESSAGE_FAILED_TO_CREATE_ATR "Не удалось создать дескриптор индикатора ATR" +#define TRANSLATION_MESSAGE_ENTRY_SL_DIFFERENT_NON_ZERO "Вход и стоп-лосс должны отличаться и быть ненулевыми." +#define TRANSLATION_MESSAGE_ENTRY_SL_DIFFERENT "Стоп-лосс должен отличаться от Входа." +#define TRANSLATION_MESSAGE_CANNOT_RETRIEVE_TICKSIZE "Невозможно получить размер тика для " +#define TRANSLATION_MESSAGE_LOOKS_LIKE "Похоже, что инструмент более не доступен. Расчет может быть неточным." +#define TRANSLATION_MESSAGE_MISCONFIGURED_SYMBOL "Символ настроен неправильно на торговом сервере - нулевая цена единицы." +#define TRANSLATION_MESSAGE_ALGO_TRADING_DISABLED "Отключен алготрейдинг! Пожалуйста, включите алготрейдинг." +#define TRANSLATION_MESSAGE_STOPLOSS_PROBLEM "Проблемный стоп-лосс" +#define TRANSLATION_MESSAGE_WRONG_POSITION_SIZE_VALUE "Неправильное значение размера позиции!" +#define TRANSLATION_MESSAGE_MULTIPLE_TP_VOLUME_SHARE_SUM "Сумма долей объема нескольких ТП" +#define TRANSLATION_MESSAGE_INCORRECT_VOLUME_SUM "Неправильная сумма объемов нескольких ТП - сделка не будет открыта." +#define TRANSLATION_MESSAGE_NETTING_MODE_DETECTED "Обнаружен режим неттинга. Невозможна работа с несколькими ТП. Основной ТП установлен на 100% объема." +#define TRANSLATION_MESSAGE_NOT_TAKING_A_TRADE "Сделка не будет открыта" +#define TRANSLATION_MESSAGE_NTAT_LINES "линии спрятаны и панель настроена так, чтобы не торговать при спрятанных линиях." +#define TRANSLATION_MESSAGE_NTAT_SPREAD "текущий спред" +#define TRANSLATION_MESSAGE_MAXIMUM_SPREAD "максимальный спред" +#define TRANSLATION_MESSAGE_NTAT_ENTRY_SL_DISTANCE "текущее расстояние Вход/СЛ" +#define TRANSLATION_MESSAGE_NTAT_TOTAL_NUMBER "текущее общее число сделок" +#define TRANSLATION_MESSAGE_NUMBER_OF_TRADES_IN_EXECUTION "число сделок на исполнении" +#define TRANSLATION_MESSAGE_MAXIMUM_TOTAL_NUMBER_OF_TRADES_ALLOWED "максимально допустимое общее число сделок" +#define TRANSLATION_MESSAGE_NTAT_PER_SYMBOL_NUMBER "текущее число сделок по символу" +#define TRANSLATION_MESSAGE_MAXIMUM_PER_SYMBOL_NUMBER_OF_TRADES_ALLOWED "максимально допустимое число сделок по символу" +#define TRANSLATION_MESSAGE_TOTAL_POTENTIAL_RISK "общий потенциальный риск" +#define TRANSLATION_MESSAGE_MAXIUMUM_TOTAL_RISK "максимально допустимый общий риск" +#define TRANSLATION_MESSAGE_INFINITE_TOTAL_POTENTIAL_RISK "бесконечный общий потенциальный риск" +#define TRANSLATION_MESSAGE_PER_SYMBOL_POTENTIAL_RISK "потенциальный риск по символу" +#define TRANSLATION_MESSAGE_MAXIMUM_PER_SYMBOL_RISK "максимально допустимый риск по символу" +#define TRANSLATION_MESSAGE_INFINITE_PER_SYMBOL_POTENTIAL_RISK "бесконечный потенциальный риск по символу" +#define TRANSLATION_MESSAGE_IGNORE_MARKET_EXECUTION_MODE_WARNING ", но IgnoreMarketExecutionMode = true. Переключите на false, если сделки не исполняются." +#define TRANSLATION_MESSAGE_EXECUTION_MODE "Режим исполнения" +#define TRANSLATION_MESSAGE_ORDER_FILLING_MODE "Режим исполнения по остатку" +#define TRANSLATION_MESSAGE_FILL_OR_KILL "Все или ничего" +#define TRANSLATION_MESSAGE_IMMEDIATE_OR_CANCEL "Все или частично" +#define TRANSLATION_MESSAGE_FOUND_EXISTING_BUY_VOLUME "Найденный текущий объем на покупку" +#define TRANSLATION_MESSAGE_FOUND_EXISTING_SELL_VOLUME "Найденный текущий объем на продажу" +#define TRANSLATION_MESSAGE_ADJUSTED_POSITION_SIZE "Исправленный размер позиции" +#define TRANSLATION_MESSAGE_ADJUSTED_POSITION_SIZE_LESS_THAN_ZERO "Исправленный размер позиции меньше нуля. Сделка исполнена не будет." +#define TRANSLATION_MESSAGE_NTAT_TOTAL_VOLUME "текущий общий объем" +#define TRANSLATION_MESSAGE_NTAT_NEW_POSITION_VOLUME "объем новой позиции" +#define TRANSLATION_MESSAGE_NTAT_MAXIMUM_TOTAL_VOLUME "максимально допустимый общий объем" +#define TRANSLATION_MESSAGE_NTAT_PER_SYMBOL_VOLUME "текущий объем по символу" +#define TRANSLATION_MESSAGE_NTAT_MAXIMUM_PER_SYMBOL_VOLUME "максимально допустимый объем по символу" +#define TRANSLATION_MESSAGE_BROKER_MINIMUM "минимальный размер позиции у брокера. Сделка не будет исполнена." +#define TRANSLATION_MESSAGE_BROKER_MAXIMUM "максимальный размер позиции у брокера. Позиция будет уменьшена." +#define TRANSLATION_MESSAGE_ERROR_SENDING_ORDER "Ошибка отправки ордера" +#define TRANSLATION_MESSAGE_ORDER_EXECUTED "Ордер исполнен." +#define TRANSLATION_MESSAGE_TICKET "Тикет" +#define TRANSLATION_MESSAGE_ORDER "Ордер" +#define TRANSLATION_MESSAGE_EXECUTED "исполнен" +#define TRANSLATION_MESSAGE_ERROR_OPENING_POSITION "Ошибка открытия позиции" +#define TRANSLATION_MESSAGE_RETURN_CODE "Код возврата" +#define TRANSLATION_MESSAGE_INITIAL_RETURN_CODE "Первичный код возврата" +#define TRANSLATION_MESSAGE_ORDER_ID "ID ордера" +#define TRANSLATION_MESSAGE_DEAL_ID "ID сделки" +#define TRANSLATION_MESSAGE_POSITION_ID "ID позиции" +#define TRANSLATION_MESSAGE_ERROR_MODIFYING_POSITION "Ошибка изменения позиции" +#define TRANSLATION_MESSAGE_SL_TP_APPLIED "СЛ/ТП добавлены успешно." +#define TRANSLATION_MESSAGE_ERROR_SELECTING_DEAL "Ошибка выбора сделки" +#define TRANSLATION_MESSAGE_ERROR_SELECTING_DEAL_HISTORY "Ошибки выбора истории сделок" +#define TRANSLATION_MESSAGE_WAITING "Ожидание..." +#define TRANSLATION_MESSAGE_ERROR_SELECTING_POSITIONS "Ошибка выбора позиций" +#define TRANSLATION_MESSAGE_POSITION_SIZER_ON "Position Sizer на " +#define TRANSLATION_MESSAGE_EXECUTE_TRADE "Исполнить сделку?" +#define TRANSLATION_MESSAGE_BUY "Покупка" +#define TRANSLATION_MESSAGE_BUY_STOP "Стоп на покупку" +#define TRANSLATION_MESSAGE_BUY_LIMIT "Лимит на покупку" +#define TRANSLATION_MESSAGE_BUY_STOP_LIMIT "Стоп-лимит на покупку" +#define TRANSLATION_MESSAGE_SELL "Продажа" +#define TRANSLATION_MESSAGE_SELL_STOP "Стоп на продажу" +#define TRANSLATION_MESSAGE_SELL_LIMIT "Лимит на продажу" +#define TRANSLATION_MESSAGE_SELL_STOP_LIMIT "Стоп-лимит на продажу" +#define TRANSLATION_MESSAGE_SIZE "Размер" +#define TRANSLATION_MESSAGE_MULTIPLE "несколько" +#define TRANSLATION_MESSAGE_TRADE_CANCELED "Сделка отменена." +#define TRANSLATION_MESSAGE_POSITIONGETTICKET_FAILED "Функция PositionGetTicket не вернула результат" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_BUY_TSL "Функция PositionModify не смогла применить трейлинг-стоп на покупку" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_SELL_TSL "Функция PositionModify не смогла применить трейлинг-стоп на продажу" +#define TRANSLATION_MESSAGE_TSL_APPLIED "Трейлинг-стоп добавлен к позиции" +#define TRANSLATION_MESSAGE_SL_WAS_MOVED_FROM "Стоп-лосс передвинут с" +#define TRANSLATION_MESSAGE_SL_WAS_MOVED_TO "на" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_BUY_BE "Функция PositionModify не смогла применить безубыток на покупку" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_SELL_BE "Функция PositionModify не смогла применить безубыток на продажу" +#define TRANSLATION_MESSAGE_BE_APPLIED "Безубыток применен к позиции" +#define TRANSLATION_MESSAGE_BE_FOR "Безубыток для " +#define TRANSLATION_MESSAGE_ERROR_SETTING_TIMER "Ошибка установки таймера" +#define TRANSLATION_MESSAGE_FAILED_DELETE_INI "Не удалось удалить ini-файл панели" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT "Не получается перевести" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT_TO "в" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT_CALCULATION "Расчет может быть неверен для" \ No newline at end of file diff --git a/MQL5/Experts/Position Sizer/Translations/Ukrainian.mqh b/MQL5/Experts/Position Sizer/Translations/Ukrainian.mqh new file mode 100644 index 0000000..81f0b2d --- /dev/null +++ b/MQL5/Experts/Position Sizer/Translations/Ukrainian.mqh @@ -0,0 +1,300 @@ +// Tabs +#define TRANSLATION_TAB_BUTTON_MAIN "Основн." +#define TRANSLATION_TAB_BUTTON_RISK "Ризик" +#define TRANSLATION_TAB_BUTTON_MARGIN "Маржа" +#define TRANSLATION_TAB_BUTTON_SWAPS "Свопи" +#define TRANSLATION_TAB_BUTTON_TRADING "Торг" + +// Entry +#define TRANSLATION_LABEL_ENTRY "Вхід" +#define TRANSLATION_BUTTON_LONG "Купівля" +#define TRANSLATION_BUTTON_SHORT "Продаж" + +#define TRANSLATION_TOOLTIP_BUTTON_LONG_SHORT "Перемикання між Купівлею та Продажом" + +#define TRANSLATION_TOOLTIP_ENTRY_INCREASE "Збільшити Вхід на 1 пункт" +#define TRANSLATION_TOOLTIP_ENTRY_DECREASE "Зменшити Вхід на 1 пункт" + +// Stop-loss +#define TRANSLATION_LABEL_STOPLOSS "Стоп-лос" +#define TRANSLATION_BUTTON_SL "СЛ, пункти" + +#define TRANSLATION_TOOLTIP_STOPLOSS_INCREASE "Збільшити Стоп-лос на 1 пункт" +#define TRANSLATION_TOOLTIP_STOPLOSS_DECREASE "Зменшити Стоп-лос на 1 пункт" + +// Take-profit +#define TRANSLATION_LABEL_TAKEPROFIT "Тейк-профіт" +#define TRANSLATION_BUTTON_TP "ТП, пункти" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_ADD "Додати рівень тейк-профіту" +#define TRANSLATION_TOOLTIP_BUTTON_TP "Встановити ТП на основі СЛ або увімкнути режим стеження за рівнем СЛ" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE "Збільшити Тейк-профіт на 1 пункт" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_DECREASE "Зменшити Тейк-профіт на 1 пункт" + +#define TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_DISTANCE "ТП" +#define TRANSLATION_LABEL_TAKEPROFIT_MULTIPLE_POINTS "пункти" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_REMOVE "Прибрати Тейк-профіт" + +#define TRANSLATION_TOOLTIP_TAKEPROFIT_INCREASE_MULTIPLE "Збільшити Тейк-профіт" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_DECREASE_MULTIPLE "Зменшити Тейк-профіт" +#define TRANSLATION_TOOLTIP_TAKEPROFIT_BY_ONE_POINT "на 1 пункт" + +// Stop price +#define TRANSLATION_LABEL_STOPPRICE "Стоп-ціна" + +#define TRANSLATION_TOOLTIP_STOPPRICE_INCREASE "Збільшити Стоп-цену на 1 пункт" +#define TRANSLATION_TOOLTIP_STOPPRICE_DECREASE "Зменшити Стоп-цену на 1 пункт" + +// ATR options +#define TRANSLATION_LABEL_ATR_PERIOD "Період ATR" +#define TRANSLATION_BUTTON_ATR_PERIOD_CURRENT "ПОТОЧНИЙ" +#define TRANSLATION_LABEL_ATR_SL_MULTIPLIER "Множник СЛ" +#define TRANSLATION_LABEL_ATR_TP_MULTIPLIER "Множник ТП" + +#define TRANSLATION_CHECKBOX_ATR_SA "ПС" +#define TRANSLATION_TOOLTIP_ATR_SA_SL "Застосовувати поправку по спреду до стоп-лосу" +#define TRANSLATION_TOOLTIP_ATR_SA_TP "Застосовувати поправку по спреду до тейк-профіту" + +#define TRANSLATION_LABEL_ATR_TIMEFRAME "Таймфрейм ATR" +#define TRANSLATION_LABEL_ATR_VALUE "ATR" + +// Order type +#define TRANSLATION_LABEL_ORDER_TYPE "Тип ордеру" +#define TRANSLATION_BUTTON_ORDER_TYPE_INSTANT "Ринковий" +#define TRANSLATION_BUTTON_ORDER_TYPE_PENDING "Відкладений" +#define TRANSLATION_BUTTON_ORDER_TYPE_STOPLIMIT "Стоп-ліміт" +#define TRANSLATION_TOOLTIP_ORDER_TYPE "Перемикання між Ринковим, Відкладеним і Стоп-лімітом" + +// Hide/show lines +#define TRANSLATION_BUTTON_HIDE_LINES "Схов. лінії" +#define TRANSLATION_BUTTON_SHOW_LINES "Показ. лінії" + +// Commission +#define TRANSLATION_LABEL_COMMISSION "Комісія (1-сторон.) за лот" +#define TRANSLATION_TOOLTIP_COMMISSION "У валюті рахунку або %, за 1 стандартний лот" +#define TRANSLATION_TOOLTIP_COMMISSION_TYPE "Клікніть, щоб змінити" + +// Account size +#define TRANSLATION_BUTTON_ACCOUNT_BALANCE "Баланс рахунку" +#define TRANSLATION_BUTTON_ACCOUNT_EQUITY "Кошти рахунку" +#define TRANSLATION_BUTTON_BALANCE_MINUS_CPR "Баланс - ПРП" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE "Перемикайте між балансом, коштами та балансом мінус поточний ризик по портфоліо" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_CUSTOM "Задано власне значення балансу" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_ADD "додаткові кошти" +#define TRANSLATION_TOOLTIP_ACCOUNT_SIZE_ASTERISK_SUB "віднімані кошти" + +// Calculations +#define TRANSLATION_LABEL_INPUT "Вхідні дані" +#define TRANSLATION_LABEL_RESULT "Результат" +#define TRANSLATION_LABEL_RISK "Ризик" +#define TRANSLATION_LABEL_MONEY "гроші" +#define TRANSLATION_LABEL_REWARD "Прибуток" +#define TRANSLATION_LABEL_REWARD_RISK "Прибуток/ризик" +#define TRANSLATION_LABEL_POSITION_SIZE "Розмір позиції" +#define TRANSLATION_BUTTON_MAX_PS "Макс РП" +#define TRANSLATION_LABEL_POINT_VALUE "Ціна пункту" + + +// Risk tab +#define TRANSLATION_CHECKBOX_COUNT_PENDING_ORDERS "Рахувати відкладені ордери" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_WO_SL "Ігнорувати ордери без стоп-лосу" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_WO_TP "Ігнорувати ордери без тейк-профіта" +#define TRANSLATION_CHECKBOX_IGNORE_ORDERS_IN_OTHER_SYMBOLS "Ігнорувати ордери по іншим символам" +#define TRANSLATION_LABEL_LOTS "Лоти" +#define TRANSLATION_LABEL_CURRENT_PORTFOLIO "Поточ. портфоліо" +#define TRANSLATION_TOOLTIP_CURRENT_PORTFOLIO "Угоди, що зараз є відкритими" +#define TRANSLATION_LABEL_POTENTIAL_PORTFOLIO "Потенц. портфол." +#define TRANSLATION_TOOLTIP_POTENTIAL_PORTFOLIO "Включно з позицією у розрахунку" + + +// Margin tab +#define TRANSLATION_LABEL_POSITION_MARGIN "Маржа позиції" +#define TRANSLATION_LABEL_FUTURE_USED_MARGIN "Майб. викор. маржа" +#define TRANSLATION_LABEL_FUTURE_FREE_MARGIN "Майб. вільна маржа" +#define TRANSLATION_LABEL_CUSTOM_LEVERAGE "Власне плече " +#define TRANSLATION_LABEL_DEFAULT "За замовч." +#define TRANSLATION_LABEL_SYMBOL "Символ" +#define TRANSLATION_LABEL_MAX_PS_BY_MARGIN "Макс розмір позиції по маржі" +#define TRANSLATION_TOOLTIP_MAX_PS_BY_MARGIN "У лотах" + + +// Swaps tab +#define TRANSLATION_LABEL_TYPE "Тип" +#define TRANSLATION_LABEL_UNKNOWN "Невідомо" +#define TRANSLATION_LABEL_DISABLED "Вимкнено" +#define TRANSLATION_LABEL_INTEREST_OPEN "Процент (відкр.)" +#define TRANSLATION_LABEL_INTEREST_CURRENT "Процент (поточ.)" +#define TRANSLATION_LABEL_REOPENING "Перевідкриття" +#define TRANSLATION_LABEL_TRIPLE_SWAP "Своп × 3" +#define TRANSLATION_EDIT_WEEKDAY_SUNDAY "Неділя" +#define TRANSLATION_EDIT_WEEKDAY_MONDAY "Понеділок" +#define TRANSLATION_EDIT_WEEKDAY_TUESDAY "Вівторок" +#define TRANSLATION_EDIT_WEEKDAY_WEDNESDAY "Середа" +#define TRANSLATION_EDIT_WEEKDAY_THURSDAY "Четвер" +#define TRANSLATION_EDIT_WEEKDAY_FRIDAY "П'ятниця" +#define TRANSLATION_EDIT_WEEKDAY_SATURDAY "Субота" +#define TRANSLATION_LABEL_NOMINAL "Знач." +#define TRANSLATION_LABEL_DAILY "На день" +#define TRANSLATION_LABEL_YEARLY "На рік" +#define TRANSLATION_LABEL_PER_LOT "за лот" +#define TRANSLATION_LABEL_PER_PS "за РП" +#define TRANSLATION_LABEL_BASE_CURRENCY "Базова валюта" +#define TRANSLATION_LABEL_MARGIN_CURRENCY "Валюта маржі" + + +// Trading tab +#define TRANSLATION_BUTTON_TRADE "Відкр." +#define TRANSLATION_LABEL_TRAILING_STOP "Трейлінг" +#define TRANSLATION_LABEL_BREAKEVEN "Беззбиток" +#define TRANSLATION_LABEL_MAGIC_NUMBER "Меджик" +#define TRANSLATION_LABEL_ORDER_COMMENTARY "Коментар" +#define TRANSLATION_LABEL_ORDER_AUTOSUFFIX "Автосуф." +#define TRANSLATION_TOOLTIP_ORDER_AUTOSUFFIX "Додавати число, що автоматично інкрементується, до коментаря кожної наступної угоди?" +#define TRANSLATION_LABEL_MAX_NUMBER_OF_TRADES "Макс № угод" +#define TRANSLATION_LABEL_TOTAL "Усього" +#define TRANSLATION_LABEL_PER_SYMBOL "По символу" +#define TRANSLATION_LABEL_MAX_VOLUME "Макс об'єм" +#define TRANSLATION_LABEL_MAX_RISK "Макс ризик" +#define TRANSLATION_CHECKBOX_DISABLE_TRADING_LINES_HIDDEN "Не дозволяти торгівлю, коли лінії сховано" +#define TRANSLATION_TOOLTIP_FILL_INWARD "Заповнити додаткові ТП рівномірно між Входом й основним ТП." +#define TRANSLATION_TOOLTIP_FILL_OUTWARD "Розмістити додаткові ТП за основним ТП, використовуючи ту саму відстань." +#define TRANSLATION_LABEL_SHARE "Частка" +#define TRANSLATION_TOOLTIP_SHARE "Автоматично заповнити частки об'єму" +#define TRANSLATION_LABEL_POINTS "Пункти" +#define TRANSLATION_LABEL_MAX_SLIPPAGE "Макс прослизання" +#define TRANSLATION_LABEL_MAX_SPREAD "Макс спред" +#define TRANSLATION_LABEL_MAX_ENTRY_SL_DISTANCE "Макс відстань Вхід/СЛ" +#define TRANSLATION_LABEL_MIN_ENTRY_SL_DISTANCE "Мін відстань Вхід/СЛ" +#define TRANSLATION_CHECKBOX_SUBTRACT_OPEN_POSITIONS_VOLUME "Відн. об. відкр. позицій" +#define TRANSLATION_CHECKBOX_SUBTRACT_PENDING_ORDERS_VOLUME "Відн. об. відкл. ордерів" +#define TRANSLATION_CHECKBOX_DO_NOT_APPLY_STOPLOSS "Не застосовувати СЛ" +#define TRANSLATION_CHECKBOX_DO_NOT_APPLY_TAKEPROFIT "Не застосовувати ТП" +#define TRANSLATION_TOOLTIP_SUBTRACT_OPEN_POSITIONS_VOLUME "Експерт відніме поточний об'єм по відкритим угодам від розрахованого розміру позиції перед тим, як відкрити її." +#define TRANSLATION_TOOLTIP_SUBTRACT_PENDING_ORDERS_VOLUME "Експерт відніме поточний об'єм по відкладеним ордерам від розрахованого розміру позиції перед тим, як відкрити її." +#define TRANSLATION_TOOLTIP_DO_NOT_APPLY_STOPLOSS "Експерт відкриє угоду без стоп-лосу." +#define TRANSLATION_TOOLTIP_DO_NOT_APPLY_TAKEPROFIT "Експерт відкриє угоду без тейк-профіту." +#define TRANSLATION_CHECKBOX_ASK_FOR_CONFIRMATION "Запитувати підтвердження" +#define TRANSLATION_TOOLTIP_ASK_FOR_CONFIRMATION "Експерт буде запитувати підтвердження перед відкриттям угоди." + + +// Chart objects +#define TRANSLATION_TOOLTIP_STOP_PRICE_LINE "Стоп-ціна (для ордерів стоп-ліміт)" +#define TRANSLATION_TOOLTIP_SL_LABEL "Відстань до СЛ, пункти" +#define TRANSLATION_TOOLTIP_TP_LABEL "Відстань до ТП, пункти" +#define TRANSLATION_TOOLTIP_ENTRY_LABEL "Відстань до Входу, пункти" +#define TRANSLATION_TOOLTIP_STOP_PRICE_LABEL "Відстань до стоп-ціни, пункти" + + +// Warnings +#define TRANSLATION_LABEL_WARNING_TOO_CLOSE "(Близько!)" +#define TRANSLATION_LABEL_WARNING_WRONG_VALUE "(Значення!)" +#define TRANSLATION_LABEL_WARNING_INVALID_TP "Невірний ТП" +#define TRANSLATION_TOOLTIP_WARNING_PS "Більше, ніж максимальний розмір позиції по маржі!" + + +// Messages +#define TRANSLATION_MESSAGE_SL_SHOULD_BE_POSITIVE "Стоп-лос повинен бути позитивним." +#define TRANSLATION_MESSAGE_TRYING_TO_SAVE_FILE "Спроба збереження налаштувань до файлу" +#define TRANSLATION_MESSAGE_FAILED_TO_OPEN_FOR_WRITING "Не вдалося відкрити файл для запису" +#define TRANSLATION_MESSAGE_ERROR "Помилка" +#define TRANSLATION_MESSAGE_SAVED_SETTINGS "Налаштування збережені успішно." +#define TRANSLATION_MESSAGE_TRYING_TO_LOAD_FILE "Спроба завантаження налаштувань з файлу." +#define TRANSLATION_MESSAGE_NO_SETTINGS_FILE_TO_LOAD "Немає файлу для завантаження." +#define TRANSLATION_MESSAGE_FAILED_TO_OPEN_FOR_READING "Не вдалося відкрити файл для читання" +#define TRANSLATION_MESSAGE_LOADED_SETTINGS "Налаштування завантажені успішно." +#define TRANSLATION_MESSAGE_NO_SETTINGS_FILE_TO_DELETE "Немає файлу для видалення." +#define TRANSLATION_MESSAGE_TRYING_TO_DELETE_FILE "Спроба видалення файлу з налаштуваннями." +#define TRANSLATION_MESSAGE_FAILED_TO_DELETE_FILE "Не вдалося видалити файл" +#define TRANSLATION_MESSAGE_DELETED_SETTINGS "Файл з налаштуваннями видалено успішно." +#define TRANSLATION_MESSAGE_DELETED_DUPLICATE_PANEL "Видалено об'єкти панелі-дублікату з префіксом" +#define TRANSLATION_MESSAGE_FAILED_TO_CREATE_ATR "Не вдалося створити дескриптор індикатору ATR" +#define TRANSLATION_MESSAGE_ENTRY_SL_DIFFERENT_NON_ZERO "Вхід і стоп-лос повинні відрізнятися та бути ненульовими." +#define TRANSLATION_MESSAGE_ENTRY_SL_DIFFERENT "Стоп-лос повинен відрізнятися від Входу." +#define TRANSLATION_MESSAGE_CANNOT_RETRIEVE_TICKSIZE "Неможливо отримати розмір тіку для " +#define TRANSLATION_MESSAGE_LOOKS_LIKE "Схоже, що інструмент більш не доступний. Розрахунок може бути неточним." +#define TRANSLATION_MESSAGE_MISCONFIGURED_SYMBOL "Символ налаштований невірно на торговому сервері - нульова ціна одиниці." +#define TRANSLATION_MESSAGE_ALGO_TRADING_DISABLED "Відключений алготрейдінг! Будь ласка, увімкніть алготрейдінг." +#define TRANSLATION_MESSAGE_STOPLOSS_PROBLEM "Проблемний стоп-лос" +#define TRANSLATION_MESSAGE_WRONG_POSITION_SIZE_VALUE "Невірне значення розміру позиції!" +#define TRANSLATION_MESSAGE_MULTIPLE_TP_VOLUME_SHARE_SUM "Сума часток об'єму декількох ТП" +#define TRANSLATION_MESSAGE_INCORRECT_VOLUME_SUM "Невірна сума об'ємів декількох ТП - угода не буде відкрита." +#define TRANSLATION_MESSAGE_NETTING_MODE_DETECTED "Виявлено режим нетінгу. Робота з декількома ТП не можлива. Основний ТП встановлено на 100% об'єму." +#define TRANSLATION_MESSAGE_NOT_TAKING_A_TRADE "Угода не буде відкрита" +#define TRANSLATION_MESSAGE_NTAT_LINES "лінії сховано й панель налаштована так, щоб не торгувати при схованих лініях." +#define TRANSLATION_MESSAGE_NTAT_SPREAD "поточний спред" +#define TRANSLATION_MESSAGE_MAXIMUM_SPREAD "максимальний спред" +#define TRANSLATION_MESSAGE_NTAT_ENTRY_SL_DISTANCE "поточна відстань Вхід/СЛ" +#define TRANSLATION_MESSAGE_NTAT_TOTAL_NUMBER "поточна загальна кількість угод" +#define TRANSLATION_MESSAGE_NUMBER_OF_TRADES_IN_EXECUTION "кількість угод на виконанні" +#define TRANSLATION_MESSAGE_MAXIMUM_TOTAL_NUMBER_OF_TRADES_ALLOWED "максимально припустима загальна кількість угод" +#define TRANSLATION_MESSAGE_NTAT_PER_SYMBOL_NUMBER "поточна кількість угод по символу" +#define TRANSLATION_MESSAGE_MAXIMUM_PER_SYMBOL_NUMBER_OF_TRADES_ALLOWED "максимально припустима кількість угод по символу" +#define TRANSLATION_MESSAGE_TOTAL_POTENTIAL_RISK "загальний потенційний ризик" +#define TRANSLATION_MESSAGE_MAXIUMUM_TOTAL_RISK "максимально припустимий загальний ризик" +#define TRANSLATION_MESSAGE_INFINITE_TOTAL_POTENTIAL_RISK "нескінченний загальний потенційний ризик" +#define TRANSLATION_MESSAGE_PER_SYMBOL_POTENTIAL_RISK "потенційний ризик по символу" +#define TRANSLATION_MESSAGE_MAXIMUM_PER_SYMBOL_RISK "максимально припустимий ризик по символу" +#define TRANSLATION_MESSAGE_INFINITE_PER_SYMBOL_POTENTIAL_RISK "нескінченний потенційний ризик по символу" +#define TRANSLATION_MESSAGE_IGNORE_MARKET_EXECUTION_MODE_WARNING ", але IgnoreMarketExecutionMode = true. Перемикніть на false, якщо угоди не виконуються." +#define TRANSLATION_MESSAGE_EXECUTION_MODE "Режим виконання" +#define TRANSLATION_MESSAGE_ORDER_FILLING_MODE "Режим виконання по залишку" +#define TRANSLATION_MESSAGE_FILL_OR_KILL "Все або нічого" +#define TRANSLATION_MESSAGE_IMMEDIATE_OR_CANCEL "Все або частково" +#define TRANSLATION_MESSAGE_FOUND_EXISTING_BUY_VOLUME "Знайдений поточний об'єм на купівлю" +#define TRANSLATION_MESSAGE_FOUND_EXISTING_SELL_VOLUME "Знайдений поточний об'єм на продаж" +#define TRANSLATION_MESSAGE_ADJUSTED_POSITION_SIZE "Виправлений розмір позиції" +#define TRANSLATION_MESSAGE_ADJUSTED_POSITION_SIZE_LESS_THAN_ZERO "Виправлений розмір позиції менший за нуль. Угода не буде виконана." +#define TRANSLATION_MESSAGE_NTAT_TOTAL_VOLUME "поточний загальний об'єм" +#define TRANSLATION_MESSAGE_NTAT_NEW_POSITION_VOLUME "об'єм нової позиції" +#define TRANSLATION_MESSAGE_NTAT_MAXIMUM_TOTAL_VOLUME "максимально припустимий загальний об'єм" +#define TRANSLATION_MESSAGE_NTAT_PER_SYMBOL_VOLUME "поточний об'єм по символу" +#define TRANSLATION_MESSAGE_NTAT_MAXIMUM_PER_SYMBOL_VOLUME "максимально припустимий об'єм по символу" +#define TRANSLATION_MESSAGE_BROKER_MINIMUM "мінімальний розмір позиції в брокера. Угода не буде виконана." +#define TRANSLATION_MESSAGE_BROKER_MAXIMUM "максимальний розмір позиції в брокера. Позиція буде зменшена." +#define TRANSLATION_MESSAGE_ERROR_SENDING_ORDER "Помилка відправки ордеру" +#define TRANSLATION_MESSAGE_ORDER_EXECUTED "Ордер виконано." +#define TRANSLATION_MESSAGE_TICKET "Тікет" +#define TRANSLATION_MESSAGE_ORDER "Ордер" +#define TRANSLATION_MESSAGE_EXECUTED "виконано" +#define TRANSLATION_MESSAGE_ERROR_OPENING_POSITION "Помилка відкриття позиції" +#define TRANSLATION_MESSAGE_RETURN_CODE "Код повернення" +#define TRANSLATION_MESSAGE_INITIAL_RETURN_CODE "Первинний код повернення" +#define TRANSLATION_MESSAGE_ORDER_ID "ID ордера" +#define TRANSLATION_MESSAGE_DEAL_ID "ID угоди" +#define TRANSLATION_MESSAGE_POSITION_ID "ID позиції" +#define TRANSLATION_MESSAGE_ERROR_MODIFYING_POSITION "Помилка зміни позиції" +#define TRANSLATION_MESSAGE_SL_TP_APPLIED "СЛ/ТП додано успішно." +#define TRANSLATION_MESSAGE_ERROR_SELECTING_DEAL "Помилка вибору угоди" +#define TRANSLATION_MESSAGE_ERROR_SELECTING_DEAL_HISTORY "Помилка вибору історії угод" +#define TRANSLATION_MESSAGE_WAITING "Очікування..." +#define TRANSLATION_MESSAGE_ERROR_SELECTING_POSITIONS "Помилка вибору позицій" +#define TRANSLATION_MESSAGE_POSITION_SIZER_ON "Position Sizer на " +#define TRANSLATION_MESSAGE_EXECUTE_TRADE "Виконати угоду?" +#define TRANSLATION_MESSAGE_BUY "Купівля" +#define TRANSLATION_MESSAGE_BUY_STOP "Стоп на купівлю" +#define TRANSLATION_MESSAGE_BUY_LIMIT "Ліміт на купівлю" +#define TRANSLATION_MESSAGE_BUY_STOP_LIMIT "Стоп-ліміт на купівлю" +#define TRANSLATION_MESSAGE_SELL "Продаж" +#define TRANSLATION_MESSAGE_SELL_STOP "Стоп на продаж" +#define TRANSLATION_MESSAGE_SELL_LIMIT "Ліміт на продаж" +#define TRANSLATION_MESSAGE_SELL_STOP_LIMIT "Стоп-ліміт на продаж" +#define TRANSLATION_MESSAGE_SIZE "Розмір" +#define TRANSLATION_MESSAGE_MULTIPLE "кілька" +#define TRANSLATION_MESSAGE_TRADE_CANCELED "Угоду відмінено." +#define TRANSLATION_MESSAGE_POSITIONGETTICKET_FAILED "Функція PositionGetTicket не повернула результат" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_BUY_TSL "Функція PositionModify не змогла застосувати трейлінг-стоп на купівлю" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_SELL_TSL "Функція PositionModify не змогла застосувати трейлінг-стоп на продаж" +#define TRANSLATION_MESSAGE_TSL_APPLIED "Трейлінг-стоп застосовано до позиції" +#define TRANSLATION_MESSAGE_SL_WAS_MOVED_FROM "Стоп-лос зсунуто з" +#define TRANSLATION_MESSAGE_SL_WAS_MOVED_TO "на" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_BUY_BE "Функція PositionModify не змогла застосувати беззбиток на купівлю" +#define TRANSLATION_MESSAGE_POSITIONMODIFY_FAILED_SELL_BE "Функція PositionModify не змогла застосувати беззбиток на продаж" +#define TRANSLATION_MESSAGE_BE_APPLIED "Беззбиток застосовано до позиції" +#define TRANSLATION_MESSAGE_BE_FOR "Беззбиток для " +#define TRANSLATION_MESSAGE_ERROR_SETTING_TIMER "Помилка встановлення таймеру" +#define TRANSLATION_MESSAGE_FAILED_DELETE_INI "Не вдалося видалити ini-файл панелі" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT "Не можна перевести" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT_TO "у" +#define TRANSLATION_MESSAGE_CANNOT_CONVERT_CALCULATION "Розрахунок може бути хибним для" \ No newline at end of file