Grid Semiautomat Panel

Author: Copyright © 2019-2021, Vladimir Karputov
Price Data Components
Series array that contains tick volumes of each bar
0 Views
0 Downloads
0 Favorites
Grid Semiautomat Panel
ÿþ//+------------------------------------------------------------------+

//|                                       Grid Semiautomat Panel.mq5 |

//|                         Copyright © 2019-2021, Vladimir Karputov |

//|                     https://www.mql5.com/ru/market/product/43516 |

//+------------------------------------------------------------------+

#property copyright "Copyright © 2019-2021, Vladimir Karputov"

#property link      "https://www.mql5.com/ru/market/product/43516"

#property version   "1.004"

//---

#include <Trade\PositionInfo.mqh>

#include <Trade\Trade.mqh>

#include <Trade\SymbolInfo.mqh>

#include <Trade\AccountInfo.mqh>

//---

#include <Controls\Dialog.mqh>

#include <Controls\Button.mqh>

#include <Controls\Label.mqh>

#include <Controls\EditKVN.mqh>

//+------------------------------------------------------------------+

//| defines                                                          |

//+------------------------------------------------------------------+

//--- indents and gaps

#define INDENT_LEFT                         (11)      // indent from left (with allowance for border width)

#define INDENT_TOP                          (11)      // indent from top (with allowance for border width)

#define CONTROLS_GAP_X                      (5)       // gap by X coordinate

#define CONTROLS_GAP_Y                      (5)       // gap by Y coordinate

//--- for buttons

#define BUTTON_WIDTH                        (175)     // size by X coordinate

#define BUTTON_HEIGHT                       (15)      // size by Y coordinate

//--- for the indication area

#define EDIT_WIDTH                          (115)      // size by X coordinate

#define EDIT_HEIGHT                         (15)      // size by Y coordinate

//--- for panel controls

#define WNDCLIENT_WIDTH                     (361)     // size by X coordinate

#define WNDCLIENT_HEIGHT                    (41)      // size by Y coordinate

//+------------------------------------------------------------------+

//| Class CControlsDialog                                            |

//| Usage: main dialog of the Controls application                   |

//+------------------------------------------------------------------+

class CControlsDialog : public CAppDialog

  {

private:

   //--- EA

   CPositionInfo     m_position;                   // object of CPositionInfo class

   CTrade            m_trade;                      // object of CTrade class

   CSymbolInfo       m_symbol;                     // object of CSymbolInfo class

   CAccountInfo      m_account;                    // object of CAccountInfo class

   //---

   double            m_step_buy;

   double            m_step_sell;



   double            m_adjusted_point;             // point value adjusted for 3 or 5 points



   bool              m_need_close_buys;            // need close all buy positions

   bool              m_need_close_sells;           // need close all sell positions

   bool              m_need_close_all;             // needclose all positions



   double            m_last_deal_in_buy;           //

   double            m_last_deal_in_sell;          //

   //--- Panel

   CWndClient        m_mony_wndclient;                // CWndClient object

   CLabel            m_mony_label_balance_equity;     // CLabel object

   CLabel            m_mony_label_margin_free_margin; // CLabel object



   CWndClient        m_manual_close_wndclient;        // CWndClient CPanel

   CButton           m_manual_close_button_buys;      // CButton object

   CButton           m_manual_close_button_sells;     // CButtonobject

   CButton           m_manual_close_button_all;       // CButton object



   CWndClient        m_auto_close_wndclient;          // CWndClient CPanel

   CEditKVN          m_auto_close_editkvn_buys;       // CEditKVN object

   CEditKVN          m_auto_close_editkvn_sells;      // CEditKVN object

   CEditKVN          m_auto_close_editkvn_all;        // CEditKVN object

   CButton           m_auto_close_button_buys;        // CButton object

   CButton           m_auto_close_button_sells;       // CButtonobject

   CButton           m_auto_close_button_all;         // CButton object



   CWndClient        m_grid_wndclient;                // CWndClient CPanel

   CLabel            m_grid_label_lot;                // CLabel object

   CLabel            m_grid_label_step;               // CLabel object

   CEditKVN          m_grid_editkvn_lot_buy;          // CEditKVN object

   CEditKVN          m_grid_editkvn_lot_sell;         // CEditKVN object

   CEditKVN          m_grid_editkvn_step_buy;         // CEditKVN object

   CEditKVN          m_grid_editkvn_step_sell;        // CEditKVN object

   CButton           m_grid_button_buy;               // CButtonobject

   CButton           m_grid_button_sell;              // CButton object



public:

                     CControlsDialog(void);

                    ~CControlsDialog(void);

   //--- create

   virtual bool      Create(const long chart,const string name,const int subwin,const int x1,const int y1,const int x2,const int y2);

   //--- panel initialization function

   int               OnInitPanel();

   //--- panel deinitialization function

   void              OnDeinitPanel(const int reason);

   //--- panel tick function

   void              OnTickPanel();

   //--- panel TradeTransaction function

   void              OnTradeTransactionPanel(const MqlTradeTransaction &trans,const MqlTradeRequest &request,const MqlTradeResult &result);



protected:

   //--- create dependent controls

   bool              CreateMoneyWndClient(void);

   bool              CreateMoneyLabels(void);

   bool              CreateManualCloseWndClient(void);

   bool              CreateManualCloseButtons(void);

   bool              CreateAutoCloseWndClient(void);

   bool              CreateAutoCloseEdits(void);

   bool              CreateAutoCloseButtons(void);

   bool              CreateGridWndClient(void);

   bool              CreateGridLabels(void);

   bool              CreateGridEdits(void);

   bool              CreateGridButtons(void);

   //--- handlers of the dependent controls events

   void              OnClickManualCloseButtonBuys(void);

   void              OnClickManualCloseButtonSells(void);

   void              OnClickManualCloseButtonAll(void);



   void              OnClickAutoCloseButtonBuys(void);

   void              OnClickAutoCloseButtonSells(void);

   void              OnClickAutoCloseButtonAll(void);



   void              OnClickGridButtonBuy(void);

   void              OnClickGridButtonSell(void);

   //--- refreshes the symbol quotes data

   bool              RefreshRates();

   //--- check the correctness of the position volume

   bool              CheckVolumeValue(double volume,string &error_description);

   //--- lot Check

   double            LotCheck(double lots,CSymbolInfo &symbol);

   //--- check Freeze and Stops levels

   bool              FreezeStopsLevels(double &level);

   //--- open position

   void              OpenPosition(const int index,const double level);

   //--- open Buy position

   void              OpenBuy(const int index);

   //--- open Sell position

   void              OpenSell(const int index);

   //--- print CTrade result

   void              PrintResultTrade(CTrade &trade,CSymbolInfo &symbol);

   //--- close positions

   void              ClosePositions(const ENUM_POSITION_TYPE pos_type,const double level);

   //--- calculate all positions

   void              CalculateAllPositions(int &count_buys,double &volume_buys,double &volume_biggest_buys,

                                           int &count_sells,double &volume_sells,double &volume_biggest_sells);

   //--- is position exists

   bool              IsPositionExists(void);

   //--- close all positions

   void              CloseAllPositions(const double level);

   //--- profit all positions

   void              ProfitAllPositions(double &profit_buys,double &profit_sells);

   //--- chart event handler

   virtual bool      OnEvent(const int id,const long &lparam,const double &dparam,const string &sparam);

   //--- refresh dependent controls

   void              RefreshLabelsMoney(void);

   //--- get state and value elements

   double            ValueAutoEditKVNBuys(void)             const { return(StringToDouble(m_auto_close_editkvn_buys.Text()));          }

   bool              PressedAutoCloseButtonBuys(void)       const { return(m_auto_close_button_buys.Pressed());                  }



   double            ValueAutoEditKVNSells(void)            const { return(StringToDouble(m_auto_close_editkvn_sells.Text()));         }

   bool              PressedAutoCloseButtonSells(void)      const { return(m_auto_close_button_sells.Pressed());                 }



   double            ValueAutoEditKVNAll(void)              const { return(StringToDouble(m_auto_close_editkvn_all.Text()));           }

   bool              PressedAutoCloseButtonAll(void)        const { return(m_auto_close_button_all.Pressed());                   }



   double            ValueGridEditKVNLotBuy(void)           const { return(StringToDouble(m_grid_editkvn_lot_buy.Text()));       }

   ushort            ValueGridEditKVNStepBuy(void)          const { return(ushort)(StringToInteger(m_grid_editkvn_step_buy.Text()));   }

   bool              PressedGridButtonBuy(void)             const { return(m_grid_button_buy.Pressed());                         }



   double            ValueGridEditKVNLotSell(void)          const { return(StringToDouble(m_grid_editkvn_lot_sell.Text()));      }

   ushort            ValueGridEditKVNStepSell(void)         const { return(ushort)(StringToInteger(m_grid_editkvn_step_sell.Text()));  }

   bool              PressedGridButtonSell(void)            const { return(m_grid_button_sell.Pressed());                        }

   //--- get state edits



  };

//+------------------------------------------------------------------+

//| Event Handling                                                   |

//+------------------------------------------------------------------+

EVENT_MAP_BEGIN(CControlsDialog)

ON_EVENT(ON_CLICK,m_manual_close_button_buys,OnClickManualCloseButtonBuys)

ON_EVENT(ON_CLICK,m_manual_close_button_sells,OnClickManualCloseButtonSells)

ON_EVENT(ON_CLICK,m_manual_close_button_all,OnClickManualCloseButtonAll)

ON_EVENT(ON_CLICK,m_auto_close_button_buys,OnClickAutoCloseButtonBuys)

ON_EVENT(ON_CLICK,m_auto_close_button_sells,OnClickAutoCloseButtonSells)

ON_EVENT(ON_CLICK,m_auto_close_button_all,OnClickAutoCloseButtonAll)

ON_EVENT(ON_CLICK,m_grid_button_buy,OnClickGridButtonBuy)

ON_EVENT(ON_CLICK,m_grid_button_sell,OnClickGridButtonSell)

EVENT_MAP_END(CAppDialog)

//+------------------------------------------------------------------+

//| Constructor                                                      |

//+------------------------------------------------------------------+

CControlsDialog::CControlsDialog(void):

   m_step_buy(0.0),

   m_step_sell(0.0),

   m_adjusted_point(0.0),

   m_need_close_buys(false),

   m_need_close_sells(false),

   m_need_close_all(false),

   m_last_deal_in_buy(0.0),

   m_last_deal_in_sell(0.0)

  {

  }

//+------------------------------------------------------------------+

//| Destructor                                                       |

//+------------------------------------------------------------------+

CControlsDialog::~CControlsDialog(void)

  {

  }

//+------------------------------------------------------------------+

//| Panel initialization function                                    |

//+------------------------------------------------------------------+

int CControlsDialog::OnInitPanel(void)

  {

//---

   if(!m_symbol.Name(Symbol())) // sets symbol name

     {

      Print(__FILE__," ",__FUNCTION__,", ERROR: CSymbolInfo.Name");

      return(INIT_FAILED);

     }

   RefreshRates();

//---

   m_trade.SetExpertMagicNumber(InpMagic);

   m_trade.SetMarginMode();

   m_trade.SetTypeFillingBySymbol(m_symbol.Name());

   m_trade.SetDeviationInPoints(InpDeviation);

//--- tuning for 3 or 5 digits

   int digits_adjust=1;

   if(m_symbol.Digits()==3 || m_symbol.Digits()==5)

      digits_adjust=10;

   m_adjusted_point=m_symbol.Point()*digits_adjust;

   m_step_buy              = 0.0;

   m_step_sell             = 0.0;

//---

   return(INIT_SUCCEEDED);

  }

//+------------------------------------------------------------------+

//| Panel deinitialization function                                  |

//+------------------------------------------------------------------+

void CControlsDialog::OnDeinitPanel(const int reason)

  {

//--- The first way to get a deinitialization reason code

   Print(__FUNCTION__," Deinitialization reason code = ",reason);

//--- The second way to get a deinitialization reason code

   Print(__FUNCTION__," _UninitReason = ",getUninitReasonText(_UninitReason));

//--- The third way to get a deinitialization reason code

   Print(__FUNCTION__," UninitializeReason() = ",getUninitReasonText(UninitializeReason()));

  }

//+------------------------------------------------------------------+

//| Panel tick function                                              |

//+------------------------------------------------------------------+

void CControlsDialog::OnTickPanel(void)

  {

//---

   RefreshLabelsMoney();

//---

   if(m_need_close_all)

     {

      if(IsPositionExists())

        {

         double level;

         if(FreezeStopsLevels(level))

           {

            CloseAllPositions(level);

            return;

           }

         else

            return;

        }

      else

         m_need_close_all=false;

     }

//---

   if(m_need_close_buys || m_need_close_sells)

     {

      int      count_buys           = 0;

      double   volume_buys          = 0.0;

      double   volume_biggest_buys  = 0.0;

      int      count_sells          = 0;

      double   volume_sells         = 0.0;

      double   volume_biggest_sells = 0.0;

      CalculateAllPositions(count_buys,volume_buys,volume_biggest_buys,

                            count_sells,volume_sells,volume_biggest_sells);

      //--- need close buys

      if(m_need_close_buys)

        {

         if(count_buys>0)

           {

            double level;

            if(FreezeStopsLevels(level))

              {

               ClosePositions(POSITION_TYPE_BUY,level);

               return;

              }

            else

               return;

           }

         else

            m_need_close_buys=false;

        }

      //--- need close sells

      if(m_need_close_sells)

        {

         if(count_sells>0)

           {

            double level;

            if(FreezeStopsLevels(level))

              {

               ClosePositions(POSITION_TYPE_SELL,level);

               return;

              }

            else

               return;

           }

         else

            m_need_close_sells=false;

        }

     }

//--- check auto close

   bool auto_close_buys=PressedAutoCloseButtonBuys();

   bool auto_close_sells=PressedAutoCloseButtonSells();

   bool auto_close_all=PressedAutoCloseButtonAll();

   if(auto_close_buys || auto_close_sells || auto_close_all)

     {

      double profit_buys=0.0;

      double profit_sells=0.0;

      ProfitAllPositions(profit_buys,profit_sells);

      if(auto_close_all)

         if(profit_buys+profit_sells>ValueAutoEditKVNAll())

            m_need_close_all=true;

      if(auto_close_buys)

         if(profit_buys>ValueAutoEditKVNBuys())

            m_need_close_buys=true;

      if(auto_close_sells)

         if(profit_sells>ValueAutoEditKVNSells())

            m_need_close_sells=true;

      return;

     }

//---

   int size_need_position=ArraySize(SPosition);

   if(size_need_position>0)

     {

      for(int i=size_need_position-1; i>=0; i--)

        {

         if(SPosition[i].waiting_transaction)

           {

            if(!SPosition[i].transaction_confirmed)

              {

               if(InpPrintLog)

                  Print(__FILE__," ",__FUNCTION__,", OK: ","transaction_confirmed: ",SPosition[i].transaction_confirmed);

               return;

              }

            else

               if(SPosition[i].transaction_confirmed)

                 {

                  ArrayRemove(SPosition,i,1);

                  return;

                 }

           }

         if(SPosition[i].pos_type==POSITION_TYPE_BUY)

           {

            double level;

            if(FreezeStopsLevels(level))

              {

               SPosition[i].waiting_transaction=true;

               OpenPosition(i,level);

              }

            return;

           }

         if(SPosition[i].pos_type==POSITION_TYPE_SELL)

           {

            double level;

            if(FreezeStopsLevels(level))

              {

               SPosition[i].waiting_transaction=true;

               OpenPosition(i,level);

              }

            return;

           }

        }

     }

//---

   if(m_last_deal_in_buy!=0.0 || m_last_deal_in_sell!=0.0)

     {

      if(!RefreshRates())

         return;

      if(m_last_deal_in_buy!=0)

         if(PressedGridButtonBuy())

           {

            double step=ValueGridEditKVNStepBuy()*m_adjusted_point;

            if(step>0)

               if(m_symbol.Ask()-m_last_deal_in_buy>step)

                 {

                  double lot=LotCheck(ValueGridEditKVNLotBuy(),m_symbol);

                  if(lot>0.0)

                    {

                     size_need_position=ArraySize(SPosition);

                     ArrayResize(SPosition,size_need_position+1);

                     SPosition[size_need_position].pos_type=POSITION_TYPE_BUY;

                     SPosition[size_need_position].volume=lot;

                     if(InpPrintLog)

                        Print(__FILE__," ",__FUNCTION__,", OK: ","Signal BUY");

                    }

                 }

           }

      if(m_last_deal_in_sell!=0)

         if(PressedGridButtonSell())

           {

            double step=ValueGridEditKVNStepSell()*m_adjusted_point;

            if(step>0)

               if(m_last_deal_in_sell-m_symbol.Bid()>step)

                 {

                  double lot=LotCheck(ValueGridEditKVNLotSell(),m_symbol);

                  if(lot>0.0)

                    {

                     size_need_position=ArraySize(SPosition);

                     ArrayResize(SPosition,size_need_position+1);

                     SPosition[size_need_position].pos_type=POSITION_TYPE_SELL;

                     SPosition[size_need_position].volume=lot;

                     if(InpPrintLog)

                        Print(__FILE__," ",__FUNCTION__,", OK: ","Signal SELL");

                    }

                 }

           }

     }

  }

//+------------------------------------------------------------------+

//| Panel TradeTransaction function                                  |

//+------------------------------------------------------------------+

void CControlsDialog::OnTradeTransactionPanel(const MqlTradeTransaction &trans,

      const MqlTradeRequest &request,

      const MqlTradeResult &result)

  {

//--- get transaction type as enumeration value

   ENUM_TRADE_TRANSACTION_TYPE type=trans.type;

//--- if transaction is result of addition of the transaction in history

   if(type==TRADE_TRANSACTION_DEAL_ADD)

     {

      long     deal_ticket       =0;

      long     deal_order        =0;

      long     deal_time         =0;

      long     deal_time_msc     =0;

      long     deal_type         =-1;

      long     deal_entry        =-1;

      long     deal_magic        =0;

      long     deal_reason       =-1;

      long     deal_position_id  =0;

      double   deal_volume       =0.0;

      double   deal_price        =0.0;

      double   deal_commission   =0.0;

      double   deal_swap         =0.0;

      double   deal_profit       =0.0;

      string   deal_symbol       ="";

      string   deal_comment      ="";

      string   deal_external_id  ="";

      if(HistoryDealSelect(trans.deal))

        {

         deal_ticket       =HistoryDealGetInteger(trans.deal,DEAL_TICKET);

         deal_order        =HistoryDealGetInteger(trans.deal,DEAL_ORDER);

         deal_time         =HistoryDealGetInteger(trans.deal,DEAL_TIME);

         deal_time_msc     =HistoryDealGetInteger(trans.deal,DEAL_TIME_MSC);

         deal_type         =HistoryDealGetInteger(trans.deal,DEAL_TYPE);

         deal_entry        =HistoryDealGetInteger(trans.deal,DEAL_ENTRY);

         deal_magic        =HistoryDealGetInteger(trans.deal,DEAL_MAGIC);

         deal_reason       =HistoryDealGetInteger(trans.deal,DEAL_REASON);

         deal_position_id  =HistoryDealGetInteger(trans.deal,DEAL_POSITION_ID);

         deal_volume       =HistoryDealGetDouble(trans.deal,DEAL_VOLUME);

         deal_price        =HistoryDealGetDouble(trans.deal,DEAL_PRICE);

         deal_commission   =HistoryDealGetDouble(trans.deal,DEAL_COMMISSION);

         deal_swap         =HistoryDealGetDouble(trans.deal,DEAL_SWAP);

         deal_profit       =HistoryDealGetDouble(trans.deal,DEAL_PROFIT);

         deal_symbol       =HistoryDealGetString(trans.deal,DEAL_SYMBOL);

         deal_comment      =HistoryDealGetString(trans.deal,DEAL_COMMENT);

         deal_external_id  =HistoryDealGetString(trans.deal,DEAL_EXTERNAL_ID);

        }

      else

         return;

      ENUM_DEAL_ENTRY enum_deal_entry=(ENUM_DEAL_ENTRY)deal_entry;

      if(deal_symbol==m_symbol.Name() && deal_magic==InpMagic)

        {

         if(deal_type==DEAL_TYPE_BUY || deal_type==DEAL_TYPE_SELL)

           {

            if(deal_entry==DEAL_ENTRY_IN)

               if(deal_type==DEAL_TYPE_BUY)

                  m_last_deal_in_buy=deal_price;

            if(deal_entry==DEAL_ENTRY_IN)

               if(deal_type==DEAL_TYPE_SELL)

                  m_last_deal_in_sell=deal_price;

            int size_need_position=ArraySize(SPosition);

            if(size_need_position>0)

              {

               for(int i=0; i<size_need_position; i++)

                 {

                  if(SPosition[i].waiting_transaction)

                     if(SPosition[i].waiting_order_ticket==deal_order)

                       {

                        Print(__FUNCTION__," Transaction confirmed");

                        SPosition[i].transaction_confirmed=true;

                        break;

                       }

                 }

              }

           }

        }

     }

  }

//+------------------------------------------------------------------+

//| Refreshes the symbol quotes data                                 |

//+------------------------------------------------------------------+

bool CControlsDialog::RefreshRates()

  {

//--- refresh rates

   if(!m_symbol.RefreshRates())

     {

      if(InpPrintLog)

         Print(__FILE__," ",__FUNCTION__,", ERROR: ","RefreshRates error");

      return(false);

     }

//--- protection against the return value of "zero"

   if(m_symbol.Ask()==0 || m_symbol.Bid()==0)

     {

      if(InpPrintLog)

         Print(__FILE__," ",__FUNCTION__,", ERROR: ","Ask == 0.0 OR Bid == 0.0");

      return(false);

     }

//---

   return(true);

  }

//+------------------------------------------------------------------+

//| Check the correctness of the position volume                     |

//+------------------------------------------------------------------+

bool CControlsDialog::CheckVolumeValue(double volume,string &error_description)

  {

//--- minimal allowed volume for trade operations

   double min_volume=m_symbol.LotsMin();

   if(volume<min_volume)

     {

      if(TerminalInfoString(TERMINAL_LANGUAGE)=="Russian")

         error_description=StringFormat("1J5< <5=LH5 <8=8<0;L=> 4>?CAB8<>3> SYMBOL_VOLUME_MIN=%.2f",min_volume);

      else

         error_description=StringFormat("Volume is less than the minimal allowed SYMBOL_VOLUME_MIN=%.2f",min_volume);

      return(false);

     }

//--- maximal allowed volume of trade operations

   double max_volume=m_symbol.LotsMax();

   if(volume>max_volume)

     {

      if(TerminalInfoString(TERMINAL_LANGUAGE)=="Russian")

         error_description=StringFormat("1J5< 1>;LH5 <0:A8<0;L=> 4>?CAB8<>3> SYMBOL_VOLUME_MAX=%.2f",max_volume);

      else

         error_description=StringFormat("Volume is greater than the maximal allowed SYMBOL_VOLUME_MAX=%.2f",max_volume);

      return(false);

     }

//--- get minimal step of volume changing

   double volume_step=m_symbol.LotsStep();

   int ratio=(int)MathRound(volume/volume_step);

   if(MathAbs(ratio*volume_step-volume)>0.0000001)

     {

      if(TerminalInfoString(TERMINAL_LANGUAGE)=="Russian")

         error_description=StringFormat("1J5< =5 :@0B5= <8=8<0;L=><C H03C SYMBOL_VOLUME_STEP=%.2f, 1;8609H89 ?@028;L=K9 >1J5< %.2f",

                                        volume_step,ratio*volume_step);

      else

         error_description=StringFormat("Volume is not a multiple of the minimal step SYMBOL_VOLUME_STEP=%.2f, the closest correct volume is %.2f",

                                        volume_step,ratio*volume_step);

      return(false);

     }

   error_description="Correct volume value";

   return(true);

  }

//+------------------------------------------------------------------+

//| Check Freeze and Stops levels                                    |

//+------------------------------------------------------------------+

bool CControlsDialog::FreezeStopsLevels(double &level)

  {

//--- check Freeze and Stops levels

   /*

      Type of order/position  |  Activation price  |  Check

      ------------------------|--------------------|--------------------------------------------

      Buy Limit order         |  Ask               |  Ask-OpenPrice  >= SYMBOL_TRADE_FREEZE_LEVEL

      Buy Stop order          |  Ask               |  OpenPrice-Ask  >= SYMBOL_TRADE_FREEZE_LEVEL

      Sell Limit order        |  Bid               |  OpenPrice-Bid  >= SYMBOL_TRADE_FREEZE_LEVEL

      Sell Stop order         |  Bid               |  Bid-OpenPrice  >= SYMBOL_TRADE_FREEZE_LEVEL

      Buy position            |  Bid               |  TakeProfit-Bid >= SYMBOL_TRADE_FREEZE_LEVEL

                              |                    |  Bid-StopLoss   >= SYMBOL_TRADE_FREEZE_LEVEL

      Sell position           |  Ask               |  Ask-TakeProfit >= SYMBOL_TRADE_FREEZE_LEVEL

                              |                    |  StopLoss-Ask   >= SYMBOL_TRADE_FREEZE_LEVEL



      Buying is done at the Ask price                 |  Selling is done at the Bid price

      ------------------------------------------------|----------------------------------

      TakeProfit        >= Bid                        |  TakeProfit        <= Ask

      StopLoss          <= Bid                        |  StopLoss          >= Ask

      TakeProfit - Bid  >= SYMBOL_TRADE_STOPS_LEVEL   |  Ask - TakeProfit  >= SYMBOL_TRADE_STOPS_LEVEL

      Bid - StopLoss    >= SYMBOL_TRADE_STOPS_LEVEL   |  StopLoss - Ask    >= SYMBOL_TRADE_STOPS_LEVEL

   */

   if(!RefreshRates() || !m_symbol.Refresh())

      return(false);

//--- FreezeLevel -> for pending order and modification

   double freeze_level=m_symbol.FreezeLevel()*m_symbol.Point();

   if(freeze_level==0.0)

      freeze_level=(m_symbol.Ask()-m_symbol.Bid())*3.0;

//--- StopsLevel -> for TakeProfit and StopLoss

   double stop_level=m_symbol.StopsLevel()*m_symbol.Point();

   if(stop_level==0.0)

      stop_level=(m_symbol.Ask()-m_symbol.Bid())*3.0;

   if(freeze_level<=0.0 || stop_level<=0.0)

      return(false);

   level=(freeze_level>stop_level)?freeze_level:stop_level;

   double spread=m_symbol.Spread()*m_symbol.Point()*3.0;

   level=(level>spread)?level:spread;

//---

   return(true);

  }

//+------------------------------------------------------------------+

//| Lot Check                                                        |

//+------------------------------------------------------------------+

double CControlsDialog::LotCheck(double lots,CSymbolInfo &symbol)

  {

//--- calculate maximum volume

   double volume=NormalizeDouble(lots,2);

   double stepvol=symbol.LotsStep();

   if(stepvol>0.0)

      volume=stepvol*MathFloor(volume/stepvol);

//---

   double minvol=symbol.LotsMin();

   if(volume<minvol)

      volume=0.0;

//---

   double maxvol=symbol.LotsMax();

   if(volume>maxvol)

      volume=maxvol;

   return(volume);

  }

//+------------------------------------------------------------------+

//| Open position                                                    |

//|   double stop_loss                                               |

//|      -> pips * m_adjusted_point (if "0.0" -> the m_stop_loss)    |

//|   double take_profit                                             |

//|      -> pips * m_adjusted_point (if "0.0" -> the m_take_profit)  |

//+------------------------------------------------------------------+

void CControlsDialog::OpenPosition(const int index,const double level)

  {

   /*

      Buying is done at the Ask price                 |  Selling is done at the Bid price

      ------------------------------------------------|----------------------------------

      TakeProfit        >= Bid                        |  TakeProfit        <= Ask

      StopLoss          <= Bid                        |  StopLoss          >= Ask

      TakeProfit - Bid  >= SYMBOL_TRADE_STOPS_LEVEL   |  Ask - TakeProfit  >= SYMBOL_TRADE_STOPS_LEVEL

      Bid - StopLoss    >= SYMBOL_TRADE_STOPS_LEVEL   |  StopLoss - Ask    >= SYMBOL_TRADE_STOPS_LEVEL

   */

//--- buy

   if(SPosition[index].pos_type==POSITION_TYPE_BUY)

     {

      OpenBuy(index);

      return;

     }

//--- sell

   if(SPosition[index].pos_type==POSITION_TYPE_SELL)

     {

      OpenSell(index);

      return;

     }

  }

//+------------------------------------------------------------------+

//| Open Buy position                                                |

//+------------------------------------------------------------------+

void CControlsDialog::OpenBuy(const int index)

  {

   double sl=0.0;

   double tp=0.0;

   double long_lot=0.0;

   if(SPosition[index].volume>0.0)

      long_lot=SPosition[index].volume;

   else

     {

      ArrayRemove(SPosition,index,1);

      return;

     }

   if(m_symbol.LotsLimit()>0.0)

     {

      int      count_buys           = 0;

      double   volume_buys          = 0.0;

      double   volume_biggest_buys  = 0.0;

      int      count_sells          = 0;

      double   volume_sells         = 0.0;

      double   volume_biggest_sells = 0.0;

      CalculateAllPositions(count_buys,volume_buys,volume_biggest_buys,

                            count_sells,volume_sells,volume_biggest_sells);

      if(volume_buys+volume_sells+long_lot>m_symbol.LotsLimit())

        {

         ArrayRemove(SPosition,index,1);

         if(InpPrintLog)

            Print(__FILE__," ",__FUNCTION__,", ERROR: ","#0 Buy, Volume Buy (",DoubleToString(volume_buys,2),

                  ") + Volume Sell (",DoubleToString(volume_sells,2),

                  ") + Volume long (",DoubleToString(long_lot,2),

                  ") > Lots Limit (",DoubleToString(m_symbol.LotsLimit(),2),")");

         return;

        }

     }

//--- check volume before OrderSend to avoid "not enough money" error (CTrade)

   double free_margin_check=m_account.FreeMarginCheck(m_symbol.Name(),

                            ORDER_TYPE_BUY,

                            long_lot,

                            m_symbol.Ask());

   double margin_check=m_account.MarginCheck(m_symbol.Name(),

                       ORDER_TYPE_BUY,

                       long_lot,

                       m_symbol.Ask());

   if(free_margin_check>margin_check)

     {

      if(m_trade.Buy(long_lot,m_symbol.Name(),

                     m_symbol.Ask(),sl,tp)) // CTrade::Buy -> "true"

        {

         if(m_trade.ResultDeal()==0)

           {

            if(m_trade.ResultRetcode()==10009) // trade order went to the exchange

              {

               SPosition[index].waiting_transaction=true;

               SPosition[index].waiting_order_ticket=m_trade.ResultOrder();

              }

            else

              {

               SPosition[index].waiting_transaction=false;

               if(InpPrintLog)

                  Print(__FILE__," ",__FUNCTION__,", ERROR: ","#1 Buy -> false. Result Retcode: ",m_trade.ResultRetcode(),

                        ", description of result: ",m_trade.ResultRetcodeDescription());

              }

            if(InpPrintLog)

               PrintResultTrade(m_trade,m_symbol);

           }

         else

           {

            if(m_trade.ResultRetcode()==10009)

              {

               SPosition[index].waiting_transaction=true;

               SPosition[index].waiting_order_ticket=m_trade.ResultOrder();

              }

            else

              {

               SPosition[index].waiting_transaction=false;

               if(InpPrintLog)

                  Print(__FILE__," ",__FUNCTION__,", OK: ","#2 Buy -> true. Result Retcode: ",m_trade.ResultRetcode(),

                        ", description of result: ",m_trade.ResultRetcodeDescription());

              }

            if(InpPrintLog)

               PrintResultTrade(m_trade,m_symbol);

           }

        }

      else

        {

         SPosition[index].waiting_transaction=false;

         if(InpPrintLog)

            Print(__FILE__," ",__FUNCTION__,", ERROR: ","#3 Buy -> false. Result Retcode: ",m_trade.ResultRetcode(),

                  ", description of result: ",m_trade.ResultRetcodeDescription());

         if(InpPrintLog)

            PrintResultTrade(m_trade,m_symbol);

        }

     }

   else

     {

      ArrayRemove(SPosition,index,1);

      if(InpPrintLog)

         Print(__FILE__," ",__FUNCTION__,", ERROR: ","CAccountInfo.FreeMarginCheck returned the value ",DoubleToString(free_margin_check,2));

      return;

     }

//---

  }

//+------------------------------------------------------------------+

//| Open Sell position                                               |

//+------------------------------------------------------------------+

void CControlsDialog::OpenSell(const int index)

  {

   double sl=0.0;

   double tp=0.0;

   double short_lot=0.0;

   if(SPosition[index].volume>0.0)

      short_lot=SPosition[index].volume;

   else

     {

      ArrayRemove(SPosition,index,1);

      return;

     }

   if(m_symbol.LotsLimit()>0.0)

     {

      int      count_buys           = 0;

      double   volume_buys          = 0.0;

      double   volume_biggest_buys  = 0.0;

      int      count_sells          = 0;

      double   volume_sells         = 0.0;

      double   volume_biggest_sells = 0.0;

      CalculateAllPositions(count_buys,volume_buys,volume_biggest_buys,

                            count_sells,volume_sells,volume_biggest_sells);

      if(volume_buys+volume_sells+short_lot>m_symbol.LotsLimit())

        {

         ArrayRemove(SPosition,index,1);

         if(InpPrintLog)

            Print(__FILE__," ",__FUNCTION__,", ERROR: ","#0 Buy, Volume Buy (",DoubleToString(volume_buys,2),

                  ") + Volume Sell (",DoubleToString(volume_sells,2),

                  ") + Volume short (",DoubleToString(short_lot,2),

                  ") > Lots Limit (",DoubleToString(m_symbol.LotsLimit(),2),")");

         return;

        }

     }

//--- check volume before OrderSend to avoid "not enough money" error (CTrade)

   double free_margin_check=m_account.FreeMarginCheck(m_symbol.Name(),

                            ORDER_TYPE_SELL,

                            short_lot,

                            m_symbol.Bid());

   double margin_check=m_account.MarginCheck(m_symbol.Name(),

                       ORDER_TYPE_SELL,

                       short_lot,

                       m_symbol.Bid());

   if(free_margin_check>margin_check)

     {

      if(m_trade.Sell(short_lot,m_symbol.Name(),

                      m_symbol.Bid(),sl,tp)) // CTrade::Sell -> "true"

        {

         if(m_trade.ResultDeal()==0)

           {

            if(m_trade.ResultRetcode()==10009) // trade order went to the exchange

              {

               SPosition[index].waiting_transaction=true;

               SPosition[index].waiting_order_ticket=m_trade.ResultOrder();

              }

            else

              {

               SPosition[index].waiting_transaction=false;

               if(InpPrintLog)

                  Print(__FILE__," ",__FUNCTION__,", ERROR: ","#1 Sell -> false. Result Retcode: ",m_trade.ResultRetcode(),

                        ", description of result: ",m_trade.ResultRetcodeDescription());

              }

            if(InpPrintLog)

               PrintResultTrade(m_trade,m_symbol);

           }

         else

           {

            if(m_trade.ResultRetcode()==10009)

              {

               SPosition[index].waiting_transaction=true;

               SPosition[index].waiting_order_ticket=m_trade.ResultOrder();

              }

            else

              {

               SPosition[index].waiting_transaction=false;

               if(InpPrintLog)

                  Print(__FILE__," ",__FUNCTION__,", OK: ","#2 Sell -> true. Result Retcode: ",m_trade.ResultRetcode(),

                        ", description of result: ",m_trade.ResultRetcodeDescription());

              }

            if(InpPrintLog)

               PrintResultTrade(m_trade,m_symbol);

           }

        }

      else

        {

         SPosition[index].waiting_transaction=false;

         if(InpPrintLog)

            Print(__FILE__," ",__FUNCTION__,", ERROR: ","#3 Sell -> false. Result Retcode: ",m_trade.ResultRetcode(),

                  ", description of result: ",m_trade.ResultRetcodeDescription());

         if(InpPrintLog)

            PrintResultTrade(m_trade,m_symbol);

        }

     }

   else

     {

      ArrayRemove(SPosition,index,1);

      if(InpPrintLog)

         Print(__FILE__," ",__FUNCTION__,", ERROR: ","CAccountInfo.FreeMarginCheck returned the value ",DoubleToString(free_margin_check,2));

      return;

     }

//---

  }

//+------------------------------------------------------------------+

//| Print CTrade result                                              |

//+------------------------------------------------------------------+

void CControlsDialog::PrintResultTrade(CTrade &trade,CSymbolInfo &symbol)

  {

   Print(__FILE__," ",__FUNCTION__,", Symbol: ",symbol.Name()+", "+

         "Code of request result: "+IntegerToString(trade.ResultRetcode())+", "+

         "Code of request result as a string: "+trade.ResultRetcodeDescription());

   Print("Deal ticket: "+IntegerToString(trade.ResultDeal())+", "+

         "Order ticket: "+IntegerToString(trade.ResultOrder())+", "+

         "Order retcode external: "+IntegerToString(trade.ResultRetcodeExternal())+", "+

         "Volume of deal or order: "+DoubleToString(trade.ResultVolume(),2));

   Print("Price, confirmed by broker: "+DoubleToString(trade.ResultPrice(),symbol.Digits())+", "+

         "Current bid price: "+DoubleToString(symbol.Bid(),symbol.Digits())+" (the requote): "+DoubleToString(trade.ResultBid(),symbol.Digits())+", "+

         "Current ask price: "+DoubleToString(symbol.Ask(),symbol.Digits())+" (the requote): "+DoubleToString(trade.ResultAsk(),symbol.Digits()));

   Print("Broker comment: "+trade.ResultComment());

  }

//+------------------------------------------------------------------+

//| Close positions                                                  |

//+------------------------------------------------------------------+

void CControlsDialog::ClosePositions(const ENUM_POSITION_TYPE pos_type,const double level)

  {

   /*

      Buying is done at the Ask price                 |  Selling is done at the Bid price

      ------------------------------------------------|----------------------------------

      TakeProfit        >= Bid                        |  TakeProfit        <= Ask

      StopLoss          <= Bid                        |  StopLoss          >= Ask

      TakeProfit - Bid  >= SYMBOL_TRADE_STOPS_LEVEL   |  Ask - TakeProfit  >= SYMBOL_TRADE_STOPS_LEVEL

      Bid - StopLoss    >= SYMBOL_TRADE_STOPS_LEVEL   |  StopLoss - Ask    >= SYMBOL_TRADE_STOPS_LEVEL

   */

   for(int i=PositionsTotal()-1; i>=0; i--) // returns the number of current positions

      if(m_position.SelectByIndex(i)) // selects the position by index for further access to its properties

         if(m_position.Symbol()==m_symbol.Name() && m_position.Magic()==InpMagic)

            if(m_position.PositionType()==pos_type)

              {

               if(m_position.PositionType()==POSITION_TYPE_BUY)

                 {

                  bool take_profit_level=(m_position.TakeProfit()!=0.0 && m_position.TakeProfit()-m_position.PriceCurrent()>=level) || m_position.TakeProfit()==0.0;

                  bool stop_loss_level=(m_position.StopLoss()!=0.0 && m_position.PriceCurrent()-m_position.StopLoss()>=level) || m_position.StopLoss()==0.0;

                  if(take_profit_level && stop_loss_level)

                     if(!m_trade.PositionClose(m_position.Ticket())) // close a position by the specified m_symbol

                        if(InpPrintLog)

                           Print(__FILE__," ",__FUNCTION__,", ERROR: ","CTrade.PositionClose ",m_position.Ticket());

                 }

               if(m_position.PositionType()==POSITION_TYPE_SELL)

                 {

                  bool take_profit_level=(m_position.TakeProfit()!=0.0 && m_position.PriceCurrent()-m_position.TakeProfit()>=level) || m_position.TakeProfit()==0.0;

                  bool stop_loss_level=(m_position.StopLoss()!=0.0 && m_position.StopLoss()-m_position.PriceCurrent()>=level) || m_position.StopLoss()==0.0;

                  if(!m_trade.PositionClose(m_position.Ticket())) // close a position by the specified m_symbol

                     if(InpPrintLog)

                        Print(__FILE__," ",__FUNCTION__,", ERROR: ","CTrade.PositionClose ",m_position.Ticket());

                 }

              }

  }

//+------------------------------------------------------------------+

//| Is position exists                                               |

//+------------------------------------------------------------------+

bool CControlsDialog::IsPositionExists(void)

  {

   for(int i=PositionsTotal()-1; i>=0; i--)

      if(m_position.SelectByIndex(i)) // selects the position by index for further access to its properties

         if(m_position.Symbol()==m_symbol.Name() && m_position.Magic()==InpMagic)

            return(true);

//---

   return(false);

  }

//+------------------------------------------------------------------+

//| Close all positions                                              |

//+------------------------------------------------------------------+

void CControlsDialog::CloseAllPositions(const double level)

  {

   /*

      Buying is done at the Ask price                 |  Selling is done at the Bid price

      ------------------------------------------------|----------------------------------

      TakeProfit        >= Bid                        |  TakeProfit        <= Ask

      StopLoss          <= Bid                        |  StopLoss          >= Ask

      TakeProfit - Bid  >= SYMBOL_TRADE_STOPS_LEVEL   |  Ask - TakeProfit  >= SYMBOL_TRADE_STOPS_LEVEL

      Bid - StopLoss    >= SYMBOL_TRADE_STOPS_LEVEL   |  StopLoss - Ask    >= SYMBOL_TRADE_STOPS_LEVEL

   */

   for(int i=PositionsTotal()-1; i>=0; i--) // returns the number of current positions

      if(m_position.SelectByIndex(i)) // selects the position by index for further access to its properties

         if(m_position.Symbol()==m_symbol.Name() && m_position.Magic()==InpMagic)

           {

            if(m_position.PositionType()==POSITION_TYPE_BUY)

              {

               bool take_profit_level=(m_position.TakeProfit()!=0.0 && m_position.TakeProfit()-m_position.PriceCurrent()>=level) || m_position.TakeProfit()==0.0;

               bool stop_loss_level=(m_position.StopLoss()!=0.0 && m_position.PriceCurrent()-m_position.StopLoss()>=level) || m_position.StopLoss()==0.0;

               if(take_profit_level && stop_loss_level)

                  if(!m_trade.PositionClose(m_position.Ticket())) // close a position by the specified m_symbol

                     if(InpPrintLog)

                        Print(__FILE__," ",__FUNCTION__,", ERROR: ","CTrade.PositionClose ",m_position.Ticket());

              }

            if(m_position.PositionType()==POSITION_TYPE_SELL)

              {

               bool take_profit_level=(m_position.TakeProfit()!=0.0 && m_position.PriceCurrent()-m_position.TakeProfit()>=level) || m_position.TakeProfit()==0.0;

               bool stop_loss_level=(m_position.StopLoss()!=0.0 && m_position.StopLoss()-m_position.PriceCurrent()>=level) || m_position.StopLoss()==0.0;

               if(take_profit_level && stop_loss_level)

                  if(!m_trade.PositionClose(m_position.Ticket())) // close a position by the specified m_symbol

                     if(InpPrintLog)

                        Print(__FILE__," ",__FUNCTION__,", ERROR: ","CTrade.PositionClose ",m_position.Ticket());

              }

           }

  }

//+------------------------------------------------------------------+

//| Profit all positions                                             |

//+------------------------------------------------------------------+

void CControlsDialog::ProfitAllPositions(double &profit_buys,double &profit_sells)

  {

   profit_buys=0.0;

   profit_sells=0.0;

   for(int i=PositionsTotal()-1; i>=0; i--)

      if(m_position.SelectByIndex(i)) // selects the position by index for further access to its properties

         if(m_position.Symbol()==m_symbol.Name() && m_position.Magic()==InpMagic)

           {

            double profit=m_position.Commission()+m_position.Swap()+m_position.Profit();

            if(m_position.PositionType()==POSITION_TYPE_BUY)

               profit_buys+=profit;

            else

               profit_sells+=profit;

           }

  }

//+------------------------------------------------------------------+

//| Calculate all positions                                          |

//+------------------------------------------------------------------+

void CControlsDialog::CalculateAllPositions(int &count_buys,double &volume_buys,double &volume_biggest_buys,

      int &count_sells,double &volume_sells,double &volume_biggest_sells)

  {

   count_buys  = 0;

   volume_buys   = 0.0;

   volume_biggest_buys  = 0.0;

   count_sells = 0;

   volume_sells  = 0.0;

   volume_biggest_sells = 0.0;

   for(int i=PositionsTotal()-1; i>=0; i--)

      if(m_position.SelectByIndex(i)) // selects the position by index for further access to its properties

         if(m_position.Symbol()==m_symbol.Name() && m_position.Magic()==InpMagic)

           {

            if(m_position.PositionType()==POSITION_TYPE_BUY)

              {

               count_buys++;

               volume_buys+=m_position.Volume();

               if(m_position.Volume()>volume_biggest_buys)

                  volume_biggest_buys=m_position.Volume();

               continue;

              }

            else

               if(m_position.PositionType()==POSITION_TYPE_SELL)

                 {

                  count_sells++;

                  volume_sells+=m_position.Volume();

                  if(m_position.Volume()>volume_biggest_sells)

                     volume_biggest_sells=m_position.Volume();

                 }

           }

  }

//+------------------------------------------------------------------+

//| Create                                                           |

//+------------------------------------------------------------------+

bool CControlsDialog::Create(const long chart,const string name,const int subwin,const int x1,const int y1,const int x2,const int y2)

  {

   if(!CAppDialog::Create(chart,name,subwin,x1,y1,x2,y2))

      return(false);

//--- create dependent controls

   if(!CreateMoneyWndClient())

      return(false);

   if(!CreateMoneyLabels())

      return(false);

   if(!CreateManualCloseWndClient())

      return(false);

   if(!CreateManualCloseButtons())

      return(false);

   if(!CreateAutoCloseWndClient())

      return(false);

   if(!CreateAutoCloseEdits())

      return(false);

   if(!CreateAutoCloseButtons())

      return(false);

   if(!CreateGridWndClient())

      return(false);

   if(!CreateGridLabels())

      return(false);

   if(!CreateGridEdits())

      return(false);

   if(!CreateGridButtons())

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Money WndClient"                                          |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateMoneyWndClient(void)

  {

//--- coordinates

   int x1=INDENT_LEFT;

   int y1=INDENT_TOP;

   int x2=x1+WNDCLIENT_WIDTH;

   int y2=y1+WNDCLIENT_HEIGHT;

//--- create "Money WndClient"

   if(!m_mony_wndclient.Create(m_chart_id,m_name+"Money WndClient",m_subwin,x1,y1,x2,y2))

      return(false);

//--- set up

   if(!m_mony_wndclient.ColorBackground(CONTROLS_RADIOGROUP_COLOR_BG))

      return(false);

   if(!m_mony_wndclient.ColorBorder(CONTROLS_RADIOGROUP_COLOR_BORDER))

      return(false);

   if(!Add(m_mony_wndclient))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Money Labels"                                             |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateMoneyLabels(void)

  {

//--- coordinates

   int x1=INDENT_LEFT+3;

   int y1=INDENT_TOP+3;

   int x2=x1+1;

   int y2=y1+1;

//--- create label "Balance Equity"

   if(!m_mony_label_balance_equity.Create(m_chart_id,m_name+"Money Balance Equity",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_mony_label_balance_equity.Font("Consolas"))

      return(false);

   if(!m_mony_label_balance_equity.Text(StringFormat("%-13s","Balance: ")+StringFormat("%-12s",DoubleToString(m_account.Balance(),2))+

                                        StringFormat("%-13s","Equity: ")+StringFormat("%-12s",DoubleToString(m_account.Equity(),2))))

      return(false);

   if(!Add(m_mony_label_balance_equity))

      return(false);

//--- create label "Margin Free Margin"

   y1=y1+CONTROLS_GAP_Y+EDIT_HEIGHT;

   y2=y1+1;

   if(!m_mony_label_margin_free_margin.Create(m_chart_id,m_name+"Money Margin Free Margin",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_mony_label_margin_free_margin.Font("Consolas"))

      return(false);

   if(!m_mony_label_margin_free_margin.Text(StringFormat("%-13s","Margin: ")+StringFormat("%-12s",DoubleToString(m_account.Margin(),2))+

         StringFormat("%-13s","Free Margin: ")+StringFormat("%-12s",DoubleToString(m_account.FreeMargin(),2))))

      return(false);

   if(!Add(m_mony_label_margin_free_margin))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Manual Close WndClient"                                  |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateManualCloseWndClient(void)

  {

//--- coordinates

   int x1=INDENT_LEFT;

   int y1=INDENT_TOP+CONTROLS_GAP_Y+WNDCLIENT_HEIGHT;

   int x2=x1+WNDCLIENT_WIDTH;

   int y2=y1+WNDCLIENT_HEIGHT;

//--- create

   if(!m_manual_close_wndclient.Create(m_chart_id,m_name+"Manual Close WndClient",m_subwin,x1,y1,x2,y2))

      return(false);

//--- set up

   if(!m_manual_close_wndclient.ColorBackground(CONTROLS_RADIOGROUP_COLOR_BG))

      return(false);

   if(!m_manual_close_wndclient.ColorBorder(CONTROLS_RADIOGROUP_COLOR_BORDER))

      return(false);

   if(!Add(m_manual_close_wndclient))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Manual Close Buttons"                                    |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateManualCloseButtons(void)

  {

//--- coordinates

   int x1=INDENT_LEFT+3;

   int y1=INDENT_TOP+CONTROLS_GAP_Y+WNDCLIENT_HEIGHT+3;

   int x2=x1+BUTTON_WIDTH;

   int y2=y1+BUTTON_HEIGHT;

//--- create button "Close Buys"

   if(!m_manual_close_button_buys.Create(m_chart_id,m_name+"Manual Close Buys",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_manual_close_button_buys.Font("Consolas"))

      return(false);

   if(!m_manual_close_button_buys.Text("Close Buys"+" ("+"+123.12"+")"))

      return(false);

   if(!Add(m_manual_close_button_buys))

      return(false);

//--- create button "Close Sells"

   x1=x1+BUTTON_WIDTH+CONTROLS_GAP_X;

   x2=x1+BUTTON_WIDTH;

   if(!m_manual_close_button_sells.Create(m_chart_id,m_name+"Manual Close Sells",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_manual_close_button_sells.Font("Consolas"))

      return(false);

   if(!m_manual_close_button_sells.Text("Close Sells"+" ("+"100.12"+")"))

      return(false);

   if(!Add(m_manual_close_button_sells))

      return(false);

//--- create button "Close All"

   x1=INDENT_LEFT+3;

   y1=y1+CONTROLS_GAP_Y+BUTTON_HEIGHT;

   y2=y1+BUTTON_HEIGHT;

   if(!m_manual_close_button_all.Create(m_chart_id,m_name+"Manual Close All",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_manual_close_button_all.Font("Consolas"))

      return(false);

   if(!m_manual_close_button_all.Text("Close All"+" ("+"+12.00"+")"))

      return(false);

   if(!Add(m_manual_close_button_all))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Auto Close WndClient"                                    |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateAutoCloseWndClient(void)

  {

//--- coordinates

   int x1=INDENT_LEFT;

   int y1=INDENT_TOP+2*(CONTROLS_GAP_Y+WNDCLIENT_HEIGHT);

   int x2=x1+WNDCLIENT_WIDTH;

   int y2=y1+WNDCLIENT_HEIGHT;

//--- create

   if(!m_auto_close_wndclient.Create(m_chart_id,m_name+"Auto Close WndClient",m_subwin,x1,y1,x2,y2))

      return(false);

//--- set up

   if(!m_auto_close_wndclient.ColorBackground(CONTROLS_RADIOGROUP_COLOR_BG))

      return(false);

   if(!m_auto_close_wndclient.ColorBorder(CONTROLS_RADIOGROUP_COLOR_BORDER))

      return(false);

   if(!Add(m_auto_close_wndclient))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Auto Close Edits"                                        |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateAutoCloseEdits(void)

  {

//--- coordinates

   int x1=INDENT_LEFT+3;

   int y1=INDENT_TOP+2*(CONTROLS_GAP_Y+WNDCLIENT_HEIGHT)+3;

   int x2=x1+EDIT_WIDTH;

   int y2=y1+EDIT_HEIGHT;

//--- create editkvn "Auto Close Buys"

   if(!m_auto_close_editkvn_buys.Create(m_chart_id,m_name+"Auto Close Buys",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_auto_close_editkvn_buys.Font("Consolas"))

      return(false);

   if(!m_auto_close_editkvn_buys.Text("123.12"))

      return(false);

   if(!m_auto_close_editkvn_buys.ReadOnly(false))

      return(false);

   if(!Add(m_auto_close_editkvn_buys))

      return(false);

//--- create editkvn "Auto Close Sells"

   x1=x1+CONTROLS_GAP_X+EDIT_WIDTH;

   x2=x1+EDIT_WIDTH;

   if(!m_auto_close_editkvn_sells.Create(m_chart_id,m_name+"Auto Close Sells",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_auto_close_editkvn_sells.Font("Consolas"))

      return(false);

   if(!m_auto_close_editkvn_sells.Text("100.12"))

      return(false);

   if(!m_auto_close_editkvn_sells.ReadOnly(false))

      return(false);

   if(!Add(m_auto_close_editkvn_sells))

      return(false);

//--- create editkvn "Auto Close All"

   x1=x1+CONTROLS_GAP_X+EDIT_WIDTH;

   x2=x1+EDIT_WIDTH;

   if(!m_auto_close_editkvn_all.Create(m_chart_id,m_name+"Auto Close All",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_auto_close_editkvn_all.Font("Consolas"))

      return(false);

   if(!m_auto_close_editkvn_all.Text("12.00"))

      return(false);

   if(!m_auto_close_editkvn_all.ReadOnly(false))

      return(false);

   if(!Add(m_auto_close_editkvn_all))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Auto Close Buttons"                                      |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateAutoCloseButtons(void)

  {

//--- coordinates

   int x1=INDENT_LEFT+3;

   int y1=INDENT_TOP+2*(CONTROLS_GAP_Y+WNDCLIENT_HEIGHT)+3+CONTROLS_GAP_Y+EDIT_HEIGHT;

   int x2=x1+EDIT_WIDTH;

   int y2=y1+EDIT_HEIGHT;

//--- create button "Auto Close Button Buys"

   if(!m_auto_close_button_buys.Create(m_chart_id,m_name+"Auto Close Button Buys",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_auto_close_button_buys.Font("Consolas"))

      return(false);

   if(!m_auto_close_button_buys.Text("Auto Close Buys"))

      return(false);

   if(!Add(m_auto_close_button_buys))

      return(false);

   m_auto_close_button_buys.Locking(true);

//--- create button "Auto Close Button Buys"

   x1=x1+CONTROLS_GAP_X+EDIT_WIDTH;

   x2=x1+EDIT_WIDTH;

   if(!m_auto_close_button_sells.Create(m_chart_id,m_name+"Auto Close Button Sells",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_auto_close_button_sells.Font("Consolas"))

      return(false);

   if(!m_auto_close_button_sells.Text("Auto Close Sells"))

      return(false);

   if(!Add(m_auto_close_button_sells))

      return(false);

   m_auto_close_button_sells.Locking(true);

//--- create button "Auto Close Button All"

   x1=x1+CONTROLS_GAP_X+EDIT_WIDTH;

   x2=x1+EDIT_WIDTH;

   if(!m_auto_close_button_all.Create(m_chart_id,m_name+"Auto Close Button All",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_auto_close_button_all.Font("Consolas"))

      return(false);

   if(!m_auto_close_button_all.Text("Auto Close All"))

      return(false);

   if(!Add(m_auto_close_button_all))

      return(false);

   m_auto_close_button_all.Locking(true);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Grid WndClient"                                          |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateGridWndClient(void)

  {

//--- coordinates

   int x1=INDENT_LEFT;

   int y1=INDENT_TOP+3*(CONTROLS_GAP_Y+WNDCLIENT_HEIGHT);

   int x2=x1+WNDCLIENT_WIDTH;

   int y2=y1+WNDCLIENT_HEIGHT+17;

//--- create

   if(!m_grid_wndclient.Create(m_chart_id,m_name+"Grid WndClient",m_subwin,x1,y1,x2,y2))

      return(false);

//--- set up

   if(!m_grid_wndclient.ColorBackground(CONTROLS_RADIOGROUP_COLOR_BG))

      return(false);

   if(!m_grid_wndclient.ColorBorder(CONTROLS_RADIOGROUP_COLOR_BORDER))

      return(false);

   if(!Add(m_grid_wndclient))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Grid Labels"                                             |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateGridLabels(void)

  {

//--- coordinates

   int x1=INDENT_LEFT+3;

   int y1=INDENT_TOP+3*(CONTROLS_GAP_Y+WNDCLIENT_HEIGHT)+3;

   int x2=x1+1;

   int y2=y1+1;

//--- create label "Grid Label Lot"

   if(!m_grid_label_lot.Create(m_chart_id,m_name+"Grid Label Lot",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_grid_label_lot.Font("Consolas"))

      return(false);

   if(!m_grid_label_lot.Text("Lot"))

      return(false);

   if(!Add(m_grid_label_lot))

      return(false);

//--- create label "Grid Label Step"

   x1=INDENT_LEFT+3+EDIT_WIDTH+CONTROLS_GAP_X;

   x2=x1+EDIT_WIDTH;

   if(!m_grid_label_step.Create(m_chart_id,m_name+"Grid Label Step",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_grid_label_step.Font("Consolas"))

      return(false);

   if(!m_grid_label_step.Text("Step"))

      return(false);

   if(!Add(m_grid_label_step))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Grid Edits"                                              |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateGridEdits(void)

  {

//--- coordinates

   int x1=INDENT_LEFT+3;

   int y1=INDENT_TOP+3*(CONTROLS_GAP_Y+WNDCLIENT_HEIGHT)+CONTROLS_GAP_Y+EDIT_HEIGHT;

   int x2=x1+EDIT_WIDTH;

   int y2=y1+EDIT_HEIGHT;

//--- create editkvn "Grid Edit Lot Buy"

   if(!m_grid_editkvn_lot_buy.Create(m_chart_id,m_name+"Grid Edit Lot Buy",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_grid_editkvn_lot_buy.Font("Consolas"))

      return(false);

   if(!m_grid_editkvn_lot_buy.Text("0.03"))

      return(false);

   if(!m_grid_editkvn_lot_buy.ReadOnly(false))

      return(false);

   if(!Add(m_grid_editkvn_lot_buy))

      return(false);

//--- create editkvn "Grid Edit Lot Sell"

   y1=y1+CONTROLS_GAP_Y+EDIT_HEIGHT;

   y2=y1+EDIT_HEIGHT;

   if(!m_grid_editkvn_lot_sell.Create(m_chart_id,m_name+"Grid Edit Lot Sell",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_grid_editkvn_lot_sell.Font("Consolas"))

      return(false);

   if(!m_grid_editkvn_lot_sell.Text("0.02"))

      return(false);

   if(!m_grid_editkvn_lot_sell.ReadOnly(false))

      return(false);

   if(!Add(m_grid_editkvn_lot_sell))

      return(false);

//--- create editkvn "Grid Edit Step Buy"

   x1=INDENT_LEFT+3+CONTROLS_GAP_X+EDIT_WIDTH;

   y1=INDENT_TOP+3*(CONTROLS_GAP_Y+WNDCLIENT_HEIGHT)+CONTROLS_GAP_Y+EDIT_HEIGHT;

   x2=x1+EDIT_WIDTH;

   y2=y1+EDIT_HEIGHT;

   if(!m_grid_editkvn_step_buy.Create(m_chart_id,m_name+"Grid Edit Step Buy",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_grid_editkvn_step_buy.Font("Consolas"))

      return(false);

   if(!m_grid_editkvn_step_buy.Text("24"))

      return(false);

   if(!m_grid_editkvn_step_buy.ReadOnly(false))

      return(false);

   if(!Add(m_grid_editkvn_step_buy))

      return(false);

//--- create editkvn "Grid Edit Step Sell"

   y1=y1+CONTROLS_GAP_Y+EDIT_HEIGHT;

   y2=y1+EDIT_HEIGHT;

   if(!m_grid_editkvn_step_sell.Create(m_chart_id,m_name+"Grid Edit Step Sell",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_grid_editkvn_step_sell.Font("Consolas"))

      return(false);

   if(!m_grid_editkvn_step_sell.Text("24"))

      return(false);

   if(!m_grid_editkvn_step_sell.ReadOnly(false))

      return(false);

   if(!Add(m_grid_editkvn_step_sell))

      return(false);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Create "Grid Buttons"                                            |

//+------------------------------------------------------------------+

bool CControlsDialog::CreateGridButtons(void)

  {

//--- coordinates

   int x1=INDENT_LEFT+3+2*(CONTROLS_GAP_X+EDIT_WIDTH);

   int y1=INDENT_TOP+3*(CONTROLS_GAP_Y+WNDCLIENT_HEIGHT)+CONTROLS_GAP_Y+EDIT_HEIGHT;

   int x2=x1+EDIT_WIDTH;

   int y2=y1+EDIT_HEIGHT;

//--- create button "Grid Buy"

   if(!m_grid_button_buy.Create(m_chart_id,m_name+"Grid Buy",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_grid_button_buy.Font("Consolas"))

      return(false);

   if(!m_grid_button_buy.Text("Buy"))

      return(false);

   if(!Add(m_grid_button_buy))

      return(false);

   m_grid_button_buy.Locking(true);

//--- create button "Grid Sell"

   y1=y1+EDIT_HEIGHT+CONTROLS_GAP_Y;

   y2=y1+EDIT_HEIGHT;

   if(!m_grid_button_sell.Create(m_chart_id,m_name+"Grid Sell",m_subwin,x1,y1,x2,y2))

      return(false);

   if(!m_grid_button_sell.Font("Consolas"))

      return(false);

   if(!m_grid_button_sell.Text("Sell"))

      return(false);

   if(!Add(m_grid_button_sell))

      return(false);

   m_grid_button_sell.Locking(true);

//--- succeed

   return(true);

  }

//+------------------------------------------------------------------+

//| Event handler                                                    |

//+------------------------------------------------------------------+

void CControlsDialog::OnClickManualCloseButtonBuys(void)

  {

   Comment(__FUNCTION__);

   m_need_close_sells=true;

  }

//+------------------------------------------------------------------+

//| Event handler                                                    |

//+------------------------------------------------------------------+

void CControlsDialog::OnClickManualCloseButtonSells(void)

  {

   Comment(__FUNCTION__);

   m_need_close_buys=true;

  }

//+------------------------------------------------------------------+

//| Event handler                                                    |

//+------------------------------------------------------------------+

void CControlsDialog::OnClickManualCloseButtonAll(void)

  {

   Comment(__FUNCTION__);

   m_need_close_all=true;

  }

//+------------------------------------------------------------------+

//| Event handler                                                    |

//+------------------------------------------------------------------+

void CControlsDialog::OnClickAutoCloseButtonBuys(void)

  {

   Comment(__FUNCTION__);

   if(m_auto_close_button_buys.Pressed())

     {

      m_auto_close_editkvn_buys.ReadOnly(true);

      m_auto_close_editkvn_buys.Color(C'0xAD,0xAD,0xAD');

      m_auto_close_editkvn_buys.ColorBackground(C'0xEB,0xEB,0xEB');

     }

   else

     {

      m_auto_close_editkvn_buys.ReadOnly(false);

      m_auto_close_editkvn_buys.Color(clrBlack);

      m_auto_close_editkvn_buys.ColorBackground(clrWhite);

     }

  }

//+------------------------------------------------------------------+

//| Event handler                                                    |

//+------------------------------------------------------------------+

void CControlsDialog::OnClickAutoCloseButtonSells(void)

  {

   Comment(__FUNCTION__);

   if(m_auto_close_button_sells.Pressed())

     {

      m_auto_close_editkvn_sells.ReadOnly(true);

      m_auto_close_editkvn_sells.Color(C'0xAD,0xAD,0xAD');

      m_auto_close_editkvn_sells.ColorBackground(C'0xEB,0xEB,0xEB');

     }

   else

     {

      m_auto_close_editkvn_sells.ReadOnly(false);

      m_auto_close_editkvn_sells.Color(clrBlack);

      m_auto_close_editkvn_sells.ColorBackground(clrWhite);

     }

  }

//+------------------------------------------------------------------+

//| Event handler                                                    |

//+------------------------------------------------------------------+

void CControlsDialog::OnClickAutoCloseButtonAll(void)

  {

   Comment(__FUNCTION__);

   if(m_auto_close_button_all.Pressed())

     {

      m_auto_close_editkvn_all.ReadOnly(true);

      m_auto_close_editkvn_all.Color(C'0xAD,0xAD,0xAD');

      m_auto_close_editkvn_all.ColorBackground(C'0xEB,0xEB,0xEB');

     }

   else

     {

      m_auto_close_editkvn_all.ReadOnly(false);

      m_auto_close_editkvn_all.Color(clrBlack);

      m_auto_close_editkvn_all.ColorBackground(clrWhite);

     }

  }

//+------------------------------------------------------------------+

//| Event handler                                                    |

//+------------------------------------------------------------------+

void CControlsDialog::OnClickGridButtonBuy(void)

  {

   Comment(__FUNCTION__);

   if(m_grid_button_buy.Pressed())

     {

      double lot=LotCheck(ValueGridEditKVNLotBuy(),m_symbol);

      if(lot==0.0)

         return;

      m_grid_editkvn_lot_buy.ReadOnly(true);

      m_grid_editkvn_lot_buy.Color(C'0xAD,0xAD,0xAD');

      m_grid_editkvn_lot_buy.ColorBackground(C'0xEB,0xEB,0xEB');

      m_grid_editkvn_step_buy.ReadOnly(true);

      m_grid_editkvn_step_buy.Color(C'0xAD,0xAD,0xAD');

      m_grid_editkvn_step_buy.ColorBackground(C'0xEB,0xEB,0xEB');

      int size_need_position=ArraySize(SPosition);

      ArrayResize(SPosition,size_need_position+1);

      SPosition[size_need_position].pos_type=POSITION_TYPE_BUY;

      SPosition[size_need_position].volume=lot;

      if(InpPrintLog)

         Print(__FILE__," ",__FUNCTION__,", OK: ","Signal BUY");

     }

   else

     {

      m_grid_editkvn_lot_buy.ReadOnly(false);

      m_grid_editkvn_lot_buy.Color(clrBlack);

      m_grid_editkvn_lot_buy.ColorBackground(clrWhite);

      m_grid_editkvn_step_buy.ReadOnly(false);

      m_grid_editkvn_step_buy.Color(clrBlack);

      m_grid_editkvn_step_buy.ColorBackground(clrWhite);

     }

  }

//+------------------------------------------------------------------+

//| Event handler                                                    |

//+------------------------------------------------------------------+

void CControlsDialog::OnClickGridButtonSell(void)

  {

   Comment(__FUNCTION__);

   if(m_grid_button_sell.Pressed())

     {

      double lot=LotCheck(ValueGridEditKVNLotSell(),m_symbol);

      if(lot==0.0)

         return;

      m_grid_editkvn_lot_sell.ReadOnly(true);

      m_grid_editkvn_lot_sell.Color(C'0xAD,0xAD,0xAD');

      m_grid_editkvn_lot_sell.ColorBackground(C'0xEB,0xEB,0xEB');

      m_grid_editkvn_step_sell.ReadOnly(true);

      m_grid_editkvn_step_sell.Color(C'0xAD,0xAD,0xAD');

      m_grid_editkvn_step_sell.ColorBackground(C'0xEB,0xEB,0xEB');

      int size_need_position=ArraySize(SPosition);

      ArrayResize(SPosition,size_need_position+1);

      SPosition[size_need_position].pos_type=POSITION_TYPE_SELL;

      SPosition[size_need_position].volume=lot;

      if(InpPrintLog)

         Print(__FILE__," ",__FUNCTION__,", OK: ","Signal SELL");

     }

   else

     {

      m_grid_editkvn_lot_sell.ReadOnly(false);

      m_grid_editkvn_lot_sell.Color(clrBlack);

      m_grid_editkvn_lot_sell.ColorBackground(clrWhite);

      m_grid_editkvn_step_sell.ReadOnly(false);

      m_grid_editkvn_step_sell.Color(clrBlack);

      m_grid_editkvn_step_sell.ColorBackground(clrWhite);

     }

  }

//+------------------------------------------------------------------+

//| Refresh Labels Money                                             |

//+------------------------------------------------------------------+

void CControlsDialog::RefreshLabelsMoney(void)

  {

   m_mony_label_balance_equity.Text(StringFormat("%-13s","Balance: ")+StringFormat("%-12s",DoubleToString(m_account.Balance(),2))+

                                    StringFormat("%-13s","Equity: ")+StringFormat("%-12s",DoubleToString(m_account.Equity(),2)));

   m_mony_label_margin_free_margin.Text(StringFormat("%-13s","Margin: ")+StringFormat("%-12s",DoubleToString(m_account.Margin(),2))+

                                        StringFormat("%-13s","Free Margin: ")+StringFormat("%-12s",DoubleToString(m_account.FreeMargin(),2)));

   double profit_buys=0.0;

   double profit_sells=0.0;

   ProfitAllPositions(profit_buys,profit_sells);

   m_manual_close_button_buys.Text("Close Buys"+" ("+DoubleToString(profit_buys,2)+")");

   m_manual_close_button_sells.Text("Close Sells"+" ("+DoubleToString(profit_sells,2)+")");

  }

//+------------------------------------------------------------------+

//| Global Variables                                                 |

//+------------------------------------------------------------------+

CControlsDialog ExtDialog;

//--- input parameters

input ulong    InpDeviation         = 10;          // Deviation, in points (1.00045-1.00055=10 points)

input bool     InpPrintLog          = false;       // Print log

input ulong    InpMagic             = 56775160;    // Magic number

//---

double   m_step_buy              = 0.0;      //

double   m_step_sell             = 0.0;      //



double   m_adjusted_point;                   // point value adjusted for 3 or 5 points



bool     m_need_close_buys       = false;    // need close all buy positions

bool     m_need_close_sells      = false;    // need close all sell positions

bool     m_need_close_all        = false;    // needclose all positions



double   m_last_deal_in_buy      = 0.0;      //

double   m_last_deal_in_sell     = 0.0;      //

//--- the tactic is this: for positions we strictly monitor the result ***

//+------------------------------------------------------------------+

//| Structure Positions                                              |

//+------------------------------------------------------------------+

struct STRUCT_POSITION

  {

   ENUM_POSITION_TYPE pos_type;              // position type

   double            volume;                 // position volume (if "0.0" -> the lot is "Money management")

   bool              waiting_transaction;    // waiting transaction, "true" -> it's forbidden to trade, we expect a transaction

   ulong             waiting_order_ticket;   // waiting order ticket, ticket of the expected order

   bool              transaction_confirmed;  // transaction confirmed, "true" -> transaction confirmed

   //--- Constructor

                     STRUCT_POSITION()

     {

      pos_type                   = WRONG_VALUE;

      volume                     = 0.0;

      waiting_transaction        = false;

      waiting_order_ticket       = 0;

      transaction_confirmed      = false;

     }

  };

STRUCT_POSITION SPosition[];

//+------------------------------------------------------------------+

//| Expert initialization function                                   |

//+------------------------------------------------------------------+

int OnInit()

  {

//--- create application dialog

   if(!ExtDialog.Create(0,"Grid Semiautomat Panel",0,40,40,431,287))

      return(INIT_FAILED);

//--- init panel

   int init_panel=ExtDialog.OnInitPanel();

   if(init_panel!=INIT_SUCCEEDED)

      return(init_panel);

//--- run application

   ExtDialog.Run();

//--- succeed

   return(INIT_SUCCEEDED);

  }

//+------------------------------------------------------------------+

//| Expert deinitialization function                                 |

//+------------------------------------------------------------------+

void OnDeinit(const int reason)

  {

   ExtDialog.OnDeinitPanel(reason);

//--- destroy dialog

   ExtDialog.Destroy(reason);

  }

//+------------------------------------------------------------------+

//| Return a textual description of the deinitialization reason code |

//+------------------------------------------------------------------+

string getUninitReasonText(int reasonCode)

  {

   string text="";

//---

   switch(reasonCode)

     {

      case REASON_PROGRAM:

         text="The EA "+__FILE__+" has stopped working calling the ExpertRemove() function";

         break;

      case REASON_REMOVE:

         text="Program "+__FILE__+" was removed from chart";

         break;

      case REASON_RECOMPILE:

         text="Program "+__FILE__+" was recompiled";

         break;

      case REASON_CHARTCHANGE:

         text="Symbol or timeframe was changed";

         break;

      case REASON_CHARTCLOSE:

         text="Chart was closed";

         break;

      case REASON_PARAMETERS:

         text="Input-parameter was changed";

         break;

      case REASON_ACCOUNT:

         text="Account was changed";

         break;

      case REASON_TEMPLATE:

         text="New template was applied to chart";

         break;

      case REASON_INITFAILED:

         text="The OnInit() handler returned a non-zero value";

         break;

      case REASON_CLOSE:

         text="Terminal closed";

         break;

      default:

         text="Another reason";

     }

//---

   return(text);

  }

//+------------------------------------------------------------------+

//| Expert tick function                                             |

//+------------------------------------------------------------------+

void OnTick()

  {

   ExtDialog.OnTickPanel();

  }

//+------------------------------------------------------------------+

//| Expert chart event function                                      |

//+------------------------------------------------------------------+

void OnChartEvent(const int id,         // event ID

                  const long& lparam,   // event parameter of the long type

                  const double& dparam, // event parameter of the double type

                  const string& sparam) // event parameter of the string type

  {

   ExtDialog.ChartEvent(id,lparam,dparam,sparam);

  }

//+------------------------------------------------------------------+

//| TradeTransaction function                                        |

//+------------------------------------------------------------------+

void OnTradeTransaction(const MqlTradeTransaction &trans,

                        const MqlTradeRequest &request,

                        const MqlTradeResult &result)

  {

   ExtDialog.OnTradeTransactionPanel(trans,request,result);

  }

//+------------------------------------------------------------------+

Comments