Скрипты: KeyFinder 2.0

 

KeyFinder 2.0:

Скрипт находит и размечает на графике опорные точки Демарка и указывает их размерность.

Этот скрипт по сути своей несет тот же функционал, что и KeyFinder и внешних отличий вы практически не найдете, за исключением кнопки, удаляющей скрипт и все созданные им объекты с графика.

Рис 1. График фьючерса на индекс РТС с примененным скриптом KeyFinder 2.0

Рис 1. График фьючерса на индекс РТС с примененным скриптом KeyFinder 2.0

Автор: Pavel Trofimov

 

Кнопка, удаляющая скрипт (не всегда срабатывает) остается на экране (не всегда). Терминал MT4, Alpari, bild 765


 
Смог смоделировать Вашу ситуацию. Такое поведение - результат применения следом за KeyFinder 2.0 другого скрипта. Пока не разобрался, как это победить на уровне кода. В плане использования - примените KeyFinder 2.0 повторно и кнопка снова будет "рабочей".
 
Может, разумнее сделать программу в виде индикатора, и очищать экран при удалении индикатора с графика?
 
komposter:
Может, разумнее сделать программу в виде индикатора, и очищать экран при удалении индикатора с графика?
Я работаю над индикатором. Скрипт - это "проба пера".
 
Rubick:
Смог смоделировать Вашу ситуацию. Такое поведение - результат применения следом за KeyFinder 2.0 другого скрипта. Пока не разобрался, как это победить на уровне кода. В плане использования - примените KeyFinder 2.0 повторно и кнопка снова будет "рабочей".
Пробовал победить "залипшую" на экране кнопку всякими способами. Простейший - удалить окно валютной пары и создать его вновь с чистого листа. Информация, выводимая скриптом, очень полезна. Например, в торговле использую много чего (уровни Мюррея - ТирМетод, торговые модели Третья Волна и Консолидация) и везде нужен похожий индикатор ( ZigZag, ZipPips,), а скрипт помогает оценить правильность построения фигур и соразмерность экстремумов. Будем ждать индюка. Держите нас в курсе. У вас есть страничка в какой-либо соцсети? Удачи и успехов вам!
 
ernst.yagafarof:
Пробовал победить "залипшую" на экране кнопку всякими способами. Простейший - удалить окно валютной пары и создать его вновь с чистого листа. Информация, выводимая скриптом, очень полезна. Например, в торговле использую много чего (уровни Мюррея - ТирМетод, торговые модели Третья Волна и Консолидация) и везде нужен похожий индикатор ( ZigZag, ZipPips,), а скрипт помогает оценить правильность построения фигур и соразмерность экстремумов. Будем ждать индюка. Держите нас в курсе. У вас есть страничка в какой-либо соцсети? Удачи и успехов вам!
Насчет странички в соц.сетях - обновил профиль.
 
У меня хорошие новости! Я закончил проектирование и написание класса для индикатора, сейчас пишу сам индикатор, планирую закончить на следующей неделе - как максимум, как минимум за текущие выходные.
 
Rubick:
У меня хорошие новости! Я закончил проектирование и написание класса для индикатора, сейчас пишу сам индикатор, планирую закончить на следующей неделе - как максимум, как минимум за текущие выходные.
Спасибо. Ждем-с!
 

Что вообще можно и к чему это применить?

я Ваш скрипт воткнул в Индикатор , переключаю график он всё пересчитывает .

GBPUSDH4

//+------------------------------------------------------------------+
//|                                                    KeyFinder.mq5 |
//|                                                   Trofimov Pavel |
//|                                               trofimovpp@mail.ru |
//+------------------------------------------------------------------+
#property copyright "Trofimov Pavel"
#property link      "trofimovpp@mail.ru"
#property version   "1.00"
#property description "Внимание! Данный алгоритм использует в расчетах циклы!"
#property description "Настоятельно рекомендуется задавать для обработки не более 1000 баров!"
#property indicator_chart_window
#property indicator_buffers 0
#property indicator_plots 0
//--- input parameters
input int      MinDimesion = 5;          // Минимальная размерность точек
input int      MaxBars     = 300;        // Количество обрабатываемых баров
input string   LabelName   = "KF_Label"; //
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int OnInit()
  {
//--- indicator buffers mapping

//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
   CleanChart();
   Comment("");
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int OnCalculate(const int rates_total,
                const int prev_calculated,
                const datetime &time[],
                const double &open[],
                const double &high[],
                const double &low[],
                const double &close[],
                const long &tick_volume[],
                const long &volume[],
                const int &spread[])
  {
//---
//проверка доступности истории для установленного количества баров
   int SMaxBars=Bars(Symbol(),0),iMaxBars=MaxBars;
   if(SMaxBars<MaxBars)
     {
      iMaxBars=SMaxBars;
      Comment("Параметр MaxBars задан слишком большим."+"\n"+"Для расчетов будет использовано "+IntegerToString(SMaxBars)+" баров.");
     };
   int clean=CleanChart();//чистим график при повторном применении
   MqlRates  rates_array[];
   string Com="";
   int iCod=CopyRates(Symbol(),Period(),0,iMaxBars,rates_array);//количество элементов массива
   iCod=iCod-1;//Индекс максимального элемента в массиве
   Com="Работаю...Ждите!";
   Comment(Com);
   if(iCod>0)
     {
      FindUpKeyPoints(iCod,rates_array);//Поиск верхних ключевых точек
      Com=Com+"\n"+"Обработаны верхние точки."+"\n";
      Comment(Com);
      FindLowKeyPoints(iCod,rates_array);//Поиск нижних ключевых точек
      Comment("Обработка завершена");
     }
   else
      Comment("Отсутствуют бары для обработки!!!");
//--- return value of prev_calculated for next call
   return(rates_total);
  }
//+------------------------------------------------------------------+
//|                  Поиск верхних ключевых точек                    |
//+------------------------------------------------------------------+
void FindUpKeyPoints(int temp_iCod,MqlRates &temp_rates[])
  {
   int HD=1;
   for(int i=temp_iCod-MinDimesion; i>(MinDimesion-1); i--)//цикл по барам от конечного - MinDimension до нулевого + MinDimension
     {
      HD=getHighDimension(temp_rates,i,temp_iCod);//получаем размерность точек
      if((HD>=MinDimesion) || (HD==-1))
        {
         //создаем марку если попадает под условия MinDimension
         string Ob_Name=LabelName+IntegerToString(i);
         if(HD!=-1)
           {
            ObjectCreate(0,Ob_Name,OBJ_TEXT,0,temp_rates[i].time,temp_rates[i].high);
            ObjectSetInteger(0,Ob_Name,OBJPROP_ANCHOR,0,ANCHOR_LOWER);
            ObjectSetString(0,Ob_Name,OBJPROP_TEXT,0,IntegerToString(HD));
            ObjectSetInteger(0,Ob_Name,OBJPROP_COLOR,clrRed);
           }
         else
           {
            //Если не можем определить размерность маркируем шариком
            ObjectCreate(0,Ob_Name,OBJ_ARROW,0,temp_rates[i].time,temp_rates[i].high);
            ObjectSetInteger(0,Ob_Name,OBJPROP_ARROWCODE,0,159);
            ObjectSetInteger(0,Ob_Name,OBJPROP_ANCHOR,0,ANCHOR_BOTTOM);
            ObjectSetInteger(0,Ob_Name,OBJPROP_COLOR,clrRed);
           };
        };
     };
  }
//+------------------------------------------------------------------+
//|                    Поиск нижних ключевых точек                   |
//+------------------------------------------------------------------+
void FindLowKeyPoints(int temp_iCod,MqlRates &temp_rates[])
  {
   int LD=1;//инициализируем размерности точек
   bool iCreate;
   for(int i=temp_iCod-MinDimesion; i>(MinDimesion-1); i--)
     {
      LD=getLowDimension(temp_rates,i,temp_iCod);
      if((LD>=MinDimesion) || (LD==-1))
        {
         string Ob_Name=LabelName+IntegerToString(i)+"_1";//Страхуемся от баров где лой и хай могут быть ключевыми точками
         if(LD!=-1)
           {
            iCreate=ObjectCreate(0,Ob_Name,OBJ_TEXT,0,temp_rates[i].time,temp_rates[i].low);
            if(iCreate)
              {
               ObjectSetInteger(0,Ob_Name,OBJPROP_ANCHOR,0,ANCHOR_UPPER);
               ObjectSetString(0,Ob_Name,OBJPROP_TEXT,0,IntegerToString(LD));
               ObjectSetInteger(0,Ob_Name,OBJPROP_COLOR,clrGreen);
              }
            else
               Comment("Не могу создать объект");
           }
         else
           {
            iCreate=ObjectCreate(0,Ob_Name,OBJ_ARROW,0,temp_rates[i].time,temp_rates[i].low);
            if(iCreate)
              {
               ObjectSetInteger(0,Ob_Name,OBJPROP_ARROWCODE,0,159);
               ObjectSetInteger(0,Ob_Name,OBJPROP_ANCHOR,0,ANCHOR_TOP);
               ObjectSetInteger(0,Ob_Name,OBJPROP_COLOR,clrGreen);
              }
            else
               Comment("Не могу создать объект");
           };
        };
     };
  }
//+------------------------------------------------------------------+
//|                Определение размерности верхней точки             |
//+------------------------------------------------------------------+
int getHighDimension(MqlRates &tmpRates[],int tmp_i,int tmp_iCod)
  {
   int k=1;
   while((tmpRates[tmp_i].high>tmpRates[tmp_i+k].high) && (tmpRates[tmp_i].high>tmpRates[tmp_i-k].high) && ((tmp_i+k)<(tmp_iCod)) && ((tmp_i-k)>0))
      k++;
   if(((tmp_i+k)==tmp_iCod) || ((tmp_i-k)==0))
      k=-1;
   return(k);
  }
//+------------------------------------------------------------------+
//|                Определение размерности нижней точки              |
//+------------------------------------------------------------------+
int getLowDimension(MqlRates &tmpRates[],int tmp_i,int tmp_iCod)
  {
   int k=1;
   while((tmpRates[tmp_i].low<tmpRates[tmp_i+k].low) && (tmpRates[tmp_i].low<tmpRates[tmp_i-k].low) && ((tmp_i+k)<(tmp_iCod)) && ((tmp_i-k)>0))
      k++;
   if(((tmp_i+k)==tmp_iCod) || ((tmp_i-k)==0))
      k=-1;
   return(k);
  }
//+-------------------------------------------------------------------------------+
//| Очистка графика от созданных скриптом объектов в случае повторного применения |
//+-------------------------------------------------------------------------------+
int CleanChart()
  {
   string Label=LabelName;
   int obj_total=ObjectsTotal(0,0,-1),n=0;
   for(int obj=obj_total-1; obj>=0; obj--)
     {
      string objname=ObjectName(0,obj,0,-1);
      if(StringFind(objname,Label)>=0)
         ObjectDelete(0,objname);
      n++;
     }
   return(n);
  }
//+------------------------------------------------------------------+
Файлы:
KeyFinder.mq5  16 kb