Bollinger Bandwidth indicator + SMA (50);

 

Hello,

this is my first post. A greeting all and congratulations for the good work of the forum.
I have a small problem. I built the Bollinger Bandwidth indicator + SMA (50); it works, but the moving average has a poor stability. What is the error in the code? You can help me?

Thank you in advance.

(Excuse my bad English; is not my native language).

The Code:


//+------------------------------------------------------------------+
//| BBwidth+SMA(50).mq4 |
//| |
//| |
//+------------------------------------------------------------------+
#property copyright ""
#property link ""

#property indicator_separate_window
#property indicator_buffers 2
#property indicator_color1 Red
#property indicator_color2 LimeGreen

//---- input parameters
extern int BB_period = 20;
extern int BB_std_deviation = 2;
extern int MA_period = 50;

//---- buffers
double ExtMapBuffer1[]; //BollingerBandWidth
double ExtMapBuffer2[]; //BandWidthSmoothing
double Upper_Band;
double Middle_Band;
double Lower_Band;

//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+

int init()
{
//---- BollingerBandWidth
SetIndexStyle(0, DRAW_LINE);
SetIndexBuffer(0, ExtMapBuffer1);
SetIndexDrawBegin(0, BB_period);

//---- BandWidthSmoothing
SetIndexStyle(1, DRAW_LINE);
SetIndexBuffer(1, ExtMapBuffer2);
SetIndexDrawBegin(1, MA_period);

return (0);
}

//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+

int deinit()
{
return (0);
}

//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+

int start()
{
int limit;
int counted_bars=IndicatorCounted();
if(counted_bars<0) return(-1);
if(counted_bars>0) counted_bars--;
limit=Bars-counted_bars;
for(int i=0; i<limit; i++)
{
//---- BollingerBand configuration
Upper_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_UPPER, i);
Middle_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_BASE, i);
Lower_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_LOWER, i);

//---- BollingerBandWidth configuration
ExtMapBuffer1[i] = ((Upper_Band - Lower_Band) / Middle_Band) * 100.0;

//---- BandWidthSmoothing configuration
ExtMapBuffer2[i]=iMAOnArray(ExtMapBuffer1,0,MA_period,0,MODE_SMA,i);
}
return (0);
}
//+------------------------------------------------------------------+

 
What is "poor stability"
 
When I open a chart, the moving average is drawn only under the last two candles.
If I change profile (file menu > profile), I must always go to the metaeditor, open BBwidth+SMA indicator code and compile it. Only then it the moving average is drawn completely.
If I still change profile I have always repeat the same thing.
 

There appears to be two problems:


1) BB (in my case) is returning zero values near towards the end of the array, so I just fudge it with:

limit=Bars-counted_bars-50;


2) ExtMapBuffer2[i] needs to be calculated after the first for-loop so that all values of ExtMapBuffer1 are populated before you can do an MA on them.


} // This bracket has been moved here to close the first for-loop

//---- BandWidthSmoothing configuration

for(i=0; i<limit; i++)
ExtMapBuffer2[i]=iMAOnArray(ExtMapBuffer1,0,MA_period,0,MODE_SMA,i);

return (0);
}

 

blogzr3, thank you for your answer.
I made the correction, but now I do not see anything (the indicator is completely empty).
Maybe I not understand.

Here are the correct code piece:

//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+

int start()
{
int limit;
int counted_bars=IndicatorCounted();
if(counted_bars<0) return(-1);
if(counted_bars>0) counted_bars--;
limit=Bars-counted_bars-50; //....First correction!!!
for(int i=0; i<limit; i++)
{
//---- BollingerBand configuration
Upper_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_UPPER, i);
Middle_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_BASE, i);
Lower_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_LOWER, i);

//---- BollingerBandWidth configuration
ExtMapBuffer1[i] = ((Upper_Band - Lower_Band) / Middle_Band) * 100.0;

//---- BandWidthSmoothing configuration
for(i=0; i<limit; i++) // ....Second correction!!!
ExtMapBuffer2[i]=iMAOnArray(ExtMapBuffer1,0,MA_period,0,MODE_SMA,i);

return (0);
}
}
//+------------------------------------------------------------------+

 

Third correction:

//---- BollingerBandWidth configuration
ExtMapBuffer1[i] = ((Upper_Band - Lower_Band) / Middle_Band) * 100.0;


} // Bracket from below move here


//---- BandWidthSmoothing configuration
for(i=0; i<limit; i++) // ....Second correction!!!
ExtMapBuffer2[i]=iMAOnArray(ExtMapBuffer1,0,MA_period,0,MODE_SMA,i);


return (0);
// Take bracket from here and move it up.
}
//+------------------------------------------------------------------+

 
for(int i=0; i<limit; i++)
{
   //---- BollingerBand configuration
   Upper_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_UPPER, i);
   Middle_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_BASE, i);
   Lower_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_LOWER, i);

   //---- BollingerBandWidth configuration
   ExtMapBuffer1[i] = ((Upper_Band - Lower_Band) / Middle_Band) * 100.0;

   //---- BandWidthSmoothing configuration
   for(i=0; i<limit; i++) // ....Second correction!!!
   ExtMapBuffer2[i]=iMAOnArray(ExtMapBuffer1,0,MA_period,0,MODE_SMA,i);

   return (0);
   }
}
Change to:
for(int i=0; i<limit; i++)
{
  //---- BollingerBand configuration
  Upper_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_UPPER, i);
  Middle_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_BASE, i);
  Lower_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_LOWER, i);

  //---- BollingerBandWidth configuration
  ExtMapBuffer1[i] = ((Upper_Band - Lower_Band) / Middle_Band) * 100.0;
}
//---- BandWidthSmoothing configuration
for(i=0; i<limit; i++) // ....Second correction!!!
  ExtMapBuffer2[i]=iMAOnArray(ExtMapBuffer1,0,MA_period,0,MODE_SMA,i);
}
return (0);

 
Ah... Finally I understand!
Now the indicator works very well.
Thanks guys, you are friends!
 

Hi,

sorry, I take back your kindness.

I have corrected the indicator code and I added a alert, but often hangs and delays of some candles.

You can help my to understand the error?

Thank you.

Here are the current code:

//+------------------------------------------------------------------+
//| BBwidth + SMA + Alert.mq4 |
//| |
//| |
//+------------------------------------------------------------------+

#property copyright ""
#property link ""

#property indicator_separate_window
#property indicator_buffers 2
#property indicator_color1 LimeGreen
#property indicator_color2 Red

//---- input parameters
extern int BB_period = 20;
extern int BB_std_deviation = 2;
extern int MA_period = 50;

//---- buffers
double ExtMapBuffer1[]; //BollingerBandWidth
double ExtMapBuffer2[]; //BandWidthSmoothing
double Upper_Band;
double Middle_Band;
double Lower_Band;

//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+

int init()
{
IndicatorBuffers(2);
//---- BollingerBandWidth
SetIndexStyle(0, DRAW_LINE);
SetIndexBuffer(0, ExtMapBuffer1);
SetIndexLabel(0, "BBwidth");
SetIndexDrawBegin(0, BB_period);

//---- BandWidthSmoothing
SetIndexStyle(1, DRAW_LINE );
SetIndexBuffer(1, ExtMapBuffer2);
SetIndexLabel(1, "BBwSmooth");
SetIndexDrawBegin(1, MA_period);

return (0);
}

//---- Bar number the alert to be searched by
#define SIGNAL_BAR 1

//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+

int deinit()
{
return (0);
}

//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+

int start()
{
int limit;
int counted_bars=IndicatorCounted();
if(counted_bars<0) return(-1);
if(counted_bars>0) counted_bars--;
limit=Bars-counted_bars-50;
for(int i=0; i<limit; i++)
{
//---- BollingerBand configuration
Upper_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_UPPER, i);
Middle_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_BASE, i);
Lower_Band = iBands(Symbol(), 0, BB_period, BB_std_deviation, 0, PRICE_CLOSE, MODE_LOWER, i);

//---- BollingerBandWidth configuration
ExtMapBuffer1[i] = ((Upper_Band - Lower_Band) / Middle_Band) * 100.0;
}
//---- BandWidthSmoothing configuration
for(i=0; i<limit; i++)
ExtMapBuffer2[i]=iMAOnArray(ExtMapBuffer1,0,MA_period,0,MODE_SMA,i);

//+------------------------------------------------------------------+
//| The Alert definition |
//+------------------------------------------------------------------+

static int PrevSignal = 0, PrevTime = 0;

if(SIGNAL_BAR > 0 && Time[0] <= PrevTime )
return(0);

PrevTime = Time[0];

if(PrevSignal <= 0)
{
if(ExtMapBuffer1[SIGNAL_BAR] - ExtMapBuffer2[SIGNAL_BAR] > 0 &&
ExtMapBuffer2[SIGNAL_BAR+1] - ExtMapBuffer1[SIGNAL_BAR+1] >= 0)
{
PrevSignal = 1;
Alert ("BBwidth (", Symbol(), ", ", Period(), ") - More Volatility!");
}
}

return (0);
}

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