Rocket RSI (pivots)

Author: © mladen, 2019

This script is designed for the MetaTrader platform and calculates and displays a modified Relative Strength Index (RSI) called "Rocket RSI," along with potential support and resistance levels on a price chart. Here's a breakdown of how it works, avoiding technical jargon:

1. Core Functionality: The "Rocket RSI"

  • What it does: At its heart, the script calculates a "Rocket RSI," which is a momentum indicator designed to measure the speed and change of price movements.

  • How it works:

    • It looks at price data over a certain period (defined by the user as "Period").
    • It applies some smoothing to that data as defined by the user in the smoothing input
    • It calculates momentum based on the change in price over the defined time periods.
    • It filters the momentum to remove noise.
    • Then it uses the smoothed momentum values to calculate the RSI.
  • Optional Transformation (Fisher Transform): The script has an option to transform the RSI values using the Fisher Transform. The Fisher Transform converts the RSI values to create a more normalized distribution, this can help identify potential overbought and oversold conditions. If this option is disabled, the script simply uses the standard "Rocket RSI" value.

2. Support and Resistance Levels

  • What they are: Support and resistance levels are price levels on a chart where the price tends to find support (a floor) or resistance (a ceiling). Traders use these levels to make decisions about where to enter or exit trades.

  • How they're calculated:

    • The script calculates these levels based on pivot points, which are calculated based on the high, low and close prices over a user-defined time frame.
    • The script calculates the high, low and close for the specified time frame interval.
    • The script then uses the calculated values to compute the support and resistance lines.
  • Display Options: The script allows you to choose how many support and resistance levels to display on the chart: only the pivot point, the pivot point + one level of support/resistance, two levels or three levels.

3. User-Adjustable Settings (Inputs)

The script has several settings that you can adjust to customize its behavior:

  • Time Frame: Determines what time frame the pivot points are derived from. If a higher timeframe is selected, the script looks at larger periods of time to calculate the high, low, and close price, giving a more zoomed out view on the market.

  • RSI Period: This is the number of past price periods used in the Rocket RSI calculation. Shorter periods make the indicator more sensitive to recent price changes, while longer periods make it smoother.

  • Smoothing: Sets the level of smoothing applied to the momentum calculation within the "Rocket RSI". Higher smoothing makes it less sensitive to small price fluctuations.

  • Price: Determines what price (e.g., close, open, high, low) is used as the basis for the RSI calculation.

  • Calculation Mode: Chooses whether to calculate the "Rocket RSI" alone or to apply the Fisher Transform.

  • Colors: Allows you to set the colors of the support, resistance, and pivot point lines for visual clarity.

  • Display Type: Controls how many support and resistance levels are displayed, ranging from just the pivot point to the pivot point plus three levels of support and resistance.

In summary: This script combines a custom RSI calculation ("Rocket RSI") with pivot point-based support and resistance levels, providing traders with information about momentum and potential price turning points. You can adjust the various settings to fine-tune the script to your specific trading style and preferences.

10 Views
0 Downloads
0 Favorites
Rocket RSI (pivots)
ÿþ//------------------------------------------------------------------

#property copyright "© mladen, 2019"

#property link      "mladenfx@gmail.com"

#property version   "1.00"

//------------------------------------------------------------------

#property indicator_separate_window

#property indicator_buffers 9

#property indicator_plots   8

#property indicator_label8  "Rocket RSI"

#property indicator_type8   DRAW_COLOR_LINE

#property indicator_color8  clrSilver,clrMediumSeaGreen,clrOrangeRed

#property indicator_width8  2



//

//---

//



enum enTimeFrames

{

   tf_cu  = PERIOD_CURRENT, // Current time frame

   tf_m1  = PERIOD_M1,      // 1 minute

   tf_m2  = PERIOD_M2,      // 2 minutes

   tf_m3  = PERIOD_M3,      // 3 minutes

   tf_m4  = PERIOD_M4,      // 4 minutes

   tf_m5  = PERIOD_M5,      // 5 minutes

   tf_m6  = PERIOD_M6,      // 6 minutes

   tf_m10 = PERIOD_M10,     // 10 minutes

   tf_m12 = PERIOD_M12,     // 12 minutes

   tf_m15 = PERIOD_M15,     // 15 minutes

   tf_m20 = PERIOD_M20,     // 20 minutes

   tf_m30 = PERIOD_M30,     // 30 minutes

   tf_h1  = PERIOD_H1,      // 1 hour

   tf_h2  = PERIOD_H2,      // 2 hours

   tf_h3  = PERIOD_H3,      // 3 hours

   tf_h4  = PERIOD_H4,      // 4 hours

   tf_h6  = PERIOD_H6,      // 6 hours

   tf_h8  = PERIOD_H8,      // 8 hours

   tf_h12 = PERIOD_H12,     // 12 hours

   tf_d1  = PERIOD_D1,      // daily

   tf_w1  = PERIOD_W1,      // weekly

   tf_mn  = PERIOD_MN1,     // monthly

   tf_cp1 = -1,             // Next higher time frame

   tf_cp2 = -2,             // Second higher time frame

   tf_cp3 = -3              // Third higher time frame

};

input enTimeFrames       inpTimeFrame = tf_h4;             // Time frame

input int                inpPeriod    = 14;                // Period

input int                inpSmooth    = 50;                // Smoothing

input ENUM_APPLIED_PRICE inpPrice     = PRICE_CLOSE;       // Price

enum enCalcMode

{

   calc_fisher  = 0, // Calculate fisher transform of "rocket" rsi

   calc_regular = 1  // Calculate "rocket" rsi only

};

input enCalcMode         inpCalcMode  = calc_fisher;       // Calculating mode

input color              inpColorSup  = clrOrangeRed;      // Support color

input color              inpColorRes  = clrMediumSeaGreen; // Resistance color

input color              inpColorPiv  = clrGray;           // Resistance color

enum enDisplayType

{

   type_1=0, // Display pivot only

   type_2=1, // Display pivot + SR 1

   type_3=2, // Display pivot + SR 1,2

   type_4=3, // Display pivot + SR 1,2,3

};

input enDisplayType inpDisplayType = type_2; // Display type



//

//---

//



double val[],valc[],sup1[],sup2[],sup3[],res1[],res2[],res3[],piv[];

ENUM_TIMEFRAMES _pivotsTimeFrame;



//------------------------------------------------------------------ 

//  Custom indicator initialization function

//------------------------------------------------------------------

//

//---

//



int OnInit()

{

   //

   //---- indicator buffers mapping

   //

         SetIndexBuffer(0,sup3,INDICATOR_DATA);

         SetIndexBuffer(1,sup2,INDICATOR_DATA);

         SetIndexBuffer(2,sup1,INDICATOR_DATA);

         SetIndexBuffer(3,piv ,INDICATOR_DATA);

         SetIndexBuffer(4,res1,INDICATOR_DATA);

         SetIndexBuffer(5,res2,INDICATOR_DATA);

         SetIndexBuffer(6,res3,INDICATOR_DATA);

         SetIndexBuffer(7,val ,INDICATOR_DATA);

         SetIndexBuffer(8,valc,INDICATOR_COLOR_INDEX);

            for (int i=0; i<7; i++)

            {

               switch (i)

               {

                  case 0 : 

                  case 1 : 

                  case 2 : PlotIndexSetInteger(i,PLOT_LINE_COLOR,inpColorSup); break;

                  case 3 : PlotIndexSetInteger(i,PLOT_LINE_COLOR,inpColorPiv); break;

                  case 4 : 

                  case 5 : 

                  case 6 : PlotIndexSetInteger(i,PLOT_LINE_COLOR,inpColorRes); break;

               }

               PlotIndexSetInteger(i,PLOT_DRAW_TYPE,DRAW_LINE);                

               PlotIndexSetInteger(i,PLOT_LINE_STYLE,STYLE_DOT);

               PlotIndexSetInteger(i,PLOT_SHOW_DATA,false);

            }

            

            iRocketRsi.init(inpPeriod,inpSmooth,inpCalcMode);

            _pivotsTimeFrame = MathMax(_Period,timeFrameGet(inpTimeFrame));

   //            

   //----

   //

 

   IndicatorSetString(INDICATOR_SHORTNAME,timeFrameToString(_pivotsTimeFrame)+" Rocket RSI ("+(string)inpPeriod+","+(string)inpSmooth+")");

   return(INIT_SUCCEEDED);

}



//------------------------------------------------------------------

//  Custom indicator iteration function

//------------------------------------------------------------------

//

//---

//



#define _setPrice(_priceType,_where,_index) { \

   switch(_priceType) \

   { \

      case PRICE_CLOSE:    _where = close[_index];                                              break; \

      case PRICE_OPEN:     _where = open[_index];                                               break; \

      case PRICE_HIGH:     _where = high[_index];                                               break; \

      case PRICE_LOW:      _where = low[_index];                                                break; \

      case PRICE_MEDIAN:   _where = (high[_index]+low[_index])/2.0;                             break; \

      case PRICE_TYPICAL:  _where = (high[_index]+low[_index]+close[_index])/3.0;               break; \

      case PRICE_WEIGHTED: _where = (high[_index]+low[_index]+close[_index]+close[_index])/4.0; break; \

      default : _where = 0; \

   }}



//

//---

//



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

{

   static int    prev_i=-1;

   static double prev_max=0,prev_min=0,prev_close=0;



   //

   //

   //

   

   int i= prev_calculated-1; if (i<0) i=0; for (; i<rates_total && !_StopFlag; i++)

   {

      double _price; _setPrice(inpPrice,_price,i);

      val[i]  = iRocketRsi.caculate(_price,i,rates_total);

      valc[i] = (i>0) ? (val[i]>val[i-1]) ? 1 : (val[i]<val[i-1]) ? 2 : valc[i-1]: 0;

      sup1[i] = sup2[i] = sup3[i] = res1[i] = res2[i] = res3[i] = EMPTY_VALUE;

      

      //

      //

      //

      

         if (prev_i!=i)

         {

            prev_i = i; 

               datetime _startTime = iTime(_Symbol,_pivotsTimeFrame,iBarShift(_Symbol,_pivotsTimeFrame,time[i])+1);

               datetime _endTime   = iTime(_Symbol,_pivotsTimeFrame,iBarShift(_Symbol,_pivotsTimeFrame,time[i]));

               int      _startBar  = iBarShift(_Symbol,_Period,_startTime);

               int      _endBar    = iBarShift(_Symbol,_Period,_endTime);

               if (_endBar < _startBar) 

               {

                  int _period = _startBar-_endBar;

                     prev_max = val[ArrayMaximum(val,rates_total-_startBar-1,_period)];

                     prev_min = val[ArrayMinimum(val,rates_total-_startBar-1,_period)];

               }                     

               prev_close = (_endBar>0) ? val[rates_total-_endBar-1] : val[i];

         }

         

         //

         //---

         //

         

            double range = (prev_max-prev_min);

            double pivot = (prev_max+prev_min+prev_close)/3.0;

            switch (inpDisplayType)

            {

               case 3 : 

                        res3[i] = pivot*2.0+prev_max-prev_min*2.0;

                        sup3[i] = pivot*2.0+prev_min-prev_max*2.0;

               case 2 :                         

                        res2[i] = pivot    +range;

                        sup2[i] = pivot    -range;

               case 1 :                         

                        res1[i] = pivot*2.0-prev_min;

                        sup1[i] = pivot*2.0-prev_max;

               case 0 : piv[i]  = pivot;

            }               

   }

   return(i);

}



//------------------------------------------------------------------

//  Custom function(s)

//------------------------------------------------------------------

//

//---

//



class CRocketRsi

{

   private :

      int    m_mode; 

      int    m_period;

      double m_coeff1;

      double m_coeff2;

      double m_coeff3;

      int    m_arraySize;

         struct sRocketRsiArrayStruct

         {

            double value;

            double momentum;

            double filter;

            double diffp;

            double diffn;

            double sump;

            double sumn;

         };

      sRocketRsiArrayStruct m_array[];         



   public :

      CRocketRsi() : m_arraySize(-1) {};

     ~CRocketRsi()                   { ArrayFree(m_array); };

     

      ///

      ///

      ///

     

      bool init(int period, int smooth, int mode)

      {

            m_period = (period>1) ? period : 1;

            m_mode   = mode;

               double _smooth = (smooth>1) ? smooth : 1;

               double a    = MathExp(-1.414*M_PI/_smooth);

                  m_coeff2 = 2*a*MathCos(1.414*M_PI/_smooth);

                  m_coeff3 = -a*a;

                  m_coeff1 = 1-m_coeff2-m_coeff3;      



            //

            //

            //

                              

            return(true); 

      }



      double caculate(double value, int i, int bars)

      {

         if (m_arraySize<bars) { m_arraySize = ArrayResize(m_array,bars+500); if (m_arraySize<bars) return(0); }

      

         m_array[i].value=value;

                          

         //

         //

         //

         

         if (i>m_period)

            {

               m_array[i].momentum = m_array[i].value-m_array[(i-m_period+1)%m_arraySize].value;

               m_array[i].filter   = m_coeff1*((m_array[i].momentum+m_array[i-1].momentum)/2.0) + m_coeff2*m_array[i-1].filter + m_coeff3*m_array[(i-2)%m_arraySize].filter;

                        if (m_array[i].filter > m_array[i-1].filter)

                              { m_array[i].diffp = m_array[i].filter - m_array[i-1].filter; m_array[i].diffn = 0; }

                        else  { m_array[i].diffn = m_array[i-1].filter - m_array[i].filter; m_array[i].diffp = 0; }

               m_array[i].sump = m_array[i-1].sump + m_array[i].diffp - m_array[i-m_period].diffp;

               m_array[i].sumn = m_array[i-1].sumn + m_array[i].diffn - m_array[i-m_period].diffn;

            }

         else

            {

               m_array[i].momentum = m_array[i].value-m_array[0].value;

               m_array[i].filter   = (i>1) ? m_coeff1*((m_array[i].momentum+m_array[i-1].momentum)/2) + m_coeff2*m_array[i-1].filter + m_coeff3*m_array[(i-2)%m_arraySize].filter : m_array[i].momentum;

               m_array[i].diffp    = (i>0) ? (m_array[i].filter>m_array[i-1].filter) ? m_array[i].filter - m_array[i-1].filter : 0 : 0;

               m_array[i].diffn    = (i>0) ? (m_array[i].filter<m_array[i-1].filter) ? m_array[i-1].filter - m_array[i].filter : 0 : 0;

            

               //

               //

               //

            

               m_array[i].sump = m_array[i].diffp;

               m_array[i].sumn = m_array[i].diffn;

                  for (int k=1; k<m_period && i>=k; k++)

                  {

                     m_array[i].sump += m_array[i-k].diffp;

                     m_array[i].sumn += m_array[i-k].diffn;

                  }

            }



            //

            //

            //

         

            double denom = m_array[i].sump+m_array[i].sumn;

            double rsi   = (denom!=0) ? (m_array[i].sump-m_array[i].sumn)/denom : 0;

               if (m_mode==0)

               {

                  if (rsi >  0.999) rsi =  0.999;

                  if (rsi < -0.999) rsi = -0.999;

                     return(0.5*MathLog((1.0+rsi)/(1.0-rsi)));

               }         

               else return(rsi);

      }

};

CRocketRsi iRocketRsi;



//

//---

//



ENUM_TIMEFRAMES _tfsPer[]={PERIOD_M1,PERIOD_M2,PERIOD_M3,PERIOD_M4,PERIOD_M5,PERIOD_M6,PERIOD_M10,PERIOD_M12,PERIOD_M15,PERIOD_M20,PERIOD_M30,PERIOD_H1,PERIOD_H2,PERIOD_H3,PERIOD_H4,PERIOD_H6,PERIOD_H8,PERIOD_H12,PERIOD_D1,PERIOD_W1,PERIOD_MN1};

string          _tfsStr[]={"1 minute","2 minutes","3 minutes","4 minutes","5 minutes","6 minutes","10 minutes","12 minutes","15 minutes","20 minutes","30 minutes","1 hour","2 hours","3 hours","4 hours","6 hours","8 hours","12 hours","daily","weekly","monthly"};



//

//---

//



string timeFrameToString(int period)

{

   if(period==PERIOD_CURRENT)

      period=_Period;

   int i; for(i=0;i<ArraySize(_tfsPer);i++) if(period==_tfsPer[i]) break;

   return(_tfsStr[i]);

}



//

//---

//



ENUM_TIMEFRAMES timeFrameGet(int period)

{

   int _shift = (period<0 ? MathAbs(period) : 0); if (period<=0) period=_Period;

   int i; for(i=0;i<ArraySize(_tfsPer);i++) if(period==_tfsPer[i]) break;

      return(_tfsPer[(int)MathMin(i+_shift,ArraySize(_tfsPer)-1)]);

}

//------------------------------------------------------------------

Comments