В роботе АСК и БИД берутся не те - страница 3

 

Огромное спасибо.

Теперь кажется работает т.к. скорость срабатывания увеличилась в разы. Хотя иногда пропускает. И бывает что в терминале профит на позицию пишется отрицательный а робот закрывает позу в плюсе. Скорее всего это глюк брокера. Если нет других предложений считаю тему закрытой.

Исправленный код:

//+------------------------------------------------------------------+
//|                                                    LastPrice.mq5 |
//|                        Copyright 2015, MetaQuotes Software Corp. |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2015, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"
input long Interval=100;  //Мин. отклонение цены сделки
input long Lots=1;   //Лот
input long SlPips=100;   //Stop Loss
input ENUM_ORDER_TYPE_FILLING Filling=ORDER_FILLING_RETURN;  //Режим заполнения ордера
double tradePrice= 0;
double LastPrice = 0;
double interval;
double pips;
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
   interval=PointsToPrice(Interval); //Из пунктов в цену символa
   pips=PointsToPrice(SlPips);
   if(!MarketBookAdd(_Symbol))
     {
      MessageBox("Не добавлен стакан по символу "+_Symbol);
      return( INIT_FAILED );
     }
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
   MarketBookRelease(_Symbol);
  }
//+------------------------------------------------------------------+
//| Expert Points to price function                                  |
//+------------------------------------------------------------------+
double PointsToPrice(const long a_points)
  {
   double step_price=SymbolInfoDouble(_Symbol,SYMBOL_TRADE_TICK_SIZE);
   double a_price=(double(a_points)*_Point)/step_price;

   if(a_points<0)
     {
      a_price=MathFloor(a_price)*step_price;
     }
   else
     {
      a_price=MathCeil(a_price)*step_price;
     }

   return( NormalizeDouble( a_price, _Digits ) );
  }
//+------------------------------------------------------------------+
//| Get Stakan values function                                       |
//+------------------------------------------------------------------+ 
bool GetStakanValues(const string aSymbol,double &ask,double &bid)
  {
   MqlBookInfo book_price[];
   bid = 0;
   ask = DBL_MAX;

//--- Get stakan
   if(MarketBookGet(aSymbol,book_price))
     {
      int size=ArraySize(book_price);
      //---    
      if(size>0)
        {
         for(int i=0; i<size; i++)
           {
            if(book_price[i].type==BOOK_TYPE_SELL)
              {
               if(book_price[i].price<ask)
                 {
                  ask=book_price[i].price;
                 }
              }
            else
            if(book_price[i].type==BOOK_TYPE_BUY)
              {
               bid=book_price[i].price;
               return( true );
              }
           }
        }
     }
//---
   if(ask==DBL_MAX) ask=0;
   return( false);
  }
//+------------------------------------------------------------------+
//| Set order function                                               |
//+------------------------------------------------------------------+  
bool SetOrder(const double price,const bool buy_sell)
  {
   MqlTradeRequest request={0};
   MqlTradeResult result={0};

//--- Fill structure
   request.action=TRADE_ACTION_PENDING;         // setting a pending order
   request.magic = 68975;                      // ORDER_MAGIC
   request.symbol = _Symbol;                   // symbol
   request.volume = double( Lots );
//---   
   if(buy_sell)
     {
      request.type=ORDER_TYPE_BUY_LIMIT;              // order type
      request.sl=price-pips;
     }
   else
     {
      request.type=ORDER_TYPE_SELL_LIMIT;
      request.sl=price+pips;
     }
   request.price=price;                        // open price
   request.type_filling=Filling;
   request.deviation=0;
   request.type_time=ORDER_TIME_DAY;
   request.expiration=0;
//---
   if(OrderSend(request,result))
     {
      if(( result.retcode==TRADE_RETCODE_PLACED) && (result.order>0))
        {
         return( true );
        }
     }
   else
     {
      Print(" Order not set!");
     }
   return( false );
  }
//+------------------------------------------------------------------+
//| BookEvent function                                               |
//+------------------------------------------------------------------+
void OnBookEvent(const string &symbol)
  {
   if(symbol==_Symbol)
     {
      double ask,bid,last,price=0;
      //---            
      if(GetStakanValues(_Symbol,ask,bid)) //Берём здесь, потому что нужно как и для открытия позиции, так и для закрытия
        {
         last=SymbolInfoDouble(_Symbol,SYMBOL_LAST);
         //---      
         if(PositionSelect(_Symbol))
           {
            if(ENUM_POSITION_TYPE(PositionGetInteger(POSITION_TYPE))==POSITION_TYPE_BUY)///BUY
              {
               if(((LastPrice<=bid || LastPrice<=ask) && (tradePrice<=bid)) || (tradePrice<bid))
                 {//--- Проверка закрытия, если да то
                  int i=PositionsTotal();//Wait openedPosition 
                  if(SetOrder(bid,false))
                    {
                     while(i==PositionsTotal())//Wait openedPosition
                       {
                       }
                     //---
                    }
                 }
              }
            else///SELL
              {
               if(((LastPrice>=ask || LastPrice>=bid) && (tradePrice>=ask)) || (tradePrice>ask))
                 {//---Проверка закрытия, если да то
                  int i=PositionsTotal();//Wait openedPosition 
                  if(SetOrder(ask,true))
                    {
                     while(i==PositionsTotal())//Wait openedPosition
                       {
                       }
                     //---
                    }
                 }
              }
           }
         else ///No Positin:
           {
            //Делаем проверки какой ордер установить (BUY or SELL ) и берём цену
            if(last>=ask+interval)///BUY
              {//Устанавливаем ордер 
               int i=PositionsTotal();//Wait openedPosition 
               if(SetOrder(ask,true)) // true ордер на покупку; false - ордер на продажу
                 {
                  /////Ордер установлен
                  while(i==PositionsTotal())//Wait openedPosition
                    {
                    }
                  LastPrice=last;
                  tradePrice=ask;
                 }
              }
            //Делаем проверки какой ордер установить (BUY or SELL ) и берём цену
            if(last<=bid-interval)///SELL
              {//Устанавливаем ордер 
               int i=PositionsTotal();//Wait openedPosition 
               if(SetOrder(bid,false)) // true ордер на покупку; false - ордер на продажу
                 {
                  /////Ордер установлен
                  while(i==PositionsTotal())//Wait openedPosition
                    {
                    }
                  LastPrice=last;
                  tradePrice=bid;
                 }
              }
           }
        }
     }
  }

//+------------------------------------------------------------------+
Причина обращения: