//+-------------------------------------------+ //| NLD_Include.mqh | //| http://www.nelodi.com | //| Copyright (c) 2019 NELODI.com | //+-------------------------------------------+ ulong EXP_MAGIC = 197502032019010203; // General Expert UID ulong MA_MAGIC = 0; // This Expert UID int ExtDeviation = 3; // Expert Deviation (pips) {3} bool ExtAsyncMode = false; // Expert Async Mode? string MA_Symbol = ""; // Expert Symbol double MA_Commission=0; double defPix=0,xMarginStop=0; double minTradeVol=0,tradePixValue=0,tradeTickValue=0; double comSpread=0,buySpread=0,sellSpread=0; double buyOpen=0,buyStop=0,buyClose=0,buyCurrent=0,buyProfit=0,buyZero=0,buyVolume=0,buyTickCost=0,buyTicks=0; double sellOpen=0,sellStop=0,sellClose=0,sellCurrent=0,sellProfit=0,sellZero=0,sellVolume=0,sellTickCost=0,sellTicks=0; double buyTotal=0,sellTotal=0,currVolume=0,bestProfit=0; bool isBuy=false,isSell=false; string lastSymbol="",bestType=""; int ExtRange0,ExtRange1,ExtRange2,ExtRange3,ExtRange4,ExtRange5,ExtraRange,VisibleRange; datetime perSeconds; //+------------------------------------------------------------------+ void Clear_ExpertData() { lastSymbol=""; currVolume=0; buyTickCost=0; sellTickCost=0; buyTicks=0; sellTicks=0; buyOpen=0; buyClose=0; buyStop=0; buyCurrent=0; buyProfit=0; buyZero=0; buyVolume=0; sellOpen=0; sellClose=0; sellStop=0; sellCurrent=0; sellProfit=0; sellZero=0; sellVolume=0; buyTotal=0; sellTotal=0; bestProfit=0; bestType=""; isBuy=false; isSell=false; } //+------------------------------------------------------------------+ void updateBuyTotal() { buyTotal+=buyProfit; buyProfit=0; } //+------------------------------------------------------------------+ void updateSellTotal() { sellTotal+=sellProfit; sellProfit=0; } //+------------------------------------------------------------------+ bool selectBuyPosition(int id=0,bool any=false) { if(Select_Position(id)) { currVolume=PositionGetDouble(POSITION_VOLUME); if(isBuy) { buyOpen=PositionGetDouble(POSITION_PRICE_OPEN); buyCurrent=PositionGetDouble(POSITION_PRICE_CURRENT); buyStop=PositionGetDouble(POSITION_SL); if(buyStop==0) buyStop=buyOpen; buyProfit=PositionGetDouble(POSITION_PROFIT)+PositionGetDouble(POSITION_SWAP)-MathCeil(MA_Commission*currVolume/SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN)*100.0)/100.0; if(buyProfit==0) buyZero=buyCurrent; else buyZero=buyCurrent-buyProfit*tradePixValue*SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN)/currVolume; return(true); } if(any) return(true); } return(false); } //+------------------------------------------------------------------+ bool selectSellPosition(int id=0,bool any=false) { if(Select_Position(id)) { currVolume=PositionGetDouble(POSITION_VOLUME); if(isSell) { sellOpen=PositionGetDouble(POSITION_PRICE_OPEN); sellCurrent=PositionGetDouble(POSITION_PRICE_CURRENT); sellStop=PositionGetDouble(POSITION_SL); if(sellStop==0) sellStop=sellOpen; sellProfit=PositionGetDouble(POSITION_PROFIT)+PositionGetDouble(POSITION_SWAP)-MathCeil(MA_Commission*currVolume/SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN)*100.0)/100.0; if(sellProfit==0) sellZero=sellCurrent; else sellZero=sellCurrent+sellProfit*tradePixValue*SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN)/currVolume; return(true); } if(any) return(true); } return(false); } //+------------------------------------------------------------------+ bool selectAnyPosition(int id) { if(Select_Position(id)) { if(isBuy) { currVolume=PositionGetDouble(POSITION_VOLUME); buyOpen=PositionGetDouble(POSITION_PRICE_OPEN); buyCurrent=PositionGetDouble(POSITION_PRICE_CURRENT); buyStop=PositionGetDouble(POSITION_SL); if(buyStop==0) buyStop=buyOpen; buyProfit=PositionGetDouble(POSITION_PROFIT)+PositionGetDouble(POSITION_SWAP)-MathCeil(MA_Commission*currVolume/SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN)*100.0)/100.0; if(buyProfit==0) buyZero=buyCurrent; else buyZero=buyCurrent-buyProfit*tradePixValue*SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN)/currVolume; return(true); } else if(isSell) { currVolume=PositionGetDouble(POSITION_VOLUME); sellOpen=PositionGetDouble(POSITION_PRICE_OPEN); sellCurrent=PositionGetDouble(POSITION_PRICE_CURRENT); sellStop=PositionGetDouble(POSITION_SL); if(sellStop==0) sellStop=sellOpen; sellProfit=PositionGetDouble(POSITION_PROFIT)+PositionGetDouble(POSITION_SWAP)-MathCeil(MA_Commission*currVolume/SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN)*100.0)/100.0; if(sellProfit==0) sellZero=sellCurrent; else sellZero=sellCurrent+sellProfit*tradePixValue*SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN)/currVolume; return(true); } else { currVolume=PositionGetDouble(POSITION_VOLUME); return(true); } } return(false); } //+------------------------------------------------------------------+ bool closeNow(string comment="") { if(TerminalInfoInteger(TERMINAL_TRADE_ALLOWED)) return(PositionClose(comment)); return(false); } //+------------------------------------------------------------------+ bool openSell(const double volume,const double price,const double stopLossPrice,const double takeProfitPrice,string comment) { return(openNow(ORDER_TYPE_SELL,volume,price,stopLossPrice,takeProfitPrice,comment)); } //+------------------------------------------------------------------+ bool openBuy(const double volume,const double price,const double stopLossPrice,const double takeProfitPrice,string comment) { return(openNow(ORDER_TYPE_BUY,volume,price,stopLossPrice,takeProfitPrice,comment)); } //+------------------------------------------------------------------+ bool tradeAllowed() { return((bool)TerminalInfoInteger(TERMINAL_TRADE_ALLOWED)); } //+------------------------------------------------------------------+ //+------------------------------------------------------------------+ bool ExtHedging; ENUM_SYMBOL_CALC_MODE ExtCalcMode; ENUM_ACCOUNT_MARGIN_MODE ExtMarginMode; MqlTradeRequest m_request; // request data MqlTradeResult m_result; // result data MqlTradeCheckResult m_check_result; // result check data //+------------------------------------------------------------------+ bool PrepareAccount(const string sym,double commisForex,double commisStock,double eMarginStop=0) { xMarginStop=(eMarginStop<0 ? 0 : eMarginStop>90 ? 90 : eMarginStop); perSeconds=PeriodSeconds(); MA_Commission=0; MA_Symbol=sym; ExtMarginMode=(ENUM_ACCOUNT_MARGIN_MODE)AccountInfoInteger(ACCOUNT_MARGIN_MODE); ExtHedging=(ExtMarginMode==ACCOUNT_MARGIN_MODE_RETAIL_HEDGING); if(MA_Symbol!="") { ExtCalcMode=(ENUM_SYMBOL_CALC_MODE)SymbolInfoInteger(MA_Symbol,SYMBOL_TRADE_CALC_MODE); if(ExtCalcMode==0) MA_Commission=commisForex; else { if(StringFind(MA_Symbol,".")>=0) MA_Commission=commisStock; else MA_Commission=0; } minTradeVol=SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MIN); tradeTickValue=TradeTickValue(); defPix=MathPow(10,SymbolInfoInteger(MA_Symbol,SYMBOL_DIGITS)); if((minTradeVol>0) && (tradeTickValue>0) && (defPix>0)) tradePixValue=1/(tradeTickValue*defPix); else tradePixValue=0; if(MA_Commission>0) comSpread=MA_Commission*tradePixValue; else comSpread=0; buySpread=-buySwap(); if(buySpread>0) buySpread=buySpread*tradePixValue; else buySpread=0; sellSpread=-sellSwap(); if(sellSpread>0) sellSpread=sellSpread*tradePixValue; else sellSpread=0; } else { defPix=0; tradeTickValue=0; tradePixValue=0; minTradeVol=0; comSpread=0; buySpread=0; sellSpread=0; } ExtRange0=3; ExtRange1=3*3; ExtRange2=3*3*3; ExtRange3=3*3*3*3; ExtRange4=3*3*3*3*3; ExtRange5=3*3*3*3*3*3; switch(_Period) { case PERIOD_MN1: { ExtRange0=3; // 90D (3M) ExtRange1=12; // 360D (1Y) ExtRange2=36; // 1080D (3Y) ExtRange3=120; // 3600D (10Y) ExtRange4=240; // 7200D (20Y) ExtRange5=480; // 7200D (40Y) break; } case PERIOD_W1: { ExtRange0=4; // 28D (1M) ExtRange1=14; // 98D (3M) ExtRange2=55; // 385D (1Y) ExtRange3=165; // 1155D (3Y) ExtRange4=522; // 3654D (10Y) ExtRange5=1044; // 1044D (20Y) break; } case PERIOD_D1: { ExtRange0=2*4; // 8D (1W) ExtRange1=2*4*4; // 32D (1M) ExtRange2=2*4*4*3; // 96D (3M) ExtRange3=2*4*4*3*4; // 384D (1Y) ExtRange4=2*4*4*3*4*3; // 1152D (3Y) ExtRange5=2*4*4*3*4*10; // 3654D (10Y) break; } case PERIOD_H8: { ExtRange0=6*4; // 8D (1W) ExtRange1=6*4*4; // 32D (1M) ExtRange2=6*4*4*3; // 96D (3M) ExtRange3=6*4*4*3*4; // 384D (1Y) ExtRange4=6*4*4*3*4*3; // 1152D (3Y) ExtRange5=6*4*4*3*4*10; // 3654D (10Y) break; } case PERIOD_H4: { ExtRange0=3*4; // 2D ExtRange1=3*4*4; // 8D (1W) ExtRange2=3*4*4*4; // 32D (1M) ExtRange3=3*4*4*4*3; // 96D (3M) ExtRange4=3*4*4*4*3*4; // 384D (1Y) ExtRange5=3*4*4*4*3*4*3; // 1152D (3Y) break; } case PERIOD_H1: { ExtRange0=4*3; // 12H ExtRange1=4*3*4; // 2D ExtRange2=4*3*4*4; // 8D (1W) ExtRange3=4*3*4*4*4; // 32D (1M) ExtRange4=4*3*4*4*4*3; // 96D (3M) ExtRange5=4*3*4*4*4*3*4; // 384D (1Y) break; } case PERIOD_M15: { ExtRange0=4*4; // 4H ExtRange1=4*4*3; // 12H ExtRange2=4*4*3*4; // 2D ExtRange3=4*4*3*4*4; // 8D (1W) ExtRange4=4*4*3*4*4*4; // 32D (1M) ExtRange5=4*4*3*4*4*4*3; // 96D (3M) break; } case PERIOD_M5: { ExtRange0=3*4; // 1H ExtRange1=3*4*4; // 4H ExtRange2=3*4*4*3; // 12H ExtRange3=3*4*4*3*4; // 2D ExtRange4=3*4*4*3*4*4; // 8D (1W) ExtRange5=3*4*4*3*4*4*4; // 32D (1M) break; } case PERIOD_M1: { ExtRange0=5*3; // 15M ExtRange1=5*3*4; // 1H ExtRange2=5*3*4*4; // 4H ExtRange3=5*3*4*4*3; // 12H ExtRange4=5*3*4*4*3*4; // 2D ExtRange5=5*3*4*4*3*4*4; // 8D break; } } VisibleRange=(int)ChartGetInteger(0,CHART_VISIBLE_BARS,0); ExtraRange=(int)(ChartGetInteger(0,CHART_WIDTH_IN_BARS,0)-VisibleRange)*(225-55)/225; if(ExtraRangeExtRange3) ExtraRange=ExtRange3; return(false); } //+------------------------------------------------------------------+ double buySwap() { if(MA_Symbol!="") return(SymbolInfoDouble(MA_Symbol,SYMBOL_SWAP_LONG)); else return(0); } //+------------------------------------------------------------------+ double sellSwap() { if(MA_Symbol!="") return(SymbolInfoDouble(MA_Symbol,SYMBOL_SWAP_SHORT)); else return(0); } //+------------------------------------------------------------------+ bool openNow(ENUM_ORDER_TYPE signal,const double volume,const double price,const double stopLossPrice,const double takeProfitPrice,string comment="") { if(MA_Symbol!="" && TerminalInfoInteger(TERMINAL_TRADE_ALLOWED)) { return(PositionOpen(signal,TradeSizeOptimized(volume),price,stopLossPrice,takeProfitPrice,comment)); } return(false); } //+------------------------------------------------------------------+ double TradeSizeOptimized(double volume) { if(MA_Symbol!="") { double stepvol=SymbolInfoDouble(MA_Symbol,SYMBOL_VOLUME_STEP); double lot=stepvol*NormalizeDouble(volume/stepvol,0); double minvol=SymbolInfoDouble(MA_Symbol,SYMBOL_VOLUME_MIN); if(lotmaxvol) lot=maxvol; return(lot); } else return(0); } //+------------------------------------------------------------------+ double TradeCost(void) { if(MA_Symbol!="") return(MA_Commission+TradeTickValue()*SymbolInfoInteger(_Symbol,SYMBOL_SPREAD)); return(0); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ double TradeTickValue(void) { if(MA_Symbol!="") return(SymbolInfoDouble(MA_Symbol,SYMBOL_TRADE_TICK_VALUE)*TradeSizeOptimized(0)); return(0); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ int Count_Positions(void) { return(PositionsTotal()); } //+------------------------------------------------------------------+ bool Select_Position(int id) { isBuy=false; isSell=false; if(ExtHedging) { string position_symbol=PositionGetSymbol(id); if(position_symbol=="") return(false); if((position_symbol==MA_Symbol || MA_Symbol=="") && (MA_MAGIC==0 || PositionGetInteger(POSITION_MAGIC)==MA_MAGIC)) { switch((ENUM_POSITION_TYPE)PositionGetInteger(POSITION_TYPE)) { case POSITION_TYPE_BUY: isBuy=true; break; case POSITION_TYPE_SELL: isSell=true; break; } } lastSymbol=position_symbol; return(isBuy || isSell); } else if(MA_Symbol!="") { //--- check position in Netting mode if(!PositionSelect(MA_Symbol)) return(false); else if(MA_MAGIC==0 || PositionGetInteger(POSITION_MAGIC)==MA_MAGIC) { lastSymbol=MA_Symbol; switch((ENUM_POSITION_TYPE)PositionGetInteger(POSITION_TYPE)) { case POSITION_TYPE_BUY: isBuy=true; break; case POSITION_TYPE_SELL: isSell=true; break; } } lastSymbol=MA_Symbol; return(isBuy || isSell); } else return(false); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ bool Check_Position(int id=0) { isBuy=false; isSell=false; if(ExtHedging) { string position_symbol=PositionGetSymbol(id); if(position_symbol=="") return(false); if((position_symbol==MA_Symbol || MA_Symbol=="") && (MA_MAGIC==0 || PositionGetInteger(POSITION_MAGIC)==MA_MAGIC)) { lastSymbol=position_symbol; switch((ENUM_POSITION_TYPE)PositionGetInteger(POSITION_TYPE)) { case POSITION_TYPE_BUY: isBuy=true; return(true); case POSITION_TYPE_SELL: isSell=true; return(true); } } return(false); } else if(MA_Symbol!="") { //--- check position in Netting mode if(!PositionSelect(MA_Symbol)) return(false); else if(MA_MAGIC==0 || PositionGetInteger(POSITION_MAGIC)==MA_MAGIC) { lastSymbol=MA_Symbol; switch((ENUM_POSITION_TYPE)PositionGetInteger(POSITION_TYPE)) { case POSITION_TYPE_BUY: isBuy=true; return(true); case POSITION_TYPE_SELL: isSell=true; return(true); } } return(false); } else return(false); } //+------------------------------------------------------------------+ bool PositionOpen(const ENUM_ORDER_TYPE order_type, const double volume, const double price, const double stopLossPrice, const double takeProfitPrice, const string comment="") { if(IsStopped(__FUNCTION__)) return(false); if(MA_Symbol=="") return(false); if(volume<=0) return(false); ClearStructures(); if(order_type!=ORDER_TYPE_BUY && order_type!=ORDER_TYPE_SELL) { m_result.retcode=TRADE_RETCODE_INVALID; m_result.comment="Invalid order type"; return(false); } double sl=0,tp=0; double bid=SymbolInfoDouble(MA_Symbol,SYMBOL_BID); double ask=SymbolInfoDouble(MA_Symbol,SYMBOL_ASK); if(order_type==ORDER_TYPE_BUY) { if(stopLossPrice>0) sl=bid-stopLossPrice*tradePixValue; if(takeProfitPrice>0) tp=ask+takeProfitPrice*tradePixValue; } else { if(stopLossPrice>0) sl=ask+stopLossPrice*tradePixValue; if(takeProfitPrice>0) tp=bid-takeProfitPrice*tradePixValue; } m_request.action =TRADE_ACTION_DEAL; m_request.symbol =MA_Symbol; m_request.magic =MA_MAGIC; m_request.volume =volume; m_request.type =order_type; m_request.price =(price>0 ? price : (order_type==ORDER_TYPE_SELL ? bid : ask)); m_request.sl =sl; m_request.tp =tp; m_request.deviation=ExtDeviation; if(!OrderTypeCheck(MA_Symbol)) return(false); if(!FillingCheck(MA_Symbol)) return(false); m_request.comment=comment; bool res=OrderSendAsync(m_request,m_result); if(!res) { string txt="ERR #"+IntegerToString(m_result.retcode_external)+" OPEN "; if(m_request.type==ORDER_TYPE_BUY) txt+="BUY @ "; else txt+="SELL @ "; int digits=(int)SymbolInfoInteger(lastSymbol,SYMBOL_DIGITS); txt+=DoubleToString(m_request.price,digits); txt+=" ("+DoubleToString(m_result.price,digits)+")"; Print(txt); } else { if(m_request.type==ORDER_TYPE_BUY) buyOpen=m_request.price; else sellOpen=m_request.price; } return(res); } //+------------------------------------------------------------------+ bool PositionClose(const string comment="") { if(IsStopped(__FUNCTION__)) return(false); bool partial_close=false; double reqPrice=0; bool res=false; int retry_count =10; uint retcode =TRADE_RETCODE_REJECT; ClearStructures(); if(!FillingCheck(lastSymbol)) return(false); do { if((ENUM_POSITION_TYPE)PositionGetInteger(POSITION_TYPE)==POSITION_TYPE_BUY) { //--- prepare request for close BUY position m_request.type=ORDER_TYPE_SELL; if(buyCurrent>0) m_request.price=buyCurrent; else m_request.price=SymbolInfoDouble(lastSymbol,SYMBOL_BID); reqPrice=m_request.price; } else { //--- prepare request for close SELL position m_request.type=ORDER_TYPE_BUY; if(sellCurrent>0) m_request.price=sellCurrent; else m_request.price=SymbolInfoDouble(lastSymbol,SYMBOL_ASK); reqPrice=m_request.price; } //--- setting request m_request.action =TRADE_ACTION_DEAL; m_request.symbol =lastSymbol; m_request.volume =PositionGetDouble(POSITION_VOLUME); m_request.magic =MA_MAGIC; m_request.deviation=ExtDeviation; m_request.comment=comment; //--- check volume double max_volume=SymbolInfoDouble(lastSymbol,SYMBOL_VOLUME_MAX); if(m_request.volume>max_volume) { m_request.volume=max_volume; partial_close=true; } else partial_close=false; //--- hedging? just send order if(ExtHedging) { m_request.position=PositionGetInteger(POSITION_TICKET); res=OrderSendAsync(m_request,m_result); break; } //--- order send res=OrderSendAsync(m_request,m_result); if(!res) { if(--retry_count!=0) continue; if(retcode==TRADE_RETCODE_DONE_PARTIAL) m_result.retcode=retcode; break; } //--- WARNING. If position volume exceeds the maximum volume allowed for deal, //--- and when the asynchronous trade mode is on, for safety reasons, position is closed not completely, //--- but partially. It is decreased by the maximum volume allowed for deal. if(ExtAsyncMode) break; retcode=TRADE_RETCODE_DONE_PARTIAL; if(partial_close) Sleep(10); } while(partial_close); if(!res) { if(m_result.retcode_external!=0) { string txt="ERR #"+IntegerToString(m_result.retcode_external)+" CLOSE "; if(m_request.type==ORDER_TYPE_SELL) txt+="BUY @ "; else txt+="SELL @ "; int digits=(int)SymbolInfoInteger(lastSymbol,SYMBOL_DIGITS); txt+=DoubleToString(m_request.price,digits); txt+=" ("+DoubleToString(m_result.price,digits)+")"; Print(txt); } } else { if(m_request.type==ORDER_TYPE_SELL) { // close BUY if(m_result.price>0) buyClose=m_result.price; else buyClose=reqPrice; if(buyOpen>0 && buyClose>0 && buyClose!=buyOpen) buyProfit=NormalizeDouble(buyProfit*(reqPrice-buyOpen)/(buyClose-buyOpen),2); else buyProfit=0; updateBuyTotal(); } else { if(m_result.price>0) sellClose=m_result.price; else sellClose=reqPrice; if(sellOpen>0 && sellClose>0 && sellClose!=sellOpen) sellProfit=NormalizeDouble(sellProfit*(sellOpen-reqPrice)/(sellOpen-sellClose),2); else sellProfit=0; updateSellTotal(); } } return(res); } //+------------------------------------------------------------------+ bool UpdateStopLossTakeProfit(double stopLossPrice,double takeProfitPrice) { if(IsStopped(__FUNCTION__)) return(false); double sl=PositionGetDouble(POSITION_SL); double tp=PositionGetDouble(POSITION_TP); double todo=false; double bid=SymbolInfoDouble(MA_Symbol,SYMBOL_BID); double ask=SymbolInfoDouble(MA_Symbol,SYMBOL_ASK); if(PositionGetInteger(POSITION_TYPE)==POSITION_TYPE_BUY) { double best=MathMax(PositionGetDouble(POSITION_PRICE_OPEN)+comSpread,ask); if((stopLossPrice>0) && ((sl==0) || (sl0) && ((tp==0) || (tp0) && ((sl==0) || (sl>ask+stopLossPrice*tradePixValue))) { todo=true; sl=ask+stopLossPrice*tradePixValue; } if((takeProfitPrice>0) && ((tp==0) || (tp>best-takeProfitPrice*tradePixValue))) { todo=true; tp=best-takeProfitPrice*tradePixValue; } } if(!todo) return(true); bool res=false; uint retcode=TRADE_RETCODE_REJECT; ClearStructures(); if(!FillingCheck(lastSymbol)) return(false); m_request.action=TRADE_ACTION_SLTP; // type of trade operation m_request.symbol=lastSymbol; // symbol m_request.sl=sl; // Stop Loss of the position m_request.tp=tp; // Take Profit of the position m_request.magic=MA_MAGIC; //--- hedging? just send order if(ExtHedging) { m_request.position=PositionGetInteger(POSITION_TICKET); res=OrderSendAsync(m_request,m_result); } else { res=OrderSendAsync(m_request,m_result); if(!res) { if(retcode==TRADE_RETCODE_DONE_PARTIAL) m_result.retcode=retcode; } else retcode=TRADE_RETCODE_DONE_PARTIAL; } if(!res && (m_result.retcode_external!=0)) { string txt="ERR #"+IntegerToString(m_result.retcode_external)+" SL "; int digits=(int)SymbolInfoInteger(lastSymbol,SYMBOL_DIGITS); txt+=DoubleToString(m_request.sl,digits); txt+=" / TP "+DoubleToString(m_request.tp,digits); Print(txt); } return(res); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ bool IsStopped(const string function) { if(!IsStopped()) return(false); PrintFormat("%s: MQL5 program is stopped. Trading is disabled",function); return(true); } //+------------------------------------------------------------------+ void ClearStructures() { ZeroMemory(m_request); ZeroMemory(m_result); ZeroMemory(m_check_result); } //+------------------------------------------------------------------+ bool OrderTypeCheck(const string sym) { bool res=false; long flags=0; if(!SymbolInfoInteger(sym,SYMBOL_ORDER_MODE,flags)) return(false); //--- depending on the type of order in request switch(m_request.type) { case ORDER_TYPE_BUY: case ORDER_TYPE_SELL: res=((flags&SYMBOL_ORDER_MARKET)!=0); break; case ORDER_TYPE_BUY_LIMIT: case ORDER_TYPE_SELL_LIMIT: res=((flags&SYMBOL_ORDER_LIMIT)!=0); break; case ORDER_TYPE_BUY_STOP: case ORDER_TYPE_SELL_STOP: res=((flags&SYMBOL_ORDER_STOP)!=0); break; case ORDER_TYPE_BUY_STOP_LIMIT: case ORDER_TYPE_SELL_STOP_LIMIT: res=((flags&SYMBOL_ORDER_STOP_LIMIT)!=0); break; default: break; } if(res) { //--- trading order is valid //--- check if we need and able to set protective orders if(m_request.sl!=0.0 || m_request.tp!=0.0) { if((flags&SYMBOL_ORDER_SL)==0) m_request.sl=0.0; if((flags&SYMBOL_ORDER_TP)==0) m_request.tp=0.0; } } else { //--- trading order is not valid //--- set error m_result.retcode=TRADE_RETCODE_INVALID_ORDER; Print(__FUNCTION__+": Invalid order type"); } return(res); } //+------------------------------------------------------------------+ //| Checks and corrects type of filling policy | //+------------------------------------------------------------------+ bool FillingCheck(const string sym) { ENUM_ORDER_TYPE_FILLING ExtTypeFilling=ORDER_FILLING_RETURN; //--- get execution mode of orders by symbol ENUM_SYMBOL_TRADE_EXECUTION exec=(ENUM_SYMBOL_TRADE_EXECUTION)SymbolInfoInteger(sym,SYMBOL_TRADE_EXEMODE); //--- check execution mode if(exec==SYMBOL_TRADE_EXECUTION_REQUEST || exec==SYMBOL_TRADE_EXECUTION_INSTANT) return(true); //--- neccessary filling type will be placed automatically //--- get possible filling policy types by symbol uint filling=(uint)SymbolInfoInteger(sym,SYMBOL_FILLING_MODE); //--- check execution mode again if(exec==SYMBOL_TRADE_EXECUTION_MARKET) { //--- for the MARKET execution mode //--- analyze order if(m_request.action!=TRADE_ACTION_PENDING) { //--- in case of instant execution order //--- if the required filling policy is supported, add it to the request if((filling&SYMBOL_FILLING_FOK)==SYMBOL_FILLING_FOK) { ExtTypeFilling=ORDER_FILLING_FOK; m_request.type_filling=ExtTypeFilling; return(true); } if((filling&SYMBOL_FILLING_IOC)==SYMBOL_FILLING_IOC) { ExtTypeFilling=ORDER_FILLING_IOC; m_request.type_filling=ExtTypeFilling; return(true); } //--- wrong filling policy, set error code m_result.retcode=TRADE_RETCODE_INVALID_FILL; return(false); } return(true); } else { if((filling&SYMBOL_FILLING_FOK)==SYMBOL_FILLING_FOK) { ExtTypeFilling=ORDER_FILLING_FOK; } if((filling&SYMBOL_FILLING_IOC)==SYMBOL_FILLING_IOC) { ExtTypeFilling=ORDER_FILLING_IOC; } } //--- EXCHANGE execution mode switch(ExtTypeFilling) { case ORDER_FILLING_FOK: //--- analyze order if(m_request.action==TRADE_ACTION_PENDING) { //--- in case of pending order //--- add the expiration mode to the request if(!ExpirationCheck(sym)) m_request.type_time=ORDER_TIME_DAY; //--- stop order? if(m_request.type==ORDER_TYPE_BUY_STOP || m_request.type==ORDER_TYPE_SELL_STOP || m_request.type==ORDER_TYPE_BUY_LIMIT || m_request.type==ORDER_TYPE_SELL_LIMIT) { //--- in case of stop order //--- add the corresponding filling policy to the request m_request.type_filling=ORDER_FILLING_RETURN; return(true); } } //--- in case of limit order or instant execution order //--- if the required filling policy is supported, add it to the request if((filling&SYMBOL_FILLING_FOK)==SYMBOL_FILLING_FOK) { m_request.type_filling=ExtTypeFilling; return(true); } //--- wrong filling policy, set error code m_result.retcode=TRADE_RETCODE_INVALID_FILL; return(false); case ORDER_FILLING_IOC: //--- analyze order if(m_request.action==TRADE_ACTION_PENDING) { //--- in case of pending order //--- add the expiration mode to the request if(!ExpirationCheck(sym)) m_request.type_time=ORDER_TIME_DAY; //--- stop order? if(m_request.type==ORDER_TYPE_BUY_STOP || m_request.type==ORDER_TYPE_SELL_STOP || m_request.type==ORDER_TYPE_BUY_LIMIT || m_request.type==ORDER_TYPE_SELL_LIMIT) { //--- in case of stop order //--- add the corresponding filling policy to the request m_request.type_filling=ORDER_FILLING_RETURN; return(true); } } //--- in case of limit order or instant execution order //--- if the required filling policy is supported, add it to the request if((filling&SYMBOL_FILLING_IOC)==SYMBOL_FILLING_IOC) { m_request.type_filling=ExtTypeFilling; return(true); } //--- wrong filling policy, set error code m_result.retcode=TRADE_RETCODE_INVALID_FILL; return(false); case ORDER_FILLING_RETURN: //--- add filling policy to the request m_request.type_filling=ExtTypeFilling; return(true); } //--- unknown execution mode, set error code m_result.retcode=TRADE_RETCODE_ERROR; return(false); } //+------------------------------------------------------------------+ bool ExpirationCheck(const string sym) { long flags=0; if(!SymbolInfoInteger(sym,SYMBOL_EXPIRATION_MODE,flags)) return(false); //--- check type switch(m_request.type_time) { case ORDER_TIME_GTC: if((flags&SYMBOL_EXPIRATION_GTC)!=0) return(true); case ORDER_TIME_DAY: if((flags&SYMBOL_EXPIRATION_DAY)!=0) return(true); case ORDER_TIME_SPECIFIED: if((flags&SYMBOL_EXPIRATION_SPECIFIED)!=0) return(true); case ORDER_TIME_SPECIFIED_DAY: if((flags&SYMBOL_EXPIRATION_SPECIFIED_DAY)!=0) return(true); default: Print(__FUNCTION__+": Unknown expiration type"); } //--- failed return(false); } //+------------------------------------------------------------------+ double currentBuyPrice=0,currentSellPrice=0; double bestBuyPrice=0,worstBuyPrice=0,midBuyPrice=0; double buyPlusProfit=0,buyMinusProfit=0,buyOpenProfit=0; int buys=0,buyP=0,buyL=0; double bestSellPrice=0,worstSellPrice=0,midSellPrice=0; double sellPlusProfit=0,sellMinusProfit=0,sellOpenProfit=0; int sells=0,sellP=0,sellL=0; //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ bool doUpdateInfo() { double _buyPlusProfit=buyPlusProfit,_buyMinusProfit=buyMinusProfit,_buyOpenProfit=buyOpenProfit; int _buys=buys,_buyP=buyP,_buyL=buyL; double _sellPlusProfit=sellPlusProfit,_sellMinusProfit=sellMinusProfit,_sellOpenProfit=sellOpenProfit; int _sells=sells,_sellP=sellP,_sellL=sellL; currentBuyPrice=0; currentSellPrice=0; if(MA_Symbol!="") { currentBuyPrice=SymbolInfoDouble(MA_Symbol,SYMBOL_ASK); currentSellPrice=SymbolInfoDouble(MA_Symbol,SYMBOL_BID); } bool haveBest=false; bestProfit=0; bestType=""; buyTickCost=0; sellTickCost=0; buyTicks=0; sellTicks=0; buyVolume=0; sellVolume=0; midBuyPrice=0; midSellPrice=0; bestBuyPrice=0; bestSellPrice=0; worstBuyPrice=0; worstSellPrice=0; buyPlusProfit=0; buyMinusProfit=0; buyOpenProfit=0; sellPlusProfit=0; sellMinusProfit=0; sellOpenProfit=0; buys=0; buyP=0; buyL=0; sells=0; sellP=0; sellL=0; int myCnt=0; int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectAnyPosition(cnt)) { if(isBuy) { if(minTradeVol>0) myCnt=(int)MathRound(currVolume/minTradeVol); else myCnt=1; if((haveBest==false) || (buyProfit>bestProfit)) { haveBest=true; bestProfit=buyProfit; bestType="B"; } buyOpenProfit+=buyProfit; buys++; if(buyProfit>0) { buyPlusProfit+=buyProfit; buyP+=myCnt; } else { buyMinusProfit+=buyProfit; buyL+=myCnt; } if(bestBuyPrice==0) bestBuyPrice=buyOpen; else if(buyOpenworstBuyPrice) worstBuyPrice=buyStop; midBuyPrice=midBuyPrice+buyZero*currVolume; buyVolume=buyVolume+currVolume; } else if(isSell) { if(minTradeVol>0) myCnt=(int)MathRound(currVolume/minTradeVol); else myCnt=1; if((haveBest==false) || (sellProfit>bestProfit)) { haveBest=true; bestProfit=sellProfit; bestType="S"; } sellOpenProfit+=sellProfit; sells++; if(sellProfit>0) { sellPlusProfit+=sellProfit; sellP+=myCnt; } else { sellMinusProfit+=sellProfit; sellL+=myCnt; } if(bestSellPrice==0) bestSellPrice=sellOpen; else if(sellOpen>bestSellPrice) bestSellPrice=sellOpen; if(worstSellPrice==0) worstSellPrice=sellStop; else if(sellStop0) midBuyPrice=midBuyPrice/buyVolume; if(sellVolume>0) midSellPrice=midSellPrice/sellVolume; if(minTradeVol>0) { buyTicks=buyVolume/minTradeVol; sellTicks=sellVolume/minTradeVol; buyTickCost=buyTicks*tradeTickValue; sellTickCost=sellTicks*tradeTickValue; } return((_buyPlusProfit!=buyPlusProfit)||(_buyMinusProfit!=buyMinusProfit)||(_buyOpenProfit!=buyOpenProfit)|| (_buys!=buys) || (_buyP!=buyP) || (_buyL!=buyL) || (sellPlusProfit!=sellPlusProfit) || (_sellMinusProfit!=sellMinusProfit) || (_sellOpenProfit!=sellOpenProfit) || (_sells!=sells) || (_sellP!=sellP) || (_sellL!=sellL)); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ double nextBuyTarget(double nextVolume) { double myPrice=currentBuyPrice+comSpread; if(buyVolume>0) return((midBuyPrice*buyVolume+myPrice*nextVolume)/(buyVolume+nextVolume)); else return(myPrice); } //+------------------------------------------------------------------+ double nextSellTarget(double nextVolume) { double myPrice=currentSellPrice-comSpread; if(sellVolume>0) return((midSellPrice*sellVolume+myPrice*nextVolume)/(sellVolume+nextVolume)); else return(myPrice); } //+------------------------------------------------------------------+ long currSpread() { if(MA_Symbol!="") return(SymbolInfoInteger(MA_Symbol,SYMBOL_SPREAD)); else return(0); } //+------------------------------------------------------------------+ void doUpdateBuyInfo() { buyPlusProfit=0; buyMinusProfit=0; buyOpenProfit=0; buys=0; buyP=0; buyL=0; int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectBuyPosition(cnt,false)) { buyOpenProfit+=buyProfit; buys++; if(buyProfit>0) { buyP++; buyPlusProfit+=buyProfit; } else { buyL++; buyMinusProfit+=buyProfit; } } } } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ void doUpdateSellInfo() { sellPlusProfit=0; sellMinusProfit=0; sellOpenProfit=0; sells=0; sellP=0; sellL=0; int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectSellPosition(cnt,false)) { sellOpenProfit+=sellProfit; sells++; if(sellProfit>0) { sellP++; sellPlusProfit+=sellProfit; } else { sellL++; sellMinusProfit+=sellProfit; } } } } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ void doUpdateBuySellInfo() { sellPlusProfit=0; sellMinusProfit=0; sellOpenProfit=0; buyPlusProfit=0; buyMinusProfit=0; buyOpenProfit=0; sells=0; sellP=0; sellL=0; buys=0; buyP=0; buyL=0; int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectAnyPosition(cnt)) { if(isBuy) { buyOpenProfit+=buyProfit; buys++; if(buyProfit>0) { buyP++; buyPlusProfit+=buyProfit; } else { buyL++; buyMinusProfit+=buyProfit; } } else if(isSell) { sellOpenProfit+=sellProfit; sells++; if(sellProfit>0) { sellP++; sellPlusProfit+=sellProfit; } else { sellL++; sellMinusProfit+=sellProfit; } } } } } //+------------------------------------------------------------------+ bool doUpdateStops(bool forBuys,double forSells,double myStopLoss,double myLockProfit,double myTakeProfit) { int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectAnyPosition(cnt)) { if(isBuy && forBuys) { if((myLockProfit>0) && (buyProfit>myLockProfit)) { if(!UpdateStopLossTakeProfit(myLockProfit,myTakeProfit)) return(false); } else if(!UpdateStopLossTakeProfit(myStopLoss,myTakeProfit)) return(false); } else if(isSell && forSells) { if((myLockProfit>0) && (sellProfit>myLockProfit)) { if(!UpdateStopLossTakeProfit(myLockProfit,myTakeProfit)) return(false); } else if(!UpdateStopLossTakeProfit(myStopLoss,myTakeProfit)) return(false); } } } return(true); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ int countBuys(double &bestPrice,double &worstPrice,double &currExp) { currentBuyPrice=0; currentSellPrice=0; if(MA_Symbol!="") { currentBuyPrice=SymbolInfoDouble(MA_Symbol,SYMBOL_ASK); currentSellPrice=SymbolInfoDouble(MA_Symbol,SYMBOL_BID); } midBuyPrice=0; buyVolume=0; bestPrice=0; worstPrice=0; currExp=0; int res=0; int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectBuyPosition(cnt,true)) { if(isBuy) { res++; currExp=currExp+currVolume; if(bestPrice==0) bestPrice=buyOpen; else if(buyOpenworstPrice) worstPrice=buyStop; midBuyPrice=midBuyPrice+buyZero*currVolume; buyVolume=buyVolume+currVolume; } else if(isSell) currExp=currExp-currVolume; } } worstBuyPrice=worstPrice; if(buyVolume>0) midBuyPrice=midBuyPrice/buyVolume; return(res); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ bool haveSells() { int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectSellPosition(cnt,false)) return(true); } return(false); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ bool haveBuys() { int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectBuyPosition(cnt,false)) return(true); } return(false); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ int countSells(double &bestPrice,double &worstPrice,double &currExp) { currentBuyPrice=0; currentSellPrice=0; if(MA_Symbol!="") { currentBuyPrice=SymbolInfoDouble(MA_Symbol,SYMBOL_ASK); currentSellPrice=SymbolInfoDouble(MA_Symbol,SYMBOL_BID); } midSellPrice=0; sellVolume=0; bestPrice=0; worstPrice=0; currExp=0; int res=0; int cnt=Count_Positions(); while(cnt>0) { cnt--; if(selectSellPosition(cnt,true)) { if(isSell) { res++; currExp=currExp+currVolume; if(bestPrice==0) bestPrice=sellOpen; else if(sellOpen>bestPrice) bestPrice=sellOpen; if(worstPrice==0) worstPrice=sellStop; else if(sellStop0) midSellPrice=midSellPrice/sellVolume; return(res); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ void countHedge(double &volBuy,double &volSell) { volBuy=0; volSell=0; double myVol=0; int cnt=Count_Positions(); while(cnt>0) { cnt--; if(Select_Position(cnt)) { myVol=PositionGetDouble(POSITION_VOLUME); if(isBuy) volBuy=volBuy+myVol; else if(isSell) volSell=volSell+myVol; } } } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ void doUpdateChart() { double com=(minTradeVol>0?MathCeil(100.0*MA_Commission*(buyVolume+sellVolume)/minTradeVol/2.0)/100.0:0); double accequ=AccountInfoDouble(ACCOUNT_EQUITY)-com; double accbal=AccountInfoDouble(ACCOUNT_BALANCE); double freemar=AccountInfoDouble(ACCOUNT_MARGIN_FREE),accmar=freemar; double usedmar=AccountInfoDouble(ACCOUNT_MARGIN); if(AccountInfoInteger(ACCOUNT_MARGIN_SO_MODE)==ACCOUNT_STOPOUT_MODE_MONEY) accmar+=AccountInfoDouble(ACCOUNT_MARGIN_SO_SO); else accmar+=usedmar*(100-AccountInfoDouble(ACCOUNT_MARGIN_SO_SO))/100; accmar-=accbal*xMarginStop/100.0; freemar-=accbal*xMarginStop/100.0; ObjectSetString(0,"Account_Balance",OBJPROP_TEXT,DoubleToString(accbal,2)); ObjectSetString(0,"Account_Equity",OBJPROP_TEXT,DoubleToString(accequ,2)); ObjectSetString(0,"Account_Margin",OBJPROP_TEXT,DoubleToString(accmar,2)); ObjectSetString(0,"Account_Free",OBJPROP_TEXT,DoubleToString(freemar,2)); string str=""; //--- BUY if(buyL+buyP>0) { str="BUY"; if(buyP>0) str+=" +"+IntegerToString(buyP); if(buyL>0) str+=" -"+IntegerToString(buyL); ObjectSetString(0,"Btn_Buy",OBJPROP_TEXT,str); ObjectSetInteger(0,"Btn_Buy",OBJPROP_BORDER_COLOR,clrNONE); ObjectSetInteger(0,"Btn_Buy",OBJPROP_BGCOLOR,C'0,100,50'); if((currentBuyPrice>0) && (bestBuyPrice>0) && (currentBuyPrice0) { str="SELL"; if(sellP>0) str+=" +"+IntegerToString(sellP); if(sellL>0) str+=" -"+IntegerToString(sellL); ObjectSetString(0,"Btn_Sell",OBJPROP_TEXT,str); ObjectSetInteger(0,"Btn_Sell",OBJPROP_BORDER_COLOR,clrNONE); ObjectSetInteger(0,"Btn_Sell",OBJPROP_BGCOLOR,C'100,0,50'); if((currentSellPrice>0) && (bestSellPrice>0) && (currentSellPrice>bestSellPrice)) ObjectSetInteger(0,"Btn_Sell",OBJPROP_COLOR,C'255,255,0'); else ObjectSetInteger(0,"Btn_Sell",OBJPROP_COLOR,C'255,255,255'); ObjectSetInteger(0,"Btn_Sell",OBJPROP_HIDDEN,false); } else { ObjectSetInteger(0,"Btn_Sell",OBJPROP_HIDDEN,false); ObjectSetString(0,"Btn_Sell",OBJPROP_TEXT,"SELL"); ObjectSetInteger(0,"Btn_Sell",OBJPROP_BORDER_COLOR,clrBlack); ObjectSetInteger(0,"Btn_Sell",OBJPROP_BGCOLOR,C'50,0,0'); ObjectSetInteger(0,"Btn_Sell",OBJPROP_COLOR,C'150,150,150'); } //--- BUY Total if(buyP+buyL>0) { str=DoubleToString(buyOpenProfit,2)+" "+IntegerToString(buyL+buyP); ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_HIDDEN,false); ObjectSetString(0,"Btn_BuyTotal",OBJPROP_TEXT,str); if(buyOpenProfit>0) { ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_BGCOLOR,C'0,100,0'); ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_COLOR,C'200,200,200'); } else if(buyOpenProfit<0) { ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_BGCOLOR,C'100,0,0'); ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_COLOR,C'200,200,0'); } else { ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_BGCOLOR,C'64,64,64'); ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_COLOR,C'0,0,0'); } } else { ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_HIDDEN,true); ObjectSetString(0,"Btn_BuyTotal",OBJPROP_TEXT,""); ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_BGCOLOR,clrBlack); ObjectSetInteger(0,"Btn_BuyTotal",OBJPROP_COLOR,clrBlack); } //--- SELL Total if(sellP+sellL>0) { str=DoubleToString(sellOpenProfit,2)+" "+IntegerToString(sellL+sellP); ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_HIDDEN,false); ObjectSetString(0,"Btn_SellTotal",OBJPROP_TEXT,str); if(sellOpenProfit>0) { ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_BGCOLOR,C'0,100,0'); ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_COLOR,C'200,200,200'); } else if(sellOpenProfit<0) { ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_BGCOLOR,C'100,0,0'); ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_COLOR,C'200,200,0'); } else { ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_BGCOLOR,C'64,64,64'); ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_COLOR,C'0,0,0'); } } else { ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_HIDDEN,true); ObjectSetString(0,"Btn_SellTotal",OBJPROP_TEXT,""); ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_BGCOLOR,clrBlack); ObjectSetInteger(0,"Btn_SellTotal",OBJPROP_COLOR,clrBlack); } //--- TOTAL if((buyL+buyP>0) && (sellL+sellP>0)) { str=DoubleToString(buyOpenProfit+sellOpenProfit,2)+" "+IntegerToString(buyL+buyP+sellL+sellP); ObjectSetInteger(0,"Btn_Total",OBJPROP_HIDDEN,false); ObjectSetString(0,"Btn_Total",OBJPROP_TEXT,str); if(buyOpenProfit+sellOpenProfit>0) { ObjectSetInteger(0,"Btn_Total",OBJPROP_BGCOLOR,C'0,150,0'); ObjectSetInteger(0,"Btn_Total",OBJPROP_COLOR,C'255,255,255'); } else if(buyOpenProfit+sellOpenProfit<0) { ObjectSetInteger(0,"Btn_Total",OBJPROP_BGCOLOR,C'150,0,0'); ObjectSetInteger(0,"Btn_Total",OBJPROP_COLOR,C'255,255,0'); } else { ObjectSetInteger(0,"Btn_Total",OBJPROP_BGCOLOR,C'128,128,128'); ObjectSetInteger(0,"Btn_Total",OBJPROP_COLOR,C'0,0,0'); } } else { ObjectSetInteger(0,"Btn_Total",OBJPROP_HIDDEN,true); ObjectSetString(0,"Btn_Total",OBJPROP_TEXT,""); ObjectSetInteger(0,"Btn_Total",OBJPROP_BGCOLOR,clrBlack); ObjectSetInteger(0,"Btn_Total",OBJPROP_COLOR,clrBlack); } //--- PROFIT if(buyP+sellP>0) { str=DoubleToString(buyPlusProfit+sellPlusProfit,2)+" "+IntegerToString(buyP+sellP); ObjectSetInteger(0,"Btn_Profit",OBJPROP_HIDDEN,false); ObjectSetString(0,"Btn_Profit",OBJPROP_TEXT,str); if(buyPlusProfit+sellPlusProfit>0) { ObjectSetInteger(0,"Btn_Profit",OBJPROP_BGCOLOR,C'0,150,0'); ObjectSetInteger(0,"Btn_Profit",OBJPROP_COLOR,C'255,255,255'); } else { ObjectSetInteger(0,"Btn_Profit",OBJPROP_BGCOLOR,C'128,128,128'); ObjectSetInteger(0,"Btn_Profit",OBJPROP_COLOR,C'0,0,0'); } } else { ObjectSetInteger(0,"Btn_Profit",OBJPROP_HIDDEN,true); ObjectSetString(0,"Btn_Profit",OBJPROP_TEXT,""); ObjectSetInteger(0,"Btn_Profit",OBJPROP_BGCOLOR,clrBlack); ObjectSetInteger(0,"Btn_Profit",OBJPROP_COLOR,clrBlack); } //--- LOSS if(buyL+sellL>0) { str=DoubleToString(buyMinusProfit+sellMinusProfit,2)+" "+IntegerToString(buyL+sellL); ObjectSetInteger(0,"Btn_Loss",OBJPROP_HIDDEN,false); ObjectSetString(0,"Btn_Loss",OBJPROP_TEXT,str); if(buyMinusProfit+sellMinusProfit<0) { ObjectSetInteger(0,"Btn_Loss",OBJPROP_BGCOLOR,C'150,0,0'); ObjectSetInteger(0,"Btn_Loss",OBJPROP_COLOR,C'255,255,0'); } else { ObjectSetInteger(0,"Btn_Loss",OBJPROP_BGCOLOR,C'128,128,128'); ObjectSetInteger(0,"Btn_Loss",OBJPROP_COLOR,C'0,0,0'); } } else { ObjectSetInteger(0,"Btn_Loss",OBJPROP_HIDDEN,true); ObjectSetString(0,"Btn_Loss",OBJPROP_TEXT,""); ObjectSetInteger(0,"Btn_Loss",OBJPROP_BGCOLOR,clrBlack); ObjectSetInteger(0,"Btn_Loss",OBJPROP_COLOR,clrBlack); } //--- BEST if((buyL+buyP+sellL+sellP>1) || (bestProfit>0)) { str=DoubleToString(bestProfit,2)+" "+bestType; ObjectSetInteger(0,"Btn_Best",OBJPROP_HIDDEN,false); ObjectSetString(0,"Btn_Best",OBJPROP_TEXT,str); if(bestProfit>0) { ObjectSetInteger(0,"Btn_Best",OBJPROP_BGCOLOR,C'0,150,0'); ObjectSetInteger(0,"Btn_Best",OBJPROP_COLOR,C'255,255,255'); } else if(bestProfit<0) { ObjectSetInteger(0,"Btn_Best",OBJPROP_BGCOLOR,C'150,0,0'); ObjectSetInteger(0,"Btn_Best",OBJPROP_COLOR,C'255,255,0'); } else { ObjectSetInteger(0,"Btn_Best",OBJPROP_BGCOLOR,C'128,128,128'); ObjectSetInteger(0,"Btn_Best",OBJPROP_COLOR,C'0,0,0'); } } else { ObjectSetInteger(0,"Btn_Best",OBJPROP_HIDDEN,true); ObjectSetString(0,"Btn_Best",OBJPROP_TEXT,""); ObjectSetInteger(0,"Btn_Best",OBJPROP_BGCOLOR,clrBlack); ObjectSetInteger(0,"Btn_Best",OBJPROP_COLOR,clrBlack); } } //+------------------------------------------------------------------+ void HighLowX(const double&open[], const datetime&arrayT[], int fromIndex,int toIndex, double &h1,double &h1_2, double &h2,double &h2_3, double &h3,double &h3_4, double &h4,double &h4_5, double &h5, double &l1,double &l1_2, double &l2,double &l2_3, double &l3,double &l3_4, double &l4,double &l4_5, double &l5, double &c1,double &c1_2, double &c2,double &c2_3, double &c3,double &c3_4, double &c4,double &c4_5, double &c5) { int z=0; if(fromIndex<0) z=-fromIndex; int i=fromIndex; if(i<1) i=1; datetime fromTime=arrayT[i],toTime; double hres=MathMax(open[i],open[i-1]),lres=MathMin(open[i],open[i-1]); double vx=1,h=hres,l=lres,c=(open[i]+open[i-1]+open[i-1])/3.0; if(z>0) { if(lres>open[0]) lres=open[0]; if(hres0; z--) { vx++; h+=hres; l+=lres; c+=open[0]; } } i++; toTime=fromTime-ExtRange1*perSeconds; fixTime(toTime); for(; iopen[i]) lres=open[i]; if(hresopen[i]) lres=open[i]; if(hresopen[i]) lres=open[i]; if(hresopen[i]) lres=open[i]; if(hresopen[i]) lres=open[i]; if(hresopen[i]) lres=open[i]; if(hresopen[i]) lres=open[i]; if(hresopen[i]) lres=open[i]; if(hresopen[i]) lres=open[i]; if(hres5)) t-=48*60*60; } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ bool bSwap(double &a,double &b) { double t=a; a=b; b=t; return(true); } //+------------------------------------------------------------------+ void bSort9(double &x1,double &x2,double &x3, double &x4,double &x5,double &x6, double &x7,double &x8,double &x9) { bool upd; do { upd=false; if(x1>x2) upd=bSwap(x1,x2); else if(x2>x3) upd=bSwap(x2,x3); else if(x3>x4) upd=bSwap(x3,x4); else if(x4>x5) upd=bSwap(x4,x5); else if(x5>x6) upd=bSwap(x5,x6); else if(x6>x7) upd=bSwap(x6,x7); else if(x7>x8) upd=bSwap(x7,x8); else if(x8>x9) upd=bSwap(x8,x9); } while(upd); } //+------------------------------------------------------------------+ void bSort10(double &x1,double &x2,double &x3,double &x4,double &x5, double &x6,double &x7,double &x8,double &x9,double &x10) { bool upd; do { upd=false; if(x1>x2) upd=bSwap(x1,x2); else if(x2>x3) upd=bSwap(x2,x3); else if(x3>x4) upd=bSwap(x3,x4); else if(x4>x5) upd=bSwap(x4,x5); else if(x5>x6) upd=bSwap(x5,x6); else if(x6>x7) upd=bSwap(x6,x7); else if(x7>x8) upd=bSwap(x7,x8); else if(x8>x9) upd=bSwap(x8,x9); else if(x9>x10) upd=bSwap(x9,x10); } while(upd); } //+------------------------------------------------------------------+ void bSort18(double &x1,double &x2,double &x3, double &x4,double &x5,double &x6, double &x7,double &x8,double &x9, double &x10,double &x11,double &x12, double &x13,double &x14,double &x15, double &x16,double &x17,double &x18) { bool upd; do { upd=false; if(x1>x2) upd=bSwap(x1,x2); else if(x2>x3) upd=bSwap(x2,x3); else if(x3>x4) upd=bSwap(x3,x4); else if(x4>x5) upd=bSwap(x4,x5); else if(x5>x6) upd=bSwap(x5,x6); else if(x6>x7) upd=bSwap(x6,x7); else if(x7>x8) upd=bSwap(x7,x8); else if(x8>x9) upd=bSwap(x8,x9); else if(x9>x10) upd=bSwap(x9,x10); else if(x10>x11) upd=bSwap(x10,x11); else if(x11>x12) upd=bSwap(x11,x12); else if(x12>x13) upd=bSwap(x12,x13); else if(x13>x14) upd=bSwap(x13,x14); else if(x14>x15) upd=bSwap(x14,x15); else if(x15>x16) upd=bSwap(x15,x16); else if(x16>x17) upd=bSwap(x16,x17); else if(x17>x18) upd=bSwap(x17,x18); } while(upd); } //+------------------------------------------------------------------+ void bSort8(double &x1,double &x2,double &x3, double &x4,double &x5,double &x6, double &x7,double &x8) { bool upd; do { upd=false; if(x1>x2) upd=bSwap(x1,x2); else if(x2>x3) upd=bSwap(x2,x3); else if(x3>x4) upd=bSwap(x3,x4); else if(x4>x5) upd=bSwap(x4,x5); else if(x5>x6) upd=bSwap(x5,x6); else if(x6>x7) upd=bSwap(x6,x7); else if(x7>x8) upd=bSwap(x7,x8); } while(upd); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ void bSort6(double &x1,double &x2,double &x3, double &x4,double &x5,double &x6) { bool upd; do { upd=false; if(x1>x2) upd=bSwap(x1,x2); else if(x2>x3) upd=bSwap(x2,x3); else if(x3>x4) upd=bSwap(x3,x4); else if(x4>x5) upd=bSwap(x4,x5); else if(x5>x6) upd=bSwap(x5,x6); } while(upd); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ void bSort5(double &x1,double &x2,double &x3, double &x4,double &x5) { bool upd; do { upd=false; if(x1>x2) upd=bSwap(x1,x2); else if(x2>x3) upd=bSwap(x2,x3); else if(x3>x4) upd=bSwap(x3,x4); else if(x4>x5) upd=bSwap(x4,x5); } while(upd); } //+------------------------------------------------------------------+ //| | //+------------------------------------------------------------------+ void bSort4(double &x1,double &x2,double &x3,double &x4) { bool upd; do { upd=false; if(x1>x2) upd=bSwap(x1,x2); else if(x2>x3) upd=bSwap(x2,x3); else if(x3>x4) upd=bSwap(x3,x4); } while(upd); } //+------------------------------------------------------------------+