RSIOMA Bollinger Bands

Download script
Author: Matt Edmonds
RSIOMA Bollinger Bands

This technical indicator is designed to help traders identify momentum, overbought/oversold conditions, and trend reversals by analyzing price action through a multi-layered mathematical approach. Instead of simply looking at raw price, it processes the data into three distinct layers of analysis: momentum smoothing, specific signal triggers, and volatility boundaries.

Core Logic Breakdown

1. Momentum Smoothing (The Foundation) The script begins by calculating a specialized version of the Relative Strength Index (RSI). Rather than using standard price fluctuations, it uses an Exponential Moving Average (EMA) to smooth out the data first. This helps filter out "market noise" and focuses on the underlying trend of the momentum. It tracks both positive and negative movements independently to determine the relative strength of the market's current direction.

2. Signal Triggers (The Action Points) Once the smoothed momentum is established, the script looks for specific price behaviors to highlight potential entry or exit points:

  • Oversold Recovery: It identifies instances where momentum is very low (below a set threshold) but has started to tick upward, suggesting a potential "bottom" may have been reached.
  • Overbought Exhaustion: It looks for moments where momentum is very high but has started to dip, suggesting the market may be "exhausted" and due for a pullback.
  • Trend Strength: The logic also monitors whether the momentum is staying above or below the mid-point (50), helping the user distinguish between a strong prevailing trend and a neutral market.

3. Volatility Boundaries (Bollinger Bands) To provide further context, the script applies Bollinger Bands directly onto the smoothed momentum line. These bands act as "envelopes":

  • The Middle Line: Represents the average momentum over a specific period.
  • Upper and Lower Bands: These measure the volatility of the momentum itself. When the momentum moves outside of these bands, it indicates extreme price velocity, which can be a sign of a breakout or an impending trend reversal.

Summary for the Trader

In practical terms, this tool doesn't just tell you if the price is going up or down; it tells you how strongly it is moving, whether that movement is reaching an unsustainable extreme (overbought/oversold), and when that momentum is beginning to lose its steam. By combining smoothed momentum with volatility bands, it aims to provide a clearer picture of market "health" than a standard price chart alone.

Indicators Used
Moving average indicator
Miscellaneous
Implements a curve of type %1
13 Views
0 Downloads
0 Favorites
RSIOMA Bollinger Bands
#property copyright "Matt Edmonds"
#property link      "matt.edmonds@gmail.com"

#property indicator_separate_window
#property indicator_minimum -10
#property indicator_maximum 100
#property indicator_buffers 10
#property indicator_color1 Blue
#property indicator_color2 Red
#property indicator_color3 Green
#property indicator_color4 Magenta
#property indicator_color5 DodgerBlue
#property indicator_color6 White
#property indicator_color7 White
#property indicator_color8 White




//---- input parameters
extern int RSIOMA = 14;

extern int BuyTrigger = 80;
extern int SellTrigger = 20;
extern int MainTrendLong = 50;
extern int MainTrendShort = 50;
extern int BollingerPeriod=10;
extern int BollingerDeviation = 1;
extern int BollingerShift = 0;
extern int BarsToUse = 200;


//---- buffers
double RSIBuffer[];
double PosBuffer[];
double NegBuffer[];

double BollingerUpper[];
double BollingerLower[];
double BollingerMiddle[];

double bdn[],bup[];
double sdn[],sup[];



//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
   string short_name;
//---- 2 additional buffers are used for counting.
     
   
   IndicatorBuffers(10);
   
   SetIndexBuffer(0,RSIBuffer);
   SetIndexBuffer(2,bup);
   SetIndexBuffer(1,bdn);
   SetIndexBuffer(3,sdn);
   SetIndexBuffer(4,sup);
   SetIndexBuffer(7,BollingerUpper);
   SetIndexBuffer(8,BollingerLower);
   SetIndexBuffer(9,BollingerMiddle);
   SetIndexLabel(9,"Bollinger Middle");
   
   SetIndexStyle(0,DRAW_LINE,STYLE_SOLID,3);
   SetIndexStyle(2,DRAW_HISTOGRAM,STYLE_SOLID,1);
   SetIndexStyle(1,DRAW_HISTOGRAM,STYLE_SOLID,1);
   SetIndexStyle(3,DRAW_HISTOGRAM,STYLE_SOLID,1);
   SetIndexStyle(4,DRAW_HISTOGRAM,STYLE_SOLID,1);
   SetIndexStyle(7,DRAW_LINE,STYLE_SOLID,1);
   SetIndexStyle(8,DRAW_LINE,STYLE_SOLID,1);
   SetIndexStyle(9,DRAW_LINE,STYLE_DOT,1);

   
   SetIndexBuffer(5,PosBuffer);
   SetIndexBuffer(6,NegBuffer);
   
   short_name="RSIOMA("+RSIOMA+")";
   IndicatorShortName(short_name);

   SetIndexDrawBegin(0,RSIOMA);
//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Relative Strength Index                                          |
//+------------------------------------------------------------------+
int start()
  {
  SetLevelValue(0, BuyTrigger);
   SetLevelValue(1, SellTrigger);
   SetLevelValue(2, MainTrendLong);
   SetLevelValue(3, MainTrendShort);
   
   SetLevelStyle(STYLE_DOT, 1, Yellow);
   
   int    i,counted_bars=IndicatorCounted();
   double rel,negative,positive;
//----
   if(Bars<=RSIOMA) return(0);
//---- initial zero
   if(counted_bars<1)
      for(i=1;i<=RSIOMA;i++) RSIBuffer[Bars-i]=0.0;
//----
   i=Bars-RSIOMA-1;
   if(counted_bars>=RSIOMA) i=Bars-counted_bars-1;
   while(i>=0)
     {
      double sumn=0.0,sump=0.0;
      if(i==Bars-RSIOMA-1)
        {
         int k=Bars-2;
         //---- initial accumulation
         while(k>=i)
           {
            
            double cma = iMA(Symbol(),0,RSIOMA,0,MODE_EMA,PRICE_CLOSE,k);
            double pma = iMA(Symbol(),0,RSIOMA,0,MODE_EMA,PRICE_CLOSE,k+1);
            
            rel=cma-pma;
            
            if(rel>0) sump+=rel;
            else      sumn-=rel;
            k--;
           }
         positive=sump/RSIOMA;
         negative=sumn/RSIOMA;
        }
      else
        {
         //---- smoothed moving average
         double ccma = iMA(Symbol(),0,RSIOMA,0,MODE_EMA,PRICE_CLOSE,i);
         double ppma = iMA(Symbol(),0,RSIOMA,0,MODE_EMA,PRICE_CLOSE,i+1);
            
         rel=ccma-ppma;
         
         if(rel>0) sump=rel;
         else      sumn=-rel;
         positive=(PosBuffer[i+1]*(RSIOMA-1)+sump)/RSIOMA;
         negative=(NegBuffer[i+1]*(RSIOMA-1)+sumn)/RSIOMA;
        }
      PosBuffer[i]=positive;
      NegBuffer[i]=negative;
      if(negative==0.0) RSIBuffer[i]=0.0;
      else
      {
          RSIBuffer[i]=100.0-100.0/(1+positive/negative);
          
          bdn[i] = 0;
          bup[i] = 0;
          sdn[i] = 0;
          sup[i] = 0;
          
          if(RSIBuffer[i]>MainTrendLong)
          bup[i] = -10;
          
          if(RSIBuffer[i]<MainTrendShort)
          bdn[i] = -10;
          
          if(RSIBuffer[i]<20 && RSIBuffer[i]>RSIBuffer[i+1])
          sup[i] = -10;
          
          if(RSIBuffer[i]>80 && RSIBuffer[i]<RSIBuffer[i+1])
          sdn[i] = -10;
            
          
      }    
      i--;
     }
//----
   for(i=0; i<BarsToUse; i++)
   {  
     BollingerLower[i] = iBandsOnArray(RSIBuffer,0,BollingerPeriod,BollingerDeviation,BollingerShift,MODE_LOWER,i); 
     BollingerUpper[i] = iBandsOnArray(RSIBuffer,0,BollingerPeriod,BollingerDeviation,BollingerShift,MODE_UPPER,i); 
     BollingerMiddle[i] = iBandsOnArray(RSIBuffer,0,BollingerPeriod,BollingerDeviation,BollingerShift,MODE_MAIN,i); 
   }   
   
   return(0);
  }

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

Comments