Download MetaTrader 5

Lotsize calculation error

To add comments, please log in or register
Added support for the Spanish language. Come and check it out!
Thierry F.
127
Thierry F. 2016.03.14 22:19 

Dear coders,

I'm trying to improve my Martingale EA, by adding a new SL method. Namely the x candle low for long trades, and for short trades the x candle high.

 

If the previous trade was a winner, the EA will calculate the lotsize with this formula:

 lotsize = ((Risk_per_Trade/100.0) * money ) / (LongSL*pips);

If the previous trade was a loser:

         double vorigelot=lastlot();
         double vorigeSL=lastSL();
         double lotXslXmartin = vorigelot*vorigeSL*MartingaleAmount;
         lotsize = lotXslXmartin/LongSL;
//+------------------------------------------------------------------+
//| last lot                                                         |
//+------------------------------------------------------------------+ 
double lastlot()                        // we will find last lot size 
{                                       // order with this function
  double lot=0;                         // lot size
  int i;                                // pos of our order 
  for(i=0; i<OrdersHistoryTotal(); i++) // looping to check all of our
   {                                     // order history from pos 0 until
                                        // last pos
       OrderSelect(i,SELECT_BY_POS,MODE_HISTORY); // is it right our order?
       if(OrderMagicNumber()!=magic)   
       continue;                        // or the magic numb of order 
       if(OrderProfit()<0)
       lot=OrderLots();
       }
  return(lot);                          // last lot size returned
}
//+------------------------------------------------------------------+
//| last SL                                                         |
//+------------------------------------------------------------------+ 
double lastSL()                        // we will find last lot size 
{                                       // order with this function
  double SL=0;
  double SLpips=0;                         // lot size
  int i;                                // pos of our order 
  for(i=0; i<OrdersHistoryTotal(); i++) // looping to check all of our
   {                                     // order history from pos 0 until
                                        // last pos
       OrderSelect(i,SELECT_BY_POS,MODE_HISTORY); // is it right our order?
       if(OrderMagicNumber()!=magic)   
       continue;                        // or the magic numb of order 
       if(OrderProfit()<0){
       
          if(OrderType()==OP_BUY){
          SL=OrderOpenPrice()-OrderStopLoss();
          //SLpips=SL/pips;
          }
          
          if(OrderType()==OP_SELL){   
          SL=OrderStopLoss()-OrderOpenPrice(); 
          //SLpips=SL/pips;  
          }
       }
   }
  return(SL);                          // last lot size returned
}

 When I backtest the EA I get error 4051 , invalid lots amount for OrderSend function.
I've already tried many things, but I couldn't find the solution. 


 This is the whole function for the lotsize calculation and the order placement.

void EnterTrade(int type){

   int err=0;
   double sl=0, tp=0,
          lotsize =0,
          LongSL=0, LongTP=0, ShortSL=0, ShortTP=0,
          price, money;
          
   bool lastprofit=false;
   
   if(OrderSelect(lastTradeTicket(),MODE_HISTORY)){
      if(OrderProfit()>0){
         lastprofit=true;
         }
   }
      
      //If to open a long trade.
   if(type == OP_BUY){
      
      price = Ask;   
       
      LongSL = NormalizeDouble(Ask - Low[iLowest(NULL,PERIOD_H4,MODE_LOW,candlesback,1)],Digits);
      Print("Calculated long SL "+LongSL);
      if(LongSL > MaxStoploss) LongSL=MaxStoploss;
      if(LongSL < MinStopLoss) LongSL=MinStopLoss;
      LongTP = LongSL*ratioSLTP;
      
      
      money = AccountInfoDouble(ACCOUNT_EQUITY);
      if(lastprofit==true){
         lotsize = ((Risk_per_Trade/100.0) * money ) / (LongSL*pips);
         Print("Llotsize last win true"+DoubleToStr(lotsize));
         }
      if(lastprofit==false){
         double vorigelot=lastlot();
         double vorigeSL=lastSL();
         double lotXslXmartin = vorigelot*vorigeSL*MartingaleAmount;
         lotsize = lotXslXmartin/LongSL;
         Print("Llotsize last win false"+DoubleToStr(lotsize,2));
         }
      
   }
      //If to open a short trade.
   if(type == OP_SELL){
      
      price = Bid;
      ShortSL = NormalizeDouble(High[iHighest(NULL,PERIOD_H4,MODE_HIGH,candlesback,1)]-Bid,Digits);
      Print("Calculated short SL"+ShortSL);
      if(ShortSL > MaxStoploss) ShortSL=MaxStoploss;
      if(ShortSL < MinStopLoss) ShortSL=MinStopLoss;
      ShortTP = ShortSL*ratioSLTP;
      
      money = AccountInfoDouble(ACCOUNT_EQUITY);
      if(lastprofit==true){
         lotsize = ((Risk_per_Trade/100.0) * money ) / (ShortSL*pips);   //     double lots = (Risk_per_Trade * money /100.0) / (SL_pips * pip_value);
         Print("Slotsize last win true"+DoubleToStr(lotsize));
         }
      if(lastprofit==false){
         double vorigelot=lastlot();
         double vorigeSL=lastSL();
         double lotXslXmartin = vorigelot*vorigeSL*MartingaleAmount;
         lotsize = lotXslXmartin/ShortSL;
         Print("Slotsize last win false"+DoubleToStr(lotsize,2));
         }      


   }
   
   int ticket =  OrderSend(Symbol(),type,lotsize,price,30,0,0,"Martingale trade",magic,0,Magenta); 
   if(ticket>0){
      if(OrderSelect(ticket,SELECT_BY_TICKET)){
         sl = OrderOpenPrice()+(ShortSL);
         tp = OrderOpenPrice()-(ShortTP);
         if(OrderType()==OP_BUY){
            sl = OrderOpenPrice()-(LongSL);
            tp = OrderOpenPrice()+(LongTP);
         }
         if(!OrderModify(ticket,price,sl,tp,0,Magenta)) {
            err = GetLastError();
            Print("Encountered an error during modification!"+(string)err+" "+ErrorDescription(err)  );
         }
      }
      else{//in case it fails to select the order for some reason 
         Print("Failed to Select Order ",ticket);
         err = GetLastError();
         Print("Encountered an error while seleting order "+(string)ticket+" error number "+(string)err+" "+ErrorDescription(err)  );
      }
   }
   else{//in case it fails to place the order and send us back a ticket number.
      err = GetLastError();
      Print("Encountered an error during order placement!"+(string)err+" "+ErrorDescription(err)  );
      if(err==ERR_TRADE_NOT_ALLOWED)MessageBox("You can not place a trade because \"Allow Live Trading\" is not checked in your options. Please check the \"Allow Live Trading\" Box!","Check Your Settings!");
   }
}
//+------------------------------------------------------------------+
//| last lot                                                         |
//+------------------------------------------------------------------+ 
double lastlot()                        // we will find last lot size 
{                                       // order with this function
  double lot=0;                         // lot size
  int i;                                // pos of our order 
  for(i=0; i<OrdersHistoryTotal(); i++) // looping to check all of our
   {                                     // order history from pos 0 until
                                        // last pos
       OrderSelect(i,SELECT_BY_POS,MODE_HISTORY); // is it right our order?
       if(OrderMagicNumber()!=magic)   
       continue;                        // or the magic numb of order 
       if(OrderProfit()<0)
       lot=OrderLots();
       }
  return(lot);                          // last lot size returned
}
//+------------------------------------------------------------------+
//| last SL                                                         |
//+------------------------------------------------------------------+ 
double lastSL()                        // we will find last lot size 
{                                       // order with this function
  double SL=0;
  double SLpips=0;                         // lot size
  int i;                                // pos of our order 
  for(i=0; i<OrdersHistoryTotal(); i++) // looping to check all of our
   {                                     // order history from pos 0 until
                                        // last pos
       OrderSelect(i,SELECT_BY_POS,MODE_HISTORY); // is it right our order?
       if(OrderMagicNumber()!=magic)   
       continue;                        // or the magic numb of order 
       if(OrderProfit()<0){
       
          if(OrderType()==OP_BUY){
          SL=OrderOpenPrice()-OrderStopLoss();
          //SLpips=SL/pips;
          }
          
          if(OrderType()==OP_SELL){   
          SL=OrderStopLoss()-OrderOpenPrice(); 
          //SLpips=SL/pips;  
          }
       }
   }
  return(SL);                          // last lot size returned
}

 

 I really hope that someone could explain why my code isn't working.

 
Thanks in advance,

 

Thierry 

To add comments, please log in or register