Author: Copyright 2016, Artem A. Trishkin, Skype artmedia70
Indicators Used
Accumulation/Distribution indicatorCommodity channel indexDeMarker indicatorForce indexRelative strength indexStochastic oscillator
0 Views
0 Downloads
0 Favorites
iCrossAD
//+------------------------------------------------------------------+
//|                                             iSignalByCrossAD.mq4 |
//|              Copyright 2016, Artem A. Trishkin, Skype artmedia70 |
//|                       https://login.mql5.com/ru/users/artmedia70 |
//+------------------------------------------------------------------+
#property copyright "Copyright 2016, Artem A. Trishkin, Skype artmedia70"
#property link      "https://login.mql5.com/ru/users/artmedia70"
#property version   "1.00"
#property strict
//#property indicator_chart_window
#property indicator_separate_window
#property indicator_buffers 3
#property indicator_plots   3
//--- plot AD
#property indicator_label1  "AD"
#property indicator_type1   DRAW_LINE
#property indicator_color1  clrRed
#property indicator_style1  STYLE_SOLID
#property indicator_width1  1
//--- plot ArrowUP
#property indicator_label2  "Arrow to Up"
#property indicator_type2   DRAW_ARROW
#property indicator_color2  clrBlue
#property indicator_style2  STYLE_SOLID
#property indicator_width2  1
//--- plot ArrowDN
#property indicator_label3  "Arrow to Down"
#property indicator_type3   DRAW_ARROW
#property indicator_color3  clrRed
#property indicator_style3  STYLE_SOLID
#property indicator_width3  1

//--- enums
enum enumYN
  {
   enYes=1, // Yes
   enNo=0,  // No
  };
//---
enum enumStyle
  {
   enStFill=1,    // Fill
   enStFrame=0,   // Frame
  };
//---
enum enumWidth
  {
   enWidth1=1,    // 1
   enWidth2=2,    // 2
   enWidth3=3,    // 3
   enWidth4=4,    // 4
  };
//---
enum enumFilterBy
  {
   enFilterNot=0,    // Without filtration
   enFilterCCI=1,    // Filter by CCI
  };
enum enumLineStoch
  {
   enLineSto0=MODE_MAIN,   // Main Line
   enLineSto1=MODE_SIGNAL, // Signal Line
  };

//--- input parameters
input int      PeriodFind=60;                            // Number bars for calculate
int periodFind=(PeriodFind<6)?6:PeriodFind; // Number bars for calculate
input int      UnheckedBars=3;                           // Unchecked bars
int unheckedBars=(UnheckedBars<2)?2:UnheckedBars; // Unchecked bars
//---
extern string  _P_Filters = "-- Filtration --"; //======================================
input enumFilterBy FilterBy=enFilterCCI;                 // Filtering indicator
input enumYN UseDefaultSetting=enYes;                    // Use settings by default CCI parameters
//---
input int PeriodIND=14;                                  // Period for CCI
int periodIND=(PeriodIND<1)?1:PeriodIND;
input ENUM_APPLIED_PRICE AppledPriceIND=PRICE_TYPICAL;   // Appled Price for CCI
ENUM_APPLIED_PRICE appledPriceIND=AppledPriceIND;
extern string  _P_Levels = "-- Parameters of CCI levels --"; //======================================
input double UpperLevelIND=100.0;                        // The upper level of the filter indicator
double upperLevelIND=UpperLevelIND;
input double LowerLevelIND=-100.0;                       // The lower level of the filter indicator
double lowerLevelIND=LowerLevelIND;
//---
extern string  _P_Graphs = "-- Graphics Options --"; //======================================
sinput enumYN DrawArea=enNo;                             // Draw the search area
sinput enumStyle StyleFrame=enStFrame;                   // Style the search area (Frame or Fill)
sinput enumWidth WidthLineArea=enWidth1;                 // Line width the search area (if Frame)
sinput ENUM_LINE_STYLE StyleLineFrame=STYLE_SOLID;       // Line style the search area (if Frame)
sinput color ColorArea=clrLightSteelBlue;                // Line color the search area
//---
sinput enumYN DrawTrendLine=enNo;                        // Draw a trend line
sinput enumWidth WidthTrendLine=enWidth1;                // The thickness of the trend line
sinput ENUM_LINE_STYLE StyleTrendLine=STYLE_DOT;         // Line style of the trend line
sinput color ColorTrendDN=clrRed;                        // Color downtrend line
sinput color ColorTrendUP=clrBlue;                       // Color uptrend line
//---
sinput enumYN DrawChartsArrow=enNo;                      // Draws arrows on chart
sinput enumWidth ArrowSize=enWidth2;                     // The size of the arrows on the chart
sinput color ColorBullishArrow=clrBlue;                  // Color bullish arrows
sinput color ColorBearishArrow=clrRed;                   // Color bearish arrows
//--- indicator buffers
double         BufferAD[];
double         BufferUpperArrow[];
double         BufferLowerArrow[];
//---
double         BufferPeakUP[][2];   // array of peak up [i][0] - time, [i][1] - value
double         BufferPeakDN[][2];   // array of peak down [i][0] - time, [i][1] - value
//--- Global variables
double point;
bool   checkFilter;
string symbol, Prefix;
int    digits, wnd;
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int OnInit()
  {
//---
   symbol=Symbol();
   point=SymbolInfoDouble(symbol,SYMBOL_POINT);
   digits=int(SymbolInfoInteger(symbol,SYMBOL_DIGITS));
   Prefix="SCAD("+IntegerToString(periodFind)+")"+symbol;
   wnd=ChartWindowFind();
   checkFilter=true;
//--- correct input variables
   if(UseDefaultSetting) CorrectInputValue(FilterBy);
//--- indicator buffers mapping
   SetIndexBuffer(0,BufferAD);
   SetIndexBuffer(1,BufferUpperArrow);
   SetIndexBuffer(2,BufferLowerArrow);
//--- setting a code from the Wingdings charset as the property of PLOT_ARROW
   PlotIndexSetInteger(1,PLOT_ARROW,241);
   PlotIndexSetInteger(2,PLOT_ARROW,242);
   SetIndexArrow(1,241);
   SetIndexArrow(2,242);
//---
   IndicatorSetInteger(INDICATOR_DIGITS,digits);
   IndicatorSetString(INDICATOR_SHORTNAME,Prefix);
//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function                       |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
//--- delete graphics
   RemoveAllObjectsFromChart(0,Prefix);
//---
  }
//+------------------------------------------------------------------+
//| 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[])
  {
//---
   //--- Checking for number bars of calculated
   if(rates_total<periodFind+unheckedBars+1) return(0);
//---
   ArraySetAsSeries(BufferAD,true);
   ArraySetAsSeries(BufferUpperArrow,true);
   ArraySetAsSeries(BufferLowerArrow,true);
   ArraySetAsSeries(open,true);
   ArraySetAsSeries(high,true);
   ArraySetAsSeries(low,true);
   ArraySetAsSeries(close,true);
   ArraySetAsSeries(time,true);
//---
   string nm="";
   double p1=0, p2=0;
   int limit=rates_total-prev_calculated;
   if(limit>1) {
      limit=rates_total-periodFind-unheckedBars-1;
      ArrayInitialize(BufferAD,EMPTY_VALUE);
      ArrayInitialize(BufferUpperArrow,EMPTY_VALUE);
      ArrayInitialize(BufferLowerArrow,EMPTY_VALUE);
      }
//---
   double value_left_dn=DBL_MAX, value_left_up=-DBL_MAX;
   double value_right_dn=DBL_MAX, value_right_up=-DBL_MAX;
   datetime time_right_dn=0, time_right_up=0;
   int bar_max=0, bar_min=0;
   ArrayResize(BufferPeakUP,0);
   ArrayResize(BufferPeakDN,0);
   //--- Main cicle
   for(int i=limit; i>=0; i--) {
      BufferAD[i]=GetDataAD(symbol,Period(),i);
      BufferUpperArrow[i]=EMPTY_VALUE;
      BufferLowerArrow[i]=EMPTY_VALUE;
      //--- Finding all the extremes within the period Find. Íàéä¸ì âñå ýêñòðåìóìû â ïðåäåëàõ periodFind
      int jup=0, jdn=0;
      for(int j=i; j<=i+periodFind+unheckedBars-1; j++) {
         BufferAD[j]=GetDataAD(symbol,Period(),j);
         if(j>i+unheckedBars) {
            //--- Up peacks. âåðøèíû
            if(DirectionExtremum(BufferAD[j+1],BufferAD[j],BufferAD[j-1])==OP_SELL) {
               jup++;
               ArrayResize(BufferPeakUP,jup,periodFind);
               BufferPeakUP[jup-1][0]=int(time[j]);
               BufferPeakUP[jup-1][1]=BufferAD[j];
               }
            //--- Down peacks. äîíûøêè
            if(DirectionExtremum(BufferAD[j+1],BufferAD[j],BufferAD[j-1])==OP_BUY) {
               jdn++;
               ArrayResize(BufferPeakDN,jdn,periodFind);
               BufferPeakDN[jdn-1][0]=int(time[j]);
               BufferPeakDN[jdn-1][1]=BufferAD[j];
               }
            }
         }
      //--- Tops within the period Find. Âåðøèíû â ïðåäåëàõ periodFind
      int size_mass_up=ArrayRange(BufferPeakUP,0);
      if(size_mass_up>0) {
         time_right_up=int(BufferPeakUP[0][0]);
         int bar_right_up=iBarShift(symbol,Period(),time_right_up);
         value_right_up=BufferPeakUP[0][1];
         int index_max=ArrayMaximumInXDimm(BufferPeakUP,1);  // íàèáîëüøåå çíà÷åíèå â ìàññèâå
         datetime time_max=int(BufferPeakUP[index_max][0]);
         bar_max=iBarShift(symbol,Period(),time_max);
         value_left_up=BufferPeakUP[index_max][1];
         if(time_right_up>time_max && BufferAD[bar_max]>value_right_up) {
            for(int k=index_max-0; k>0; k--) {
               int bar_k=iBarShift(symbol,Period(),datetime(BufferPeakUP[k][0]));
               double virtual_price=EquationDirect(bar_max,value_left_up,bar_right_up,value_right_up,bar_k);
               //--- if the top of crosses the line. åñëè âåðøèíà ïåðåñåêàåò ëèíèþ
               if(BufferAD[bar_k]>virtual_price) {
                  bar_max=iBarShift(symbol,Period(),int(BufferPeakUP[k][0]));
                  value_left_up=BufferPeakUP[k][1];
                  }
               }
            //--- check the intersection to down. ïðîâåðêà ïåðåñå÷åíèÿ âíèç
            if(EquationDirect(bar_max,value_left_up,bar_right_up,value_right_up,i+1)<BufferAD[i+1] &&
              (EquationDirect(bar_max,value_left_up,bar_right_up,value_right_up,i+2)>=BufferAD[i+2] ||
               EquationDirect(bar_max,value_left_up,bar_right_up,value_right_up,i+3)>=BufferAD[i+3])) 
               {
               if(FilterBy!=enFilterNot) {
                  double filter_1=GetDataIND(symbol,Period(),FilterBy,i+1);
                  double filter_2=GetDataIND(symbol,Period(),FilterBy,i+2);
                  double filter_3=GetDataIND(symbol,Period(),FilterBy,i+3);
                  checkFilter=(filter_1<=lowerLevelIND && filter_2<lowerLevelIND)?true:false;
                  }
               else checkFilter=true;
               if(checkFilter) {
                  BufferUpperArrow[i]=BufferAD[i+1];
                  if(DrawChartsArrow) SetArrow(0,241,ColorBullishArrow,0,Prefix+"ChartArrowUP_"+TimeToString(time[i]),ANCHOR_TOP,time[i],open[i],ArrowSize);
                  }
               }
            }
         }
      //--- Bottoms within the period Find. Äîíûøêè â ïðåäåëàõ periodFind
      int size_mass_dn=ArrayRange(BufferPeakDN,0);
      if(size_mass_dn>0) {
         time_right_dn=int(BufferPeakDN[0][0]);
         int bar_right_dn=iBarShift(symbol,Period(),time_right_dn);
         value_right_dn=BufferPeakDN[0][1];
         int index_min=ArrayMinimumInXDimm(BufferPeakDN,1);  // íàèìåíüøåå çíà÷åíèå â ìàññèâå
         datetime time_min=int(BufferPeakDN[index_min][0]);
         bar_min=iBarShift(symbol,Period(),time_min);
         value_left_dn=BufferPeakDN[index_min][1];
         if(time_right_dn>time_min && BufferAD[bar_min]<value_right_dn) {
            for(int k=index_min-0; k>0; k--) {
               int bar_k=iBarShift(symbol,Period(),datetime(BufferPeakDN[k][0]));
               double virtual_price=EquationDirect(bar_min,value_left_dn,bar_right_dn,value_right_dn,bar_k);
               //--- if the bottom of line crosses. åñëè äíî ïåðåñåêàåò ëèíèþ
               if(BufferAD[bar_k]<virtual_price) {
                  bar_min=iBarShift(symbol,Period(),int(BufferPeakDN[k][0]));
                  value_left_dn=BufferPeakDN[k][1];
                  }
               }
            //--- check the intersection to up. ïðîâåðêà ïåðåñå÷åíèÿ ââåðõ
            if(EquationDirect(bar_min,value_left_dn,bar_right_dn,value_right_dn,i+1)>BufferAD[i+1] &&
              (EquationDirect(bar_min,value_left_dn,bar_right_dn,value_right_dn,i+2)<=BufferAD[i+2] ||
               EquationDirect(bar_min,value_left_dn,bar_right_dn,value_right_dn,i+3)<=BufferAD[i+3])) 
               {
               if(FilterBy!=enFilterNot) {
                  double filter_1=GetDataIND(symbol,Period(),FilterBy,i+1);
                  double filter_2=GetDataIND(symbol,Period(),FilterBy,i+2);
                  double filter_3=GetDataIND(symbol,Period(),FilterBy,i+3);
                  checkFilter=(filter_1>=upperLevelIND && filter_2>upperLevelIND)?true:false;
                  }
               else checkFilter=true;
               if(checkFilter) {
                  BufferLowerArrow[i]=BufferAD[i+1];
                  if(DrawChartsArrow) SetArrow(0,242,ColorBearishArrow,0,Prefix+"ChartArrowDN_"+TimeToString(time[i]),ANCHOR_BOTTOM,time[i],open[i],ArrowSize);
                  }
               }
            }
         }
     }
   if(DrawArea) SetRectangle(0,ColorArea,Prefix+"_range",wnd,time[periodFind+unheckedBars],BufferAD[ArrayMaximum(BufferAD,periodFind,unheckedBars)],time[unheckedBars],BufferAD[ArrayMinimum(BufferAD,periodFind,unheckedBars)],WidthLineArea,StyleLineFrame,StyleFrame);
   if(DrawTrendLine) {
      SetTLine(0,Prefix+"_TLineDN",ColorTrendDN,wnd,time[bar_max],BufferAD[bar_max],time_right_up,BufferPeakUP[0][1],WidthTrendLine,StyleTrendLine,true);
      SetTLine(0,Prefix+"_TLineUP",ColorTrendUP,wnd,time[bar_min],BufferAD[bar_min],time_right_dn,BufferPeakDN[0][1],WidthTrendLine,StyleTrendLine,true);
      }
//--- return value of prev_calculated for next call
   return(rates_total);
  }
//+----------------------------------------------------------------------------+
//--- Author KimIV (http://www.kimiv.ru/), edited by Artmedia70 (https://www.mql5.com/ru/users/artmedia70)
double EquationDirect(int left_bar, double left_price, int right_bar, double right_price, double bar_to_search) {
  return((right_bar==left_bar)?left_price:(right_price-left_price)/(right_bar-left_bar)*(bar_to_search-left_bar)+left_price);
}
//+------------------------------------------------------------------+
int DirectionExtremum(double a, double b, double c) {
   if((a-b)*(b-c)<0) {
      if(c>b) return(OP_BUY);
      if(c<b) return(OP_SELL);
      }
   return(EMPTY);
}
//+------------------------------------------------------------------+
int ArrayMaximumInXDimm(double &massive[][], int rank_index=1, int count=0, int start_find=0) {
   if(ArrayRange(massive,0)==0) return(EMPTY);
   int res=0, num=(count<=0)?ArrayRange(massive,0):count;
   double value=massive[start_find][rank_index];
   for(int i=start_find+1; i<num; i++) {
      if(massive[i][rank_index]>value) {
         value=massive[i][rank_index];
         res=i;
         }
      }
   return(res);
}
//+------------------------------------------------------------------+
int ArrayMinimumInXDimm(double &massive[][], int rank_index=1, int count=0, int start_find=0) {
   if(ArrayRange(massive,0)<=0) return(EMPTY);
   int res=0, num=(count==0)?ArrayRange(massive,0):count;
   double value=massive[start_find][rank_index];
   for(int i=start_find+1; i<num; i++) {
      if(massive[i][rank_index]<value) {
         value=massive[i][rank_index];
         res=i;
         }
      }
   return(res);
}
//+------------------------------------------------------------------+
void RemoveAllObjectsFromChart(long chart_id, string prefix) {
   ObjectsDeleteAll(chart_id,prefix);
}
//+------------------------------------------------------------------+
void SetRectangle(const long chart_id, color rect_color, const string name, const int sub_window,
                  datetime time1, double price1, datetime time2, double price2, 
                  int width=1, int style=0, bool background=false, string tooltip="\n", bool selection=false, bool hidden=true) {
   
   if(ObjectFind(name)<0) ObjectCreate(chart_id, name, OBJ_RECTANGLE, sub_window, 0, 0, 0, 0);
   ObjectSetInteger(chart_id,name,OBJPROP_TIME1,time1);
   ObjectSetDouble(chart_id,name,OBJPROP_PRICE1,price1);
   ObjectSetInteger(chart_id,name,OBJPROP_TIME2,time2);
   ObjectSetDouble(chart_id,name,OBJPROP_PRICE2,price2);
   ObjectSetInteger(chart_id,name,OBJPROP_COLOR,rect_color);
   ObjectSetInteger(chart_id,name,OBJPROP_STYLE,style);
   ObjectSetInteger(chart_id,name,OBJPROP_WIDTH,width);
   ObjectSetInteger(chart_id,name,OBJPROP_BACK,background);
   ObjectSetInteger(chart_id,name,OBJPROP_SELECTABLE,selection);
   ObjectSetInteger(chart_id,name,OBJPROP_SELECTED,selection);
   ObjectSetInteger(chart_id,name,OBJPROP_HIDDEN,hidden);
   ObjectSetString(chart_id,name,OBJPROP_TOOLTIP,tooltip);
}
//+------------------------------------------------------------------+
void SetTLine(const long chart_id, const string name, color line_color, const int sub_window,
              datetime line_time1, double line_price1, datetime line_time2, double line_price2, int line_width=1,
              int line_style=0, bool line_ray_right=False, bool line_ray_left=False, 
              string line_text="", string tooltip="\n", bool selection=false, bool hidden=true) {
   
   if(ObjectFind(name)<0) ObjectCreate(chart_id, name, OBJ_TREND, sub_window, 0, 0, 0, 0);
   ObjectSetInteger(chart_id,name,OBJPROP_TIME1,line_time1);
   ObjectSetDouble(chart_id,name,OBJPROP_PRICE1,line_price1);
   ObjectSetInteger(chart_id,name,OBJPROP_TIME2,line_time2);
   ObjectSetDouble(chart_id,name,OBJPROP_PRICE2,line_price2);
   ObjectSetInteger(chart_id,name,OBJPROP_COLOR,line_color);
   ObjectSetInteger(chart_id,name,OBJPROP_RAY_RIGHT,line_ray_right);
   ObjectSetInteger(chart_id,name,OBJPROP_RAY_LEFT,line_ray_left);
   ObjectSetInteger(chart_id,name,OBJPROP_STYLE,line_style);
   ObjectSetInteger(chart_id,name,OBJPROP_WIDTH,line_width);
   ObjectSetString(chart_id,name,OBJPROP_TEXT,line_text);
   ObjectSetString(chart_id,name,OBJPROP_FONT,"Tahoma");
   ObjectSetInteger(chart_id,name,OBJPROP_SELECTABLE,selection);
   ObjectSetInteger(chart_id,name,OBJPROP_SELECTED,selection);
   ObjectSetInteger(chart_id,name,OBJPROP_HIDDEN,hidden);
   ObjectSetString(chart_id,name,OBJPROP_TOOLTIP,tooltip);
}
//+------------------------------------------------------------------+
void SetArrow(long chart_id, int arrow_code, color arrow_color, int sub_window, 
              string name, long arrow_anchor, datetime arrow_time, double arrow_price, int arrow_size=0, 
              string tooltip="\n", bool selection=false, bool hidden=true) {
   
   if(ObjectFind(name)<0) ObjectCreate(chart_id, name, OBJ_ARROW, sub_window, 0, 0);
   ObjectSetInteger(chart_id,name,OBJPROP_TIME,arrow_time);
   ObjectSetDouble(chart_id,name,OBJPROP_PRICE,arrow_price);
   ObjectSetInteger(chart_id,name,OBJPROP_ARROWCODE,arrow_code);
   ObjectSetInteger(chart_id,name,OBJPROP_COLOR,arrow_color);
   ObjectSetInteger(chart_id,name,OBJPROP_WIDTH,arrow_size);
   ObjectSetInteger(chart_id,name,OBJPROP_ANCHOR,arrow_anchor);
   ObjectSetInteger(chart_id,name,OBJPROP_SELECTED,selection);
   ObjectSetInteger(chart_id,name,OBJPROP_SELECTABLE,selection);
   ObjectSetInteger(chart_id,name,OBJPROP_HIDDEN,hidden);
   ObjectSetString(chart_id,name,OBJPROP_TOOLTIP,tooltip);
}
//+------------------------------------------------------------------+
double GetDataIND(string sy, int timeframe, enumFilterBy filtered_indicator, int pos) {
   switch(filtered_indicator)
     {
      default: // CCI
        return(GetDataCCI(sy,timeframe,periodIND,appledPriceIND,pos));
        break;
     }
}
//+------------------------------------------------------------------+
double GetDataAD(string sy, int timeframe, int pos) {
   return(iAD(sy,timeframe,pos));
}
//+------------------------------------------------------------------+
double GetDataCCI(string sy, int timeframe, int period, ENUM_APPLIED_PRICE appled_price, int pos) {
   return(iCCI(sy,timeframe,period,appled_price,pos));
}
//+------------------------------------------------------------------+
double GetDataDeM(string sy, int timeframe, int period, int pos) {
   return(iDeMarker(sy,timeframe,period,pos));
}
//+------------------------------------------------------------------+
double GetDataFoI(string sy, int timeframe, int period, ENUM_MA_METHOD ma_method, ENUM_APPLIED_PRICE appled_price, int pos) {
   return(iForce(sy,timeframe,period,ma_method,appled_price,pos));
}
//+------------------------------------------------------------------+
double GetDataRSI(string sy, int timeframe, int period, ENUM_APPLIED_PRICE appled_price, int pos) {
   return(iRSI(sy,timeframe,period,appled_price,pos));
}
//+------------------------------------------------------------------+
double GetDataSTO(string sy, int timeframe, int k_period, int d_period, int slowing, ENUM_MA_METHOD ma_method, ENUM_STO_PRICE price_field, int mode, int pos) {
   return(iStochastic(sy,timeframe,k_period,d_period,slowing,ma_method,price_field,mode,pos));
}
//+------------------------------------------------------------------+
void CorrectInputValue(enumFilterBy filtered_indicator) {
   switch(filtered_indicator)
     {
      default: // CCI
        periodIND=14;
        appledPriceIND=PRICE_TYPICAL;
        break;
     }
}
//+------------------------------------------------------------------+

Comments

Markdown supported. Formatting help

Markdown Formatting Guide

Element Markdown Syntax
Heading # H1
## H2
### H3
Bold **bold text**
Italic *italicized text*
Link [title](https://www.example.com)
Image ![alt text](image.jpg)
Code `code`
Code Block ```
code block
```
Quote > blockquote
Unordered List - Item 1
- Item 2
Ordered List 1. First item
2. Second item
Horizontal Rule ---