Parabolic_MARSI_Adaptive_MACD

Author: Copyright 2018, MetaQuotes Software Corp.
Price Data Components
Indicators Used
Moving average indicatorRelative strength index
0 Views
0 Downloads
0 Favorites
Parabolic_MARSI_Adaptive_MACD
ÿþ//+------------------------------------------------------------------+

//|                                Parabolic_MARSI_Adaptive_MACD.mq5 |

//|                        Copyright 2018, MetaQuotes Software Corp. |

//|                                                 https://mql5.com |

//+------------------------------------------------------------------+

#property copyright "Copyright 2018, MetaQuotes Software Corp."

#property link      "https://mql5.com"

#property version   "1.00"

#property description "Parabolic MARSI adaptive Macd indicator"

#property indicator_separate_window

#property indicator_buffers 12

#property indicator_plots   6

//--- plot MACD

#property indicator_label1  "MACD"

#property indicator_type1   DRAW_COLOR_HISTOGRAM

#property indicator_color1  clrGreen,clrDarkSeaGreen,clrRed,clrLightSalmon,clrDarkGray

#property indicator_style1  STYLE_SOLID

#property indicator_width1  8

//--- plot Signal

#property indicator_label2  "Signal"

#property indicator_type2   DRAW_LINE

#property indicator_color2  clrRed

#property indicator_style2  STYLE_SOLID

#property indicator_width2  1

//--- plot SarUP

#property indicator_label3  "SAR Up"

#property indicator_type3   DRAW_ARROW

#property indicator_color3  clrBlue

#property indicator_style3  STYLE_SOLID

#property indicator_width3  3

//--- plot SarDN

#property indicator_label4  "SAR Down"

#property indicator_type4   DRAW_ARROW

#property indicator_color4  clrRed

#property indicator_style4  STYLE_SOLID

#property indicator_width4  3

//--- plot SarPointUP

#property indicator_label5  "SAR point up"

#property indicator_type5   DRAW_ARROW

#property indicator_color5  clrBlue

#property indicator_style5  STYLE_SOLID

#property indicator_width5  3

//--- plot SarPointDN

#property indicator_label6  "SAR point down"

#property indicator_type6   DRAW_ARROW

#property indicator_color6  clrRed

#property indicator_style6  STYLE_SOLID

#property indicator_width6  3

//--- defines

#define   maInstances       1

#define   maWorkBufferx1    1*maInstances

#define   maWorkBufferx2    2*maInstances

#define   maWorkBufferx3    3*maInstances

//--- enums

enum ENUM_MA_METHOD_EXT

  {

   METHOD_SMA  =  MODE_SMA,   // Simple moving average

   METHOD_EMA  =  MODE_EMA,   // Exponential moving average

   METHOD_SMMA =  MODE_SMMA,  // Smoothed moving average

   METHOD_LWMA =  MODE_LWMA,  // Linear weighted moving average

   METHOD_TEMA =  4           // Triple exponential moving average - TEMA

  };

//--- input parameters

input uint                 InpPeriodRSI1     =  14;            // First RSI period

input double               InpSpeed1         =  1.2;           // First RSI speed

input ENUM_APPLIED_PRICE   InpAppliedPrice1  =  PRICE_CLOSE;   // First RSI applied price

input uint                 InpPeriodRSI2     =  34;            // Second RSI period

input double               InpSpeed2         =  0.8;           // Second RSI speed

input ENUM_APPLIED_PRICE   InpAppliedPrice2  =  PRICE_CLOSE;   // Second RSI applied price

input uint                 InpPeriodSig      =  9;             // Signal period

input ENUM_MA_METHOD_EXT   InpMethodSig      =  METHOD_SMA;    // Signal method

input double               InpStep           =  0.01;          // SAR accumulation step

input double               InpMax            =  0.1;           // SAR accumulation limit

//--- indicator buffers

double         BufferMACD[];

double         BufferColors[];

double         BufferSignal[];

double         BufferSarUP[];

double         BufferSarDN[];

double         BufferSarPointUP[];

double         BufferSarPointDN[];

double         BufferMA1[];

double         BufferMA2[];

double         BufferRSI1[];

double         BufferRSI2[];

double         BufferSlope[];

//--- global variables

double         BufferMaRsi[][2];

double         BufferSAR[][7];

double         BufferSMA[][maWorkBufferx2];

double         BufferEMA[][maWorkBufferx1];

double         BufferSMMA[][maWorkBufferx1];

double         BufferLWMA[][maWorkBufferx1];

double         BufferTEMA[][maWorkBufferx3];

//---

double         step_sar;

double         max_sar;

double         speed1;

double         speed2;

int            period_rsi1;

int            period_rsi2;

int            period_sig;

int            period_max;

int            handle_maP1;

int            handle_maP2;

int            handle_rsi1;

int            handle_rsi2;

//+------------------------------------------------------------------+

//| Custom indicator initialization function                         |

//+------------------------------------------------------------------+

int OnInit()

  {

//--- set global variables

   period_rsi1=int(InpPeriodRSI1<1 ? 1 : InpPeriodRSI1);

   period_rsi2=int(InpPeriodRSI2<1 ? 1 : InpPeriodRSI2);

   period_sig=int(InpPeriodSig<1 ? 1 : InpPeriodSig);

   period_max=fmax(period_sig,fmax(period_rsi1,period_rsi2));

   speed1=InpSpeed1;

   speed2=InpSpeed2;

   step_sar=(InpStep<0.0001 ? 0.0001 : InpStep);

   max_sar=(InpMax<0.0001 ? 0.0001 : InpMax);

//--- indicator buffers mapping

   SetIndexBuffer(0,BufferMACD,INDICATOR_DATA);

   SetIndexBuffer(1,BufferColors,INDICATOR_COLOR_INDEX);

   SetIndexBuffer(2,BufferSignal,INDICATOR_DATA);

   SetIndexBuffer(3,BufferSarUP,INDICATOR_DATA);

   SetIndexBuffer(4,BufferSarDN,INDICATOR_DATA);

   SetIndexBuffer(5,BufferSarPointUP,INDICATOR_DATA);

   SetIndexBuffer(6,BufferSarPointDN,INDICATOR_DATA);

   SetIndexBuffer(7,BufferMA1,INDICATOR_CALCULATIONS);

   SetIndexBuffer(8,BufferMA2,INDICATOR_CALCULATIONS);

   SetIndexBuffer(9,BufferRSI1,INDICATOR_CALCULATIONS);

   SetIndexBuffer(10,BufferRSI2,INDICATOR_CALCULATIONS);

   SetIndexBuffer(11,BufferSlope,INDICATOR_CALCULATIONS);

//--- setting a code from the Wingdings charset as the property of PLOT_ARROW

   PlotIndexSetInteger(2,PLOT_ARROW,158);

   PlotIndexSetInteger(3,PLOT_ARROW,158);

   PlotIndexSetInteger(4,PLOT_ARROW,159);

   PlotIndexSetInteger(5,PLOT_ARROW,159);

//--- setting indicator parameters

   IndicatorSetString(INDICATOR_SHORTNAME,"Parabolic MARSI adaptive Macd ("+(string)period_rsi1+","+DoubleToString(speed1,1)+","+(string)period_rsi2+","+DoubleToString(speed2,1)+")");

   IndicatorSetInteger(INDICATOR_DIGITS,Digits());

//--- setting buffer arrays as timeseries

   ArraySetAsSeries(BufferMACD,true);

   ArraySetAsSeries(BufferColors,true);

   ArraySetAsSeries(BufferSignal,true);

   ArraySetAsSeries(BufferSarUP,true);

   ArraySetAsSeries(BufferSarDN,true);

   ArraySetAsSeries(BufferSarPointUP,true);

   ArraySetAsSeries(BufferSarPointDN,true);

   ArraySetAsSeries(BufferMA1,true);

   ArraySetAsSeries(BufferMA2,true);

   ArraySetAsSeries(BufferRSI1,true);

   ArraySetAsSeries(BufferRSI2,true);

   ArraySetAsSeries(BufferSlope,true);

//--- create handles

   ResetLastError();

   handle_maP1=iMA(NULL,PERIOD_CURRENT,1,0,MODE_SMA,InpAppliedPrice1);

   if(handle_maP1==INVALID_HANDLE)

     {

      Print(__LINE__,": The iMA(1) object was not created: Error ",GetLastError());

      return INIT_FAILED;

     }

   handle_maP2=iMA(NULL,PERIOD_CURRENT,1,0,MODE_SMA,InpAppliedPrice2);

   if(handle_maP2==INVALID_HANDLE)

     {

      Print(__LINE__,": The iMA(1) object was not created: Error ",GetLastError());

      return INIT_FAILED;

     }

   handle_rsi1=iRSI(NULL,PERIOD_CURRENT,period_rsi1,InpAppliedPrice1);

   if(handle_rsi1==INVALID_HANDLE)

     {

      Print(__LINE__,": The iRSI(",(string)period_rsi1,") object was not created: Error ",GetLastError());

      return INIT_FAILED;

     }

   handle_rsi2=iRSI(NULL,PERIOD_CURRENT,period_rsi2,InpAppliedPrice2);

   if(handle_rsi2==INVALID_HANDLE)

     {

      Print(__LINE__,": The iRSI(",(string)period_rsi2,") object was not created: Error ",GetLastError());

      return INIT_FAILED;

     }

//---

   return(INIT_SUCCEEDED);

  }

//+------------------------------------------------------------------+

//| 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[])

  {

//--- @>25@:0 :>;8G5AB20 4>ABC?=KE 10@>2

   if(rates_total<fmax(period_max,4)) return 0;

//--- @>25@:0 8 @0AGQB :>;8G5AB20 ?@>AG8BK205<KE 10@>2

   int limit=rates_total-prev_calculated;

   if(limit>1)

     {

      limit=rates_total-1;

      ArrayInitialize(BufferMACD,EMPTY_VALUE);

      ArrayInitialize(BufferColors,4);

      ArrayInitialize(BufferSignal,EMPTY_VALUE);

      ArrayInitialize(BufferSarUP,EMPTY_VALUE);

      ArrayInitialize(BufferSarDN,EMPTY_VALUE);

      ArrayInitialize(BufferSarPointUP,EMPTY_VALUE);

      ArrayInitialize(BufferSarPointDN,EMPTY_VALUE);

      ArrayInitialize(BufferMA1,0);

      ArrayInitialize(BufferMA2,0);

      ArrayInitialize(BufferRSI1,0);

      ArrayInitialize(BufferRSI2,0);

      ArrayInitialize(BufferSlope,0);

     }

//--- >43>B>2:0 40==KE

   int count=(limit>0 ? rates_total : 1),copied=0;

   copied=CopyBuffer(handle_maP1,0,0,count,BufferMA1);

   if(copied!=count) return 0;

   copied=CopyBuffer(handle_maP2,0,0,count,BufferMA2);

   if(copied!=count) return 0;

   copied=CopyBuffer(handle_rsi1,0,0,count,BufferRSI1);

   if(copied!=count) return 0;

   copied=CopyBuffer(handle_rsi2,0,0,count,BufferRSI2);

   if(copied!=count) return 0;



//---  0AGQB 8=48:0B>@0

   for(int i=limit; i>=0 && !IsStopped(); i--)

     {

      double sarClose=0,sarOpen=0,sarPosition=0,sarChange=0;

      BufferMACD[i]=iMaRsi(rates_total,period_rsi1,speed1,BufferMA1[i],BufferRSI1[i],i,0)-iMaRsi(rates_total,period_rsi2,speed2,BufferMA2[i],BufferRSI2[i],i,1);

      BufferSignal[i]=iCustomMa(rates_total,InpMethodSig,BufferMACD[i],period_sig,i);

      iParabolic(rates_total,BufferMACD[i],BufferMACD[i],step_sar,max_sar,sarClose,sarOpen,sarPosition,sarChange,i);



      BufferSlope[i]=(i<rates_total-1 ? (BufferMACD[i]>BufferMACD[i+1] ? 1 : BufferMACD[i]<BufferMACD[i+1] ? -1 : BufferSlope[i+1]) : 0);

      BufferColors[i]=(BufferMACD[i]>0 ? (BufferSlope[i]==1 ? 0 : 1) : BufferMACD[i]<0 ? (BufferSlope[i]==1 ? 3 : 2) : 4);



      BufferSarUP[i]=BufferSarDN[i]=BufferSarPointUP[i]=BufferSarPointDN[i]=EMPTY_VALUE;

      if(sarPosition==1)

         BufferSarUP[i]=sarClose;

      else

         BufferSarDN[i]=sarClose;

      if(sarChange!=0)

        {

         if(sarPosition==1)

            BufferSarPointUP[i]=sarClose;

         else

            BufferSarPointDN[i]=sarClose;

        }

     }



//--- return value of prev_calculated for next call

   return(rates_total);

  }

//+------------------------------------------------------------------+

//|                                                                  |

//+------------------------------------------------------------------+

double iMaRsi(const int rates_total,const int rsi_period,const double speed,const double ma,const double rsi,int shift,int instance=0)

  {

   if(ArrayRange(BufferMaRsi,0)!=rates_total)

      ArrayResize(BufferMaRsi,rates_total);

   int r=rates_total-shift-1;

   if(r<rsi_period)

      BufferMaRsi[r][instance]=ma;

   else

      BufferMaRsi[r][instance]=BufferMaRsi[r-1][instance]+(speed*fabs(rsi/100.0-0.5))*(ma-BufferMaRsi[r-1][instance]);

   return(BufferMaRsi[r][instance]);

  }

//+------------------------------------------------------------------+

//|                                                                  |

//+------------------------------------------------------------------+

#define _high     0

#define _low      1

#define _ohigh    2

#define _olow     3

#define _open     4

#define _position 5

#define _af       6

void iParabolic(const int rates_total,double high,double low,double step,double limit,double &pClose,double &pOpen,double &pPosition,double &pChange,int shift)

  {

   if(ArrayRange(BufferSAR,0)!=rates_total)

      ArrayResize(BufferSAR,rates_total);

   int i=rates_total-shift-1;

   pChange=0;

   BufferSAR[i][_ohigh]=high;

   BufferSAR[i][_olow]=low;

   if(i<1)

     {

      BufferSAR[i][_high]=high;

      BufferSAR[i][_low]=low;

      BufferSAR[i][_open]=high;

      BufferSAR[i][_position]=WRONG_VALUE;

      return;

     }

   BufferSAR[i][_open]=BufferSAR[i-1][_open];

   BufferSAR[i][_af]=BufferSAR[i-1][_af];

   BufferSAR[i][_position]=BufferSAR[i-1][_position];

   BufferSAR[i][_high]=fmax(BufferSAR[i-1][_high],high);

   BufferSAR[i][_low]=fmin(BufferSAR[i-1][_low],low);



   if(BufferSAR[i][_position]==1)

     {

      if(low<=BufferSAR[i][_open])

        {

         BufferSAR[i][_position]=WRONG_VALUE;

         pChange=WRONG_VALUE;

         pClose=BufferSAR[i][_high];

         BufferSAR[i][_high]=high;

         BufferSAR[i][_low]=low;

         BufferSAR[i][_af]=step;

         BufferSAR[i][_open]=pClose+BufferSAR[i][_af]*(BufferSAR[i][_low]-pClose);

         if(BufferSAR[i][_open]<BufferSAR[i][_ohigh])

            BufferSAR[i][_open]=BufferSAR[i  ][_ohigh];

         if(BufferSAR[i][_open]<BufferSAR[i-1][_ohigh])

            BufferSAR[i][_open]=BufferSAR[i-1][_ohigh];

        }

      else

        {

         pClose=BufferSAR[i][_open];

         if(BufferSAR[i][_high]>BufferSAR[i-1][_high] && BufferSAR[i][_af]<limit)

            BufferSAR[i][_af]=fmin(BufferSAR[i][_af]+step,limit);

         BufferSAR[i][_open]=pClose+BufferSAR[i][_af]*(BufferSAR[i][_high]-pClose);

         if(BufferSAR[i][_open]>BufferSAR[i][_olow])

            BufferSAR[i][_open]=BufferSAR[i][_olow];

         if(BufferSAR[i][_open]>BufferSAR[i-1][_olow])

            BufferSAR[i][_open]=BufferSAR[i-1][_olow];

        }

     }

   else

     {

      if(high>=BufferSAR[i][_open])

        {

         BufferSAR[i][_position]=1;

         pChange=1;

         pClose=BufferSAR[i][_low];

         BufferSAR[i][_low]=low;

         BufferSAR[i][_high]=high;

         BufferSAR[i][_af]=step;

         BufferSAR[i][_open]=pClose+BufferSAR[i][_af]*(BufferSAR[i][_high]-pClose);

         if(BufferSAR[i][_open]>BufferSAR[i][_olow])

            BufferSAR[i][_open]=BufferSAR[i][_olow];

         if(BufferSAR[i][_open]>BufferSAR[i-1][_olow])

            BufferSAR[i][_open]=BufferSAR[i-1][_olow];

        }

      else

        {

         pClose=BufferSAR[i][_open];

         if(BufferSAR[i][_low]<BufferSAR[i-1][_low] && BufferSAR[i][_af]<limit)

            BufferSAR[i][_af]=fmin(BufferSAR[i][_af]+step,limit);

         BufferSAR[i][_open]=pClose+BufferSAR[i][_af]*(BufferSAR[i][_low]-pClose);

         if(BufferSAR[i][_open]<BufferSAR[i][_ohigh])

            BufferSAR[i][_open]=BufferSAR[i][_ohigh];

         if(BufferSAR[i][_open]<BufferSAR[i-1][_ohigh])

            BufferSAR[i][_open]=BufferSAR[i-1][_ohigh];

        }

     }

   pOpen=BufferSAR[i][_open];

   pPosition=BufferSAR[i][_position];

  }

//+------------------------------------------------------------------+

//|                                                                  |

//+------------------------------------------------------------------+

double iCustomMa(const int rates_total,ENUM_MA_METHOD_EXT mode,double price,double length,const int shift,int instance=0)

  {

   int r=rates_total-shift-1;

   switch(mode)

     {

      case METHOD_SMA   : return(SMA(price,(int)length,r,rates_total,instance));   

      case METHOD_EMA   : return(EMA(price,length,r,rates_total,instance));

      case METHOD_SMMA  : return(SMMA(price,(int)length,r,rates_total,instance));

      case METHOD_LWMA  : return(LWMA(price,(int)length,r,rates_total,instance));

      case METHOD_TEMA  : return(TEMA(price,(int)length,r,rates_total,instance));

      default           : return(price);

     }

  }

//+------------------------------------------------------------------+

//|                                                                  |

//+------------------------------------------------------------------+

double SMA(double price,int period,int r,int _bars,int instance=0)

  {

   if(ArrayRange(BufferSMA,0)!=_bars)

      ArrayResize(BufferSMA,_bars);

   instance*=2;

   int k=0;

   BufferSMA[r][instance]=price;

   BufferSMA[r][instance+1]=price;

   for(k=1; k<period && (r-k)>=0; k++) BufferSMA[r][instance+1]+=BufferSMA[r-k][instance];

   BufferSMA[r][instance+1]/=1.0*k;

   return(BufferSMA[r][instance+1]);

  }

//+------------------------------------------------------------------+

//|                                                                  |

//+------------------------------------------------------------------+

double EMA(double price,double period,int r,int _bars,int instance=0)

  {

   if(ArrayRange(BufferEMA,0)!=_bars)

      ArrayResize(BufferEMA,_bars);



   BufferEMA[r][instance]=price;

   if(r>0 && period>1)

      BufferEMA[r][instance]=BufferEMA[r-1][instance]+(2.0/(1.0+period))*(price-BufferEMA[r-1][instance]);

   return(BufferEMA[r][instance]);

  }

//+------------------------------------------------------------------+

//|                                                                  |

//+------------------------------------------------------------------+

double SMMA(double price,double period,int r,int _bars,int instance=0)

  {

   if(ArrayRange(BufferSMMA,0)!=_bars)

      ArrayResize(BufferSMMA,_bars);



   BufferSMMA[r][instance]=price;

   if(r>1 && period>1)

      BufferSMMA[r][instance]=BufferSMMA[r-1][instance]+(price-BufferSMMA[r-1][instance])/period;

   return(BufferSMMA[r][instance]);

  }

//+------------------------------------------------------------------+

//|                                                                  |

//+------------------------------------------------------------------+

double LWMA(double price,double period,int r,int _bars,int instance=0)

  {

   if(ArrayRange(BufferLWMA,0)!=_bars)

      ArrayResize(BufferLWMA,_bars);



   BufferLWMA[r][instance]=price;

   if(period<=1)

      return(price);

   double sumw=period;

   double sum=period*price;



   for(int k=1; k<period && (r-k)>=0; k++)

     {

      double weight=period-k;

      sumw+=weight;

      sum+=weight*BufferLWMA[r-k][instance];

     }

   return(sum/sumw);

  }

//+------------------------------------------------------------------+

//|                                                                  |

//+------------------------------------------------------------------+

#define _tema1 0

#define _tema2 1

#define _tema3 2

double TEMA(double price,double period,int r,int bars,int instance=0)

  {

   if(period<=1) return(price);

   if(ArrayRange(BufferTEMA,0)!=bars)

      ArrayResize(BufferTEMA,bars);

   instance*=3;



   BufferTEMA[r][_tema1+instance]=price;

   BufferTEMA[r][_tema2+instance]=price;

   BufferTEMA[r][_tema3+instance]=price;

   double alpha=2.0/(1.0+period);

   if(r>0)

     {

      BufferTEMA[r][_tema1+instance]=BufferTEMA[r-1][_tema1+instance]+alpha*(price-BufferTEMA[r-1][_tema1+instance]);

      BufferTEMA[r][_tema2+instance]=BufferTEMA[r-1][_tema2+instance]+alpha*(BufferTEMA[r][_tema1+instance]-BufferTEMA[r-1][_tema2+instance]);

      BufferTEMA[r][_tema3+instance]=BufferTEMA[r-1][_tema3+instance]+alpha*(BufferTEMA[r][_tema2+instance]-BufferTEMA[r-1][_tema3+instance]);

     }

   return(BufferTEMA[r][_tema3+instance]+3.0*(BufferTEMA[r][_tema1+instance]-BufferTEMA[r][_tema2+instance]));

  }

//+------------------------------------------------------------------+

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 ---