Любой вопрос новичка, чтоб не захламлять форум. Профи, не проходите мимо. Без вас никуда - 6. - страница 388

 
gyfto:

Пытаюсь организовать тик для эксперта, - нихрена не выходит. Выходные врасплох застали. Как его правильно организовывать? Вот например имеем следующий элементарный эксперт:

- как сэмулировать тики и запустить таймер?

Я понимаю, что выходные, но на рынке расписание праздников не совпадает с теми же по РФ, да и работать-таки надо...

Библиотека.

 //=================================================================================================================================================
 // 4.7. Функции для управления обновлением графика.
 //=================================================================================================================================================
 // 4.7.1. Функция запускает обновление всех графиков с указанным периодом. Если обновление уже запущено, то функция меняет период обновления графиков.
 //        Останавливается обновление функциями "ServiceStopRefreshChart()" или "ServiceStopRefreshAllCharts()" или закрытием графика.
 void ServiceRefreshAllCharts(int nPeriodMilliSec); // Период обновления графика в миллисекундах.
 //=================================================================================================================================================
 // 4.7.2. Функция запускает обновление всех графиков однократно. Вызов функции при работающих других режимах останавливает обновление всех графиков.
 void ServiceRefreshAllOnceCharts();
 //=================================================================================================================================================
 // 4.7.3. Функция запускает обновление указанного графика с указанным периодом. Если обновление уже запущено, то функция меняет только период обновления графика.
 //        Останавливается обновление функциями "ServiceStopRefreshChart()" или "ServiceStopRefreshAllCharts()" или закрытием графика.
 void ServiceRefreshChart(int hwndChart,        // Системный дескриптор обновляемого графика.
                          int nPeriodMilliSec); // Период обновления графика в миллисекундах.
 //=================================================================================================================================================
 // 4.7.4. Функция запускает обновление автономных графиков с указанным периодом. Если обновление уже запущено, то функция меняет период обновления графиков.
 //        Останавливается обновление функциями "ServiceStopRefreshChart()" или "ServiceStopRefreshAllCharts()" или закрытием графика.
 void ServiceRefreshOfflineCharts(int nPeriodMilliSec); // Период обновления графика в миллисекундах.
 //=================================================================================================================================================
 // 4.7.5. Функция запускает обновление online-графиков с указанным периодом. Если обновление уже запущено, то функция меняет период обновления графиков.
 //        Останавливается обновление функциями "ServiceStopRefreshChart()" или "ServiceStopRefreshAllCharts()" или закрытием графика.
 void ServiceRefreshOnlineCharts(int nPeriodMilliSec); // Период обновления графика в миллисекундах.
 //=================================================================================================================================================
 // 4.7.6. Функция останавливает обновление указанного графика.
 void ServiceStopRefreshChart(int hwndChart); // Системный дескриптор графика, на котором останавливается обновление.
 //=================================================================================================================================================
 // 4.7.7. Функция корректно останавливает обновление всех графиков при bTerminate = FALSE, иначе функция завершает обновление аварийно.
 void ServiceStopRefreshAllCharts(int bTerminate); // Флаг аварийной остановки потоков обновления графиков.
                                                   // FALSE - потоки останавливаются корректно, TRUE - потоки останавливаются аварийно.
 //=================================================================================================================================================
 // 4.7.8. Функция эммулирует тик для эксперта на указанном графике.
 void ServiceTickExpert(int hwndChart); // Системный дескриптор окна графика, для эмуляции тика для эксперта.
 //=================================================================================================================================================
 // 4.7.9. Функция эммулирует тик для индикаторов на указанном графике.
 void ServiceTickIndicators(int hwndChart); // Системный дескриптор окна графика, для эмуляции тика для индикаторов.
 //=================================================================================================================================================
 
Zhunko:

Библиотека.


Именно ServiceTickExpert() я пытался использовать перед тем, как обратиться на форум. Попытался сейчас запустить тестовый эксперт

#import "ServicesMT4.dll"
   void ServiceTickExpert(int hwndChart);
   void ServiceRefreshChart(int hwndChart, int nPeriodMilliSec);
#import
int delay = 180;
datetime read_now;
int init(){
   read_now = TimeCurrent() + delay;
}
int start(){
   int hWnd = WindowHandle(Symbol(), Period());
   ServiceTickExpert(hWnd);
   ServiceRefreshChart(hWnd, 500);
   int how_many_remains = read_now - TimeCurrent();
   Comment(StringConcatenate(
      StringSubstr("-", (how_many_remains%60 >= 0), 0),
      StringSubstr("0", (MathAbs(how_many_remains/60) > 9), 0),
      MathAbs(how_many_remains/60),
      ":",
      StringSubstr("0", (MathAbs(how_many_remains%60) > 9), 0),
      MathAbs(how_many_remains%60)
   ));
   return(0);
}

- но тишина.

 
Link_x:
Главное - что бы они отображались. :)

Делаем так и запредельные значения испаряются, а проблема остается.

Думается мне, проблема в этой строке:

R_time        = Seconds() * Minute() * Hour(); 

Все значения на одно и то же время умножаются - текущее время сервера, а точнее - последнее известное время.

А также в обьявлении переменных типа bool там где он должны быть double, ну и пара других мелких косяков. Букварь ещё не скурен до конца, как я понимаю )))

#property indicator_separate_window
#property indicator_buffers 3
#property indicator_color1 Gold
#property indicator_color2 Gold
#property indicator_color3 Gold
//+---------------------------------------------------------------------+
extern double _N_ = 1; 
extern double _M_ = -1; 
extern int History = 10000; //многовато, а вдруг столько на графике нету? Проверка нужна...
//+---------------------------------------------------------------------+
int p; 
//+---------------------------------------------------------------------+
double Buf_0[];
double Buf_1[];
double Buf_2[];
double RSI;
double ADX_Main; 
double ADX_dD;
double ADX_DD;
double price;
//+---------------------------------------------------------------------+  5 переменных ниже были обьявлены как bool, непонятно только с какого перепугу
double R_adx; 
double R_time;
double R_adx_time;
double R_rsi_time;
double R_rrsi_time;
//+---------------------------------------------------------------------+
int init()
{
//+---------------------------------------------------------------------+  
SetIndexBuffer(0,Buf_0);
SetIndexStyle(0,DRAW_LINE);
//+---------------------------------------------------------------------+  
SetIndexBuffer(1,Buf_1);
SetIndexStyle(1,DRAW_LINE);
//+---------------------------------------------------------------------+  
SetIndexBuffer(2,Buf_2);
SetIndexStyle(2,DRAW_LINE);
//+---------------------------------------------------------------------+  
return(0);
}
//+---------------------------------------------------------------------+
int start()
{
//+---------------------------------------------------------------------+  
for(
p=0;
p<History;
p++)
{
//+---------------------------------------------------------------------+  
//price = Bid;
//+---------------------------------------------------------------------+  
ADX_Main    = iADX(Symbol(),0,14,0,0,p);
ADX_dD      = iADX(Symbol(),0,14,0,1,p);
ADX_DD      = iADX(Symbol(),0,14,0,2,p);
RSI         = iRSI(Symbol(),0,14,0,p);
//+---------------------------------------------------------------------+  
R_adx         = (ADX_DD - ADX_dD) * ADX_Main; 
string R_time1        = TimeToString(Time[p],TIME_SECONDS); //Время отркытия свечи р
R_time        = StringToDouble(R_time1); 
//+---------------------------------------------------------------------+  
R_adx_time    = _N_ * (R_time + R_adx);
R_rsi_time    = _N_ * (R_time + RSI);
R_rrsi_time   = _M_ * (R_time + RSI);
//+---------------------------------------------------------------------+  
Buf_0[p] = R_adx_time;
Buf_1[p] = R_rsi_time;
Buf_2[p] = R_rrsi_time;
//+---------------------------------------------------------------------+  
}
return(0); //эта строка была чуть  выше чем надо :)
}
//+-------------------
 
evillive:

Думается мне, проблема в этой строке:

Все значения на одно и то же время умножаются - текущее время сервера, а точнее - последнее известное время.

А также в обьявлении переменных типа bool там где он должны быть double, ну и пара других мелких косяков. Букварь ещё не скурен до конца, как я понимаю )))


Ох, спасибо!
Мне понятны ошибки и залеты.
Вообще не представляю, как я такое мог набрать? :)

Заметил, что индикатор рисует картины, которые я себе даже не представлял.
Немного поработал над "телом" кода.
R_adx           = (ADX_DD - ADX_dD) * ADX_Main; 
string R_time_1 = TimeToStr(Time[p],TIME_SECONDS);
R_time          = StrToDouble(R_time_1); 
string T_time_1 = TimeToStr(Time[p],TIME_MINUTES);
T_time          = StrToDouble(T_time_1);
string B_time_1 = TimeToStr(Time[p],TIME_DATE);
B_time          = StrToDouble(B_time_1);
A_time          = R_time * T_time * B_time;
Уже больше похоже на то, что я себе представлял.
Но "временные волны" полностью гасят "ценовые волны". Усиливаем "ценовые волны" и ослабляем "временные волны".
R_rsi_time    = _N_ * (A_time + (RSI * 2000)) / 1.9;
A_time          = R_time * T_time * B_time / 4;
R_adx           = ((ADX_DD - ADX_dD) * ADX_Main) * 40; 
 
gyfto:


Именно ServiceTickExpert() я пытался использовать перед тем, как обратиться на форум. Попытался сейчас запустить тестовый эксперт

- но тишина.

Это нерабочий код. Может, всё же, в скрипт с примерами загляните?

Есть 3 способа обновлять график.

1. Самому организовать бесконечный цикл в старте эксперта. Необходим однократный запуск эксперта из инита или удалённой программы.
2. Запустить обновление из другого потока. Тогда любой эксперт, не зависимо от его кода, будет исполняться.

3. Похоже на п. 2, всё тоже, но с помощью системного таймера.

В библиотеке первые 2 реализованы. То, что у Вас в коде, требует самостоятельной организации цикла обновления графика или зацикленности эксперта. В первом случае требуется зацикленный скрипт. Во втором случае надо один раз стартануть эксперт.

Первые 7 функций из того раздела (4.7) организуют обновление и управляют независимым обновлением графика в отдельном потоке. Можно один раз запустить и выгрузить программу. Графики будут продолжать обновляться без MQL-программ.

#include <ServicesMT4.mqh>

int delay = 180;
datetime read_now;
int hWnd = 0;

void init()
 {
  read_now = TimeCurrent() + delay;
  hWnd = WindowHandle(Symbol(), Period());
  ServiceRefreshChart(hWnd, 500);
 }
void deinit()
 {
  ServiceStopRefreshChart(hWnd);
 }
void start()
 {
  int how_many_remains = TimeLocal() - read_now;
  Comment(StringConcatenate(StringSubstr("-", (how_many_remains%60 >= 0), 0),
                            StringSubstr("0", (MathAbs(how_many_remains/60) > 9), 0),
                            MathAbs(how_many_remains/60), ":",
                            StringSubstr("0", (MathAbs(how_many_remains%60) > 9), 0),
                            MathAbs(how_many_remains%60)));
 }
 
Link_x:

Ох, спасибо!
Мне понятны ошибки и залеты.
Вообще не представляю, как я такое мог набрать? :)

Заметил, что индикатор рисует картины, которые я себе даже не представлял.
Немного поработал над "телом" кода.
Уже больше похоже на то, что я себе представлял.
Но "временные волны" полностью гасят "ценовые волны". Усиливаем "ценовые волны" и ослабляем "временные волны".


Можно узнать что это такое страшное

R_adx           = (ADX_DD - ADX_dD) * ADX_Main; 
string R_time_1 = TimeToStr(Time[p],TIME_SECONDS);
R_time          = StrToDouble(R_time_1); 
string T_time_1 = TimeToStr(Time[p],TIME_MINUTES);
T_time          = StrToDouble(T_time_1);
string B_time_1 = TimeToStr(Time[p],TIME_DATE);
B_time          = StrToDouble(B_time_1);
A_time          = R_time * T_time * B_time;
 
Zhunko:
Может, всё же, в скрипт с примерами загляните? Это нерабочий код.


Но... но я именно по вашему скрипту и модифицировал сначала известный скрипт iTicks! Вот, сейчас опять запустил, сначала тестовый эксперт (код его на предыдущей странице, не на этой), затем iTicks следующей модификации:

#include <ServicesMT4.mqh>
extern int  delay_MSecond = 2000;
int start(){
   while(!IsStopped()){
      string _symbol = Symbol(); int _period = Period();
      int hWnd = WindowHandle(_symbol, _period);
      ServiceTickExpert(hWnd);
      Sleep(delay_MSecond);
   }
   return(0);
}

по образцу кода из Check_ServicesMT4.dll.mq4

if (TickExpert) while (!IsStopped()) {ServiceTickExpert(hwndChart); Sleep(1000);}

На чарте без изменений

Галочка "разрешить вызов dll" стоит...

Добавлено

Zhunko:

Есть 3 способа обновлять график.

Я отвечал на старую версию сообщения, прошу пардону, щас буду разбираться...
 

gyfto, пример в тестовом скрипт сделан для обновления графика, на который настроился. Можно настроить на удалённый (чужой) график.

Это же очевидно, что обновлять график для скрипта бессмысленно.

Настройте его на график с Вашим экспертом. Эксперт будет работать.

#include <ServicesMT4.mqh>

int hWnd = 0;

void init()
 {
  hWnd = WindowHandle(Symbol(), Period());
  ServiceRefreshChart(hWnd, 500);
 }
void deinit()
 {
  ServiceStopRefreshChart(hWnd);
 }
void start()
 {
  Comment(TimeToStr(TimeLocal(), TIME_DATE|TIME_SECONDS));
 }
 

Блин, вот я дурак. Я понял свою ошибку. Ключевое слово

void start()
 {
  Comment(TimeToStr(TimeLocal(), TIME_DATE|TIME_SECONDS));
 }

А у меня было

int init(){
   read_now = TimeCurrent() + delay;
}

и так далее, которое при запуске было константой (2013.12.31 18:59:59). Вот так невнимательность и подводит... Прошу прощения за беспокойство, теперь всё понятно.

Вот этот код действительно рабочий:

int delay = 180;
datetime read_now;
int init(){
   read_now = TimeLocal() + delay;
   start();
}
int start(){
   while(!IsStopped()){
      int how_many_remains = read_now - TimeLocal();
      Comment(StringConcatenate(
         StringSubstr("-", (how_many_remains%60 >= 0), 0),
         StringSubstr("0", (MathAbs(how_many_remains/60) > 9), 0),
         MathAbs(how_many_remains/60),
         ":",
         StringSubstr("0", (MathAbs(how_many_remains%60) > 9), 0),
         MathAbs(how_many_remains%60)
      ));
      Sleep(1000);
   }
   return(0);
}

Естественно, он только для выходных. Ещё раз прошу прощения за беспокойство.

 

Так неприлично. Надо так:

#include <ServicesMT4.mqh>

int delay = 180;
datetime read_now;
int hWnd = 0;

void init()
 {
  read_now = TimeLocal() + delay;
  hWnd = WindowHandle(Symbol(), Period());
  ServiceRefreshChart(hWnd, 100);
 }
void start()
 {
  ServiceStopRefreshChart(hWnd);
  while(!IsStopped())
   {
    int how_many_remains = read_now - TimeLocal();
    Comment(StringConcatenate(StringSubstr("-", (how_many_remains%60 >= 0), 0),
                              StringSubstr("0", (MathAbs(how_many_remains/60) > 9), 0),
                              MathAbs(how_many_remains/60), ":",
                              StringSubstr("0", (MathAbs(how_many_remains%60) > 9), 0),
                              MathAbs(how_many_remains%60)));
    Sleep(1000);
   }
 }
Причина обращения: