Errors, bugs, questions - page 1622

 
fxsaber:
It seems to be about the sometimes unclosed windows from visual testing. I can't reproduce it, though. It's working now.

Have you been testing or optimising? If the latter, there are indeed problems with this.

 
Karputov Vladimir:

Here is the script that brings up the "File" menu - item "Connect to trading account" - click on the "OK" button - thus the terminal will connect to the last trading account that was authored:

#ifndef  _IsX64
#define  HWND long
#define  HMENU long
#define  HBITMAP long
#define  ULONG_PTR long
#else
#define  HWND int
#define  HMENU int
#define  HBITMAP int
#define  ULONG_PTR int
#endif

_IsX64 cannot be used in this way. It is only relevant at runtime.

 
Alexey Navoykov:

Have you been testing or optimising? If the latter, there are indeed problems with this.

Single runs, I did not include optimisation.
 
Koldun Zloy:

_IsX64 cannot be used in this way. It only matters at runtime.

Thanks for the tip. Corrected it and made it as a include file:

//+------------------------------------------------------------------+
//|                                          LoginToTradeAccount.mqh |
//|                              Copyright © 2016, Vladimir Karputov |
//|                                           http://wmua.ru/slesar/ |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2016, Vladimir Karputov"
#property link      "http://wmua.ru/slesar/"
#property version   "1.00"
#property description "Library for clicks on the MetaTrader 5 menu \"File\" item \"Login to trading account\""
#property description "Библиотека для кликов по меню MetaTrader 5 \"Файл\" пункт \"Подключиться к торговому счёту\""

int number_menu=1;   //menu "File"; меню "Файл"
int item_menu=14;    //item "Login to trading account"; пункт "Подключиться к торговому счёту"

#define  GA_ROOT            0x00000002  // Retrieves the root window by walking the chain of parent windows
#define  WM_COMMAND         0x00000111
#define  BM_CLICK           0x000000F5

#import "user32.dll"
int  GetLastError();
//+------------------------------------------------------------------+
//| GetAncestor. Retrieves the handle to the ancestor of the         |
//| specified window. Возвращает хендл предка заданного окна         |
//+------------------------------------------------------------------+
//--- x64
long  GetAncestor(long hwnd,int gaFlags);
//--- x86
int  GetAncestor(int hwnd,int gaFlags);
//+------------------------------------------------------------------+
//| GetMenu. Retrieves a handle to the menu assigned to the          |
//| specified window. Возвращает хендл меню,                         |
//| назначенного указанному окну.                                    |
//+------------------------------------------------------------------+
//--- x64
long GetMenu(long hWnd);
//--- x86
int GetMenu(int hWnd);
//+------------------------------------------------------------------+
//| GetSubMenu. Retrieves a handle to the drop-down menu or submenu  |
//| activated by the specified menu item. Возвращает хендл           |
//| выпадающего меню или подменю указанного пункта меню.             |
//+------------------------------------------------------------------+
//--- x64
long GetSubMenu(long hMenu,int nPos);
//--- x86
int GetSubMenu(int hMenu,int nPos);
//+------------------------------------------------------------------+
//| GetMenuItemID. Retrieves the menu item identifier of a menu item |
//| located at the specified position in a menu. Возвращает          |
//| идентификатор пункта меню, расположенного в                      |
//| указанной позиции в меню.                                        |
//+------------------------------------------------------------------+
//--- x64
int   GetMenuItemID(long hMenu,int nPos);
//--- x86
int   GetMenuItemID(int hMenu,int nPos);
//+------------------------------------------------------------------+
//| PostMessageW. Places (posts) a message in the message queue      |
//| associated with the thread that created the specified window     |
//| and returns without waiting for the thread to process the        |
//| message. Размещает (публикует) сообщение в очереди сообщений,    |
//| связанной с потоком, который создал указанное окно и             |
//| возвращается, не дожидаясь потока, чтобы обработать сообщение.   |
//+------------------------------------------------------------------+
//--- x64
bool  PostMessageW(long hWnd,int Msg,int wParam,int lParam);
//--- x86
bool  PostMessageW(int hWnd,int Msg,int wParam,int lParam);
//+------------------------------------------------------------------+
//| GetLastActivePopup. Determines which pop-up window owned by the  |
//| specified window was most recently active. Определяет, какое     |
//| всплывающее окно, принадлежащие указанному окну, совсем недавно  |
//| было активным.                                                   |
//+------------------------------------------------------------------+
//--- x64
long  GetLastActivePopup(long hWnd);
//--- x86
int  GetLastActivePopup(int hWnd);
//+------------------------------------------------------------------+
//| GetDlgItem. Retrieves a handle to a control in the specified     |
//| dialog box. Возвращает хэндл элемента управления в               |
//| указанном диалоговом окне.                                       |
//+------------------------------------------------------------------+
//--- x64
long  GetDlgItem(long hDlg,int nIDDlgItem);
//--- x86
int  GetDlgItem(int hDlg,int nIDDlgItem);
#import
//+------------------------------------------------------------------+
//| Click on the item "Login to trading account"                     |
//| Клик на пункте "Подключиться к торговому счёту"                  |
//+------------------------------------------------------------------+
void LoginToTradeAccount()
  {
   long mainChartID=ChartID(); //returns the ID of the current chart; возвращает идентификатор текущего графика
   int hdlmainChartID=ChartWindowsHandle(mainChartID); //returns the Chart window handle (HWND); получает хэндл графика 

   if(_IsX64)
     {
      long hdlRoot=GetAncestor((long)hdlmainChartID,GA_ROOT);
      long hmenu=GetMenu(hdlRoot);
      long hsubmenu=GetSubMenu(hmenu,number_menu);
      int hpos=GetMenuItemID(hsubmenu,item_menu);
      PostMessageW(hdlRoot,WM_COMMAND,hpos,0);
      Sleep(2000);
      long hlastPopup=GetLastActivePopup(hdlRoot);
      long hOK=GetDlgItem(hlastPopup,0x00000001);
      PostMessageW(hOK,BM_CLICK,0,0);
     }
   else
     {
      int hdlRoot=GetAncestor(hdlmainChartID,GA_ROOT);
      int hmenu=GetMenu(hdlRoot);
      int hsubmenu=GetSubMenu(hmenu,number_menu);
      int hpos=GetMenuItemID(hsubmenu,item_menu);
      PostMessageW(hdlRoot,WM_COMMAND,hpos,0);
      Sleep(2000);
      int hlastPopup=GetLastActivePopup(hdlRoot);
      int hOK=GetDlgItem(hlastPopup,0x00000001);
      PostMessageW(hOK,BM_CLICK,0,0);
     }
  }
//+------------------------------------------------------------------+
//| The function gets the handle graphics                            |
//| Функция получает хэндл графика                                   |
//+------------------------------------------------------------------+
int ChartWindowsHandle(long chart_ID)
  {
//--- prepare the variable to get the property value
//--- подготовим переменную для получения значения свойства
   long result=-1;
//--- reset the error value
//--- сбросим значение ошибки
   ResetLastError();
//--- receive the property value
//--- получим значение свойства
   if(!ChartGetInteger(chart_ID,CHART_WINDOW_HANDLE,0,result))
     {
      //--- display the error message in Experts journal
      //--- выведем сообщение об ошибке в журнал "Эксперты"
      Print(__FUNCTION__+", Error Code = ",GetLastError());
     }
//--- return the value of the chart property
//--- вернем значение свойства графика
   return((int)result);
  }
//+------------------------------------------------------------------+
Files:
 
Dmitri Custurov:
Unfortunately, not always. If there is no connection for a long time, the terminal shows "Account disable" and then you have to login manually. This happens e.g. at a fund where the servers are usually switched off at night.

Here is the solution: EA periodically checks connection status to the trade server(TERMINAL_CONNECTED) and if the returned value is "0", it calls (using WIn API) "File" menu, "Connect to trade account" item. The include file where the menu click function is implemented can be found here. Example of an EA:

//+------------------------------------------------------------------+
//|                                           TestAccountDisable.mq5 |
//|                        Copyright 2016, MetaQuotes Software Corp. |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2016, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.00"

#include <LoginToTradeAccount.mqh>
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
//--- create timer
   EventSetTimer(12);

//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
//--- destroy timer
   EventKillTimer();

  }
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {
//---

  }
//+------------------------------------------------------------------+
//| Timer function                                                   |
//+------------------------------------------------------------------+
void OnTimer()
  {
//---
   static bool cleaner=false;
   if(!cleaner)
     {
      long rezult=TerminalInfoInteger(TERMINAL_CONNECTED);
      Comment("TERMINAL_CONNECTED: ",IntegerToString(rezult));
      if(rezult==0)
         LoginToTradeAccount();
     }
   else
      Comment("");
   cleaner=!cleaner;
  }
//+------------------------------------------------------------------+

Advisor checks connection status every 12 seconds and erases comments every once in a while.

 
Is there really no define?
 

How do I connect an array file to my EA?

First, the script writes an array:

string filename="mas.dat";
int handle=FileOpen(filename,FILE_BIN|FILE_WRITE);
FileWriteArray(handle,hol,0,4608);
FileClose(handle);

I connect the file in the EA:

#include <mas.dat> 

When compiling, errors:

'??????????????????????????t????...' - identifier is too long mas.dat 1 1

'' - unknown symbol mas.dat 1 3015

 
Aliaksandr Yemialyanau:

How do I connect an array file to my EA?

First, the script writes an array:

I connect the file in the EA:

When compiling, errors:

'??????????????????????????t????...' - identifier is too long mas.dat 1 1

'' - unknown symbol mas.dat 1 3015

It's much faster to read the whole array file into memory and then work with it - it will be times faster.
 
Karputov Vladimir:

Here is the solution: EA periodically checks connection status to the trade server(TERMINAL_CONNECTED) and if the returned value is "0", it calls (using WIn API) "File" menu, "Connect to trade account" item. The include file in which the menu click function is implemented can be found here. Example of an EA:

The advisor checks the connection status every 12 seconds and erases the comments every once in a while.

Thank you very much for the solution provided. Everything is working.
 
Debugging
#define  i ii

void OnTick()
{
  for (int i = 0; i < 5; i++)
    Print(i); // отладчик по Shift+F9 показывает не ii, а i, выдавая Unknown identifier
}
Reason: