//+------------------------------------------------------------------+
//|                                               Dorsey inertia.mq4 |
//|                                                           mladen |
//+------------------------------------------------------------------+
#property copyright "mladen"
#property link      "mladenfx@gmail.com"

#property indicator_separate_window
#property indicator_buffers    1
#property indicator_color1     Green
#property indicator_width1     2
#property indicator_level1     50
#property indicator_levelcolor DarkSlateGray

//
//
//
//
//

extern int RVIPeriod       = 10;
extern int AvgPeriod       = 14;
extern int SmoothingPeriod = 20;

//
//
//
//
//

double InertiaBuffer[];
double buffers[][5];

//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
//
//
//
//
//

int init()
{
   SetIndexBuffer(0,InertiaBuffer);
      IndicatorShortName("Dorsey inertia ("+RVIPeriod+","+SmoothingPeriod+")");
   SetIndexLabel(0,"Inertia");
   return(0);
}

//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
//
//
//
//
//

#define iHUp 0
#define iHDo 1
#define iLUp 2
#define iLDo 3
#define iRvi 4

//
//
//
//
//

int start()
{
   int counted_bars=IndicatorCounted();
   int limit,r,i;
   
   if(counted_bars<0) return(-1);
   if(counted_bars>0) counted_bars--;
           limit=Bars-counted_bars;
           if (ArrayRange(buffers,0) != Bars) ArrayResize(buffers,Bars);

   //
   //
   //
   //
   //
   
   for(i=limit, r=Bars-limit-1; i>=0; i--,r++)
   {
      double stdDev = iStdDev(NULL,0,RVIPeriod,0,MODE_SMA,PRICE_HIGH,i);
      double u      = 0;
      double d      = 0;
      
         if (High[i]>High[i+1]) u = stdDev;
         if (High[i]<High[i+1]) d = stdDev;
         
         buffers[r][iHUp] = ((AvgPeriod-1.0)*buffers[r-1][iHUp]+u)/AvgPeriod;
         buffers[r][iHDo] = ((AvgPeriod-1.0)*buffers[r-1][iHDo]+d)/AvgPeriod;

      //
      //
      //
      //
      //
      
      stdDev = iStdDev(NULL,0,RVIPeriod,0,MODE_SMA,PRICE_LOW,i);
      u      = 0;
      d      = 0;
            
         if (Low[i]>Low[i+1]) u = stdDev;
         if (Low[i]<Low[i+1]) d = stdDev;
         
         buffers[r][iLUp] = ((AvgPeriod-1.0)*buffers[r-1][iLUp]+u)/AvgPeriod;
         buffers[r][iLDo] = ((AvgPeriod-1.0)*buffers[r-1][iLDo]+d)/AvgPeriod;
        
      //
      //
      //
      //
      //
 
         double rvih = 0.0;
         double rvil = 0.0;

            if((buffers[r][iHUp]+buffers[r][iHDo]) != 0.0) rvih = 100.00*buffers[r][iHUp]/(buffers[r][iHUp]+buffers[r][iHDo]);
            if((buffers[r][iLUp]+buffers[r][iLDo]) != 0.0) rvil = 100.00*buffers[r][iLUp]/(buffers[r][iLUp]+buffers[r][iLDo]);
              
         buffers[r][iRvi] = (rvih+rvil)/2.0;

      //
      //
      //
      //
      //
               
         double sum = 0;
            for (int k=0; k<SmoothingPeriod; k++) sum += buffers[r-k][iRvi];
                               InertiaBuffer[i] = sum / SmoothingPeriod;
   }
   
   //
   //
   //
   //
   //
   
   return(0);
}