Пт. Мар 29th, 2024

Функция безубытка mql4

Внешние переменные:

input int LevelProfit = 60;  //Уровень профита в пунктах, которого должна достигнуть позиция для того, чтобы её стоп был перенесён на уровень безубытка.
input int LevelWLoss  =  30;  //  Уровень безубытка в пунктах, на который будет перенесён стоп позиции после того, как её профит достигнет уровня LevelProfit в пунктах.

Сама функция безубытка:

void MovingInWL(string sy="", int op=-1, int mn=-1) {
  double po, pp;
  int    i, k=OrdersTotal();

  for (i=0; i<k; i++) {
    if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES)) {
      po=MarketInfo(OrderSymbol(), MODE_POINT);
      if (OrderType()==OP_BUY && OrderMagicNumber() == Magic3) {
        if (OrderStopLoss()-OrderOpenPrice()<LevelWLoss*po) {
          pp=MarketInfo(OrderSymbol(), MODE_BID);
          if (pp-OrderOpenPrice()>LevelProfit*po) {
            ModifyOrder(OrderOpenPrice(), OrderOpenPrice()+LevelWLoss*po, OrderTakeProfit(),0);
          }
        }
      }
      if (OrderType()==OP_SELL && OrderMagicNumber() == Magic3) {
        if (OrderStopLoss()==0 || OrderOpenPrice()-OrderStopLoss()<LevelWLoss*po) {
          pp=MarketInfo(OrderSymbol(), MODE_ASK);
          if (OrderOpenPrice()-pp>LevelProfit*po) {
            ModifyOrder(OrderOpenPrice(), OrderOpenPrice()-LevelWLoss*po, OrderTakeProfit(),0);
          }
        }
      }
    }
  }
}

Входные параметры функции:

MovingInWL(string sy="", int op=-1, int mn=-1)

Sy -символ;
op — тип ордера, к которым применять функцию (OP_BUY или OP_SELL). Если -1 — ко всем типам ордеров.
mn — магик ордеров, к которым будет применена функция безубытка. Если -1 — применяется ко всем ордерам без исключения, хоть с магиками, хоть без них.

Данная функция безубытка использует функцию гарантированной модификации ордера:

void ModifyOrder(double pp,double sl,double tp,datetime ex)
  {
   bool   fm;
   color  cl=IIFc(OrderType()==OP_BUY
                  || OrderType()==OP_BUYLIMIT
                  || OrderType()==OP_BUYSTOP, clModifyBuy, clModifySell);
   double op,pa,pb,os,ot;
   int    dg=MarketInfo(OrderSymbol(),MODE_DIGITS),er,it;

   if(pp<=0) pp=OrderOpenPrice();
   if(sl<0 ) sl=OrderStopLoss();
   if(tp<0 ) tp=OrderTakeProfit();

   pp=NormalizeDouble(pp, dg);
   sl=NormalizeDouble(sl, dg);
   tp=NormalizeDouble(tp, dg);
   op=NormalizeDouble(OrderOpenPrice() , dg);
   os=NormalizeDouble(OrderStopLoss()  , dg);
   ot=NormalizeDouble(OrderTakeProfit(), dg);

   if(pp!=op || sl!=os || tp!=ot)
     {
      for(it=1; it<=NumberOfTry; it++)
        {
         if(!IsTesting() && (!IsExpertEnabled() || IsStopped())) break;
         while(!IsTradeAllowed()) Sleep(5000);
         RefreshRates();
         fm=OrderModify(OrderTicket(),pp,sl,tp,ex,cl);
         if(fm)
           {
            Print("Modify OK."); break;
              } else {
            er=GetLastError();
            //if(UseSound) PlaySound(SoundError);
            pa=MarketInfo(OrderSymbol(), MODE_ASK);
            pb=MarketInfo(OrderSymbol(), MODE_BID);
            Print("ERROR(",er,") Modify: ",ErrorDescription(er),", attempt: ",it);
            Print("Price Ask=",pa,"  Price Bid=",pb,"  Symbol= ",OrderSymbol(),
                  "  op="+GetNameOP(OrderType()),"  pp=",pp,"  sl=",sl,"  tp=",tp);
            Sleep(1000*10);
           }
        }
     }
  }

Функцию модификации можно использовать и отдельно для установки стопов и тейков в советниках.

Здесь:

pp — Цена установки ордера;

sl — уровень (цена) стоп-лосса;

tp — уровень (цена ) тейк-профита;

ex — дата экспирации (0 — значит не использовать).

Перед использованием функции модификации ордера, этот самый модифицируемый ордер нужно выбрать с помощью OrderSelect.

Приятных вам безубытков и модификаций!


Поделись с друзьями:

от drivermql

Добавить комментарий

Ваш адрес email не будет опубликован.

Этот сайт использует Akismet для борьбы со спамом. Узнайте, как обрабатываются ваши данные комментариев.