Странности индикатора?

 

В программировании не новичек...

Столкнулся после написания индикатора со следующим:

Если кинуть индикатор на граффик все работает и отображается правильно.

После перезагрузки терминала линии индикатора не отображаются.

Если поменять таймфрейм, появляются линии. Но при возврате на исходный тф.  отображаются с ошибками и приходят в норму

только после "Сброс" .

Сразу Сброс не помогает, Обновить тоже...

Программное обновление не помогает... 

Пробовал на разных билдах .... одинаково...

Код проверен сотню раз... (да там и проверять нечего пара десятков строк)

-==-

Может кто сталкивался с таким..., подскажите... в чем фишка...?

PS:

...бары перебирал и назад в вперед... не помогает. 

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

 
используются несколько индикаторных буферов? Не отображается вообще ничего или просто черным цветом на черном фоне?
 
ViDan888:

В программировании не новичек...


Надо бы код посмотреть
 

Скорей всего, нет переинициализации стат. переменных.

Хотя...))) без кода - довольно странное занятие - это обсуждение...)))

 

...вроде ставил галку - Следить за темой...

--==--

Ну коль ответы есть..., салбыть и интерес к явлению..., вот код:

--==--

//+------------------------------------------------------------------+
//| i_Go55.mq4 |
//| ViDan |
//| vi_dancom@mail.ru |
//+------------------------------------------------------------------+
#property copyright "ViDan"
#property link "vi_dancom@mail.ru"

#property indicator_separate_window
#property indicator_buffers 1
#property indicator_color1 Lime
#property indicator_level1 20
#property indicator_level2 -20
#property indicator_levelcolor Green
#property indicator_minimum -200
#property indicator_maximum 200
double Buffer1[];
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init()
{
SetIndexStyle(0, DRAW_LINE);
SetIndexBuffer(0, Buffer1);
SetIndexEmptyValue(0, 0.0);
//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+
int deinit()
{
//----

//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
int start()
{
int limit, i;
int counted_bars=IndicatorCounted();
if(counted_bars<0) return(-1);
//---- last counted bar will be recounted
if(counted_bars>0) counted_bars--;
limit=Bars-counted_bars;
//if(limit == 0) limit = 1;
//----
for(i=0; i<=limit; i++)
//for(i=limit; i>=0; i--)
{
Buffer1[i] = 0.0;
double d_degRi = d_Degry(Period(),55, 3, 1, i)+d_Degry(Period(),89, 3, 1, i);
Buffer1[i] = d_degRi;
//WindowRedraw();
}
//----
return(0);
}
//+------------------------------------------------------------------+
////////////////////Расчет градуса наклона МА по 2м барам начало = i_shift отстоящих на i_delta
double d_Degry(int i_tf,int i_ma, int i_mode, int i_delta, int i_shift)
{
double d_tng;
double d_vrInt;
double d_tng0 = iMA(NULL,i_tf,i_ma,0,i_mode,PRICE_CLOSE,i_shift)-iMA(NULL,i_tf,i_ma,0,i_mode,PRICE_CLOSE,i_shift+i_delta);
double d_ktng = (WindowPriceMax(0)-WindowPriceMin(0))/WindowBarsPerChart();
d_ktng =(d_ktng*(1/Point));
d_tng = (d_tng0*(1/Point))/d_ktng;
d_vrInt=MathArctan(d_tng)* (180 / 3.14159265358979);
return (d_vrInt) ;
}
//+------------------------------------------------------------------+
 

 

Дело в странностях работы функции WindowBarsPerChart() и родственников из этой группы.

При старте терминала происходит инициализация и расчет индикатора. Так вот, во время этого расчета, функция WindowBarsPerChart() возвращает значение 0. Соответственно, происходит деление на ноль. Индикатор вырубается.

Можно подправить, чтобы индикатор пересчитывался при приходе первого тика. Но, если нет связи, непонятно как решать эту проблему.

Ниже даю вариант.

//+------------------------------------------------------------------+
//| i_Go55.mq4 |
//| ViDan |
//| vi_dancom@mail.ru |
//+------------------------------------------------------------------+
#property copyright "ViDan"
#property link "vi_dancom@mail.ru"

#property indicator_separate_window
#property indicator_buffers 1
#property indicator_color1 Lime
#property indicator_level1 20
#property indicator_level2 -20
#property indicator_levelcolor Green
#property indicator_minimum -200
#property indicator_maximum 200
double Buffer1[];
int RunCount;  // добавлена переменная
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init()
{
SetIndexStyle(0, DRAW_LINE);
SetIndexBuffer(0, Buffer1);
//SetIndexEmptyValue(0, 0.0);
//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+
int deinit()
{
//----

//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
int start()
{

int counted_bars=IndicatorCounted();
int limit, i;
if(counted_bars<0) return(-1);
//---- last counted bar will be recounted
if(counted_bars>0) counted_bars--;
limit=Bars-counted_bars; 
RunCount++; // при приходе первого тика пересчитываем полностью индикатор
if (RunCount == 2) limit = MathMax(0, Bars - 55);

//if(limit == 0) limit = 1;
//----
for(i=0; i<limit; i++) 
//for(i=limit; i>=0; i--) 
{
Buffer1[i] = 0.0;
double d_degRi = d_Degry(Period(),55, 3, 1, i)+d_Degry(Period(),89, 3, 1, i);
Buffer1[i] = d_degRi;
//WindowRedraw();
}
//----
return(0);
}
//+------------------------------------------------------------------+
////////////////////Расчет градуса наклона МА по 2м барам начало = i_shift отстоящих на i_delta
double d_Degry(int i_tf,int i_ma, int i_mode, int i_delta, int i_shift)
{
if (WindowBarsPerChart() == 0) return(0); // уходим от деления на ноль
double d_tng;
double d_vrInt;
double d_tng0 = iMA(NULL,i_tf,i_ma,0,i_mode,PRICE_CLOSE,i_shift)-iMA(NULL,i_tf,i_ma,0,i_mode,PRICE_CLOSE,i_shift+i_delta);
double d_ktng = (WindowPriceMax()-WindowPriceMin())/WindowBarsPerChart();
d_ktng =(d_ktng*(1/Point));
d_tng = (d_tng0*(1/Point))/d_ktng;
d_vrInt=MathArctan(d_tng)* (180. / 3.14159265358979);
return (d_vrInt) ;
}
//+------------------------------------------------------------------+
 

Mislaid - Спасибо!

...Однако, неплохо бы метаквотесам документировать такие особенности работы функций.

Нда, в несессионный день работать не будет... 

 
ViDan888:

Mislaid - Спасибо!

...Однако, неплохо бы метаквотесам документировать такие особенности работы функций.

Нда, в несессионный день работать не будет...

Почему, можно обновить индикатор. При запущенном терминале все работает
 

...Кстати..., в скриптах функции этой группы работают правильно...

Считаю сей факт "косяком"  в MQL4 ... и весьма неприятным .

Хорошо бы пофиксить... 

 
Mislaid:
Почему, можно обновить индикатор. При запущенном терминале все работает


...ну..., это понятно.
Причина обращения: