Author: www.Wolfforex.com, 2025
0 Views
0 Downloads
0 Favorites
BMA_v1
ÿþ//+------------------------------------------------------------------+

//|                                              Band Moving Average |

//|                                    Copyright © 2025 Wolfforex.com|

//|                                        https://www.wolfforex.com |

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

#property copyright "www.Wolfforex.com, 2025"

#property version   "1.06"

#property strict



#property indicator_chart_window

#property indicator_buffers 3

#property indicator_plots   3

#property indicator_color1  clrRed

#property indicator_color2  clrBlue

#property indicator_color3  clrGreen

#property indicator_type1   DRAW_LINE

#property indicator_type2   DRAW_LINE

#property indicator_type3   DRAW_LINE

#property indicator_style1  STYLE_SOLID

#property indicator_style2  STYLE_SOLID

#property indicator_style3  STYLE_SOLID

#property indicator_width1  1

#property indicator_width2  1

#property indicator_width3  1



// Indicator parameters:

input int MA_Period = 49;

input int MA_Shift = 0;

input ENUM_MA_METHOD MA_Method = MODE_SMA;

input double Percentage = 2;



// Indicator buffers:

double ExtMapBuffer1[];

double ExtMapBuffer2[];

double ExtMapBuffer3[];



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

//| Custom indicator initialization function                         |

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

int OnInit()

{

   int    draw_begin;

   string short_name;



   if (MA_Period < 2)

   {

      Print("MA Period should be greater than 1.");

      return(INIT_PARAMETERS_INCORRECT);

   }



   // Drawing settings:

   draw_begin = MA_Period - 1;

   IndicatorSetInteger(INDICATOR_DIGITS, _Digits);



   PlotIndexSetDouble(0, PLOT_EMPTY_VALUE, 0.0);

   PlotIndexSetDouble(1, PLOT_EMPTY_VALUE, 0.0);

   PlotIndexSetDouble(2, PLOT_EMPTY_VALUE, 0.0);



   PlotIndexSetInteger(0, PLOT_SHIFT, MA_Shift);

   PlotIndexSetInteger(1, PLOT_SHIFT, MA_Shift);

   PlotIndexSetInteger(2, PLOT_SHIFT, MA_Shift);

   

   PlotIndexSetInteger(0, PLOT_DRAW_BEGIN, draw_begin);

   PlotIndexSetInteger(1, PLOT_DRAW_BEGIN, draw_begin);

   PlotIndexSetInteger(2, PLOT_DRAW_BEGIN, draw_begin);



   // Indicator short name:

   switch(MA_Method)

   {

      case MODE_SMA  : short_name = "Band SMA("; break;

      case MODE_EMA  : short_name = "Band EMA("; draw_begin = 0; break;

      case MODE_SMMA : short_name = "Band SMMA("; break;

      case MODE_LWMA : short_name = "Band LWMA(";

   }

   IndicatorSetString(INDICATOR_SHORTNAME, short_name + IntegerToString(MA_Period) + ")");



   // Indicator buffers mapping:

   SetIndexBuffer(0, ExtMapBuffer1, INDICATOR_DATA);

   SetIndexBuffer(1, ExtMapBuffer2, INDICATOR_DATA);

   SetIndexBuffer(2, ExtMapBuffer3, INDICATOR_DATA);



   // Initialization done.

   return(INIT_SUCCEEDED);

}



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

//| Data calculation                                                 |

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

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

{

   ArraySetAsSeries(Close, false);



   // Fill buffers with zero values for the first run.

   if (prev_calculated == 0)

   {

      ArrayInitialize(ExtMapBuffer1, 0.0);

      ArrayInitialize(ExtMapBuffer2, 0.0);

      ArrayInitialize(ExtMapBuffer3, 0.0);

   }



   // Not enought bars to use with the given period.

   if (rates_total <= MA_Period) return(0);



   switch(MA_Method)

   {

      case MODE_SMA  : sma(Close, rates_total); break;

      case MODE_EMA  : ema(Close, rates_total);  break;

      case MODE_SMMA : smma(Close, rates_total); break;

      case MODE_LWMA : lwma(Close, rates_total); 

   }



   return(rates_total);

}



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

//| Simple Moving Average                                            |

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

void sma(const double &Close[], const int rates_total)

{

   double sum = 0;

   int pos = 0;



   // Initial accumulation.

   for (int i = 0; i < (MA_Period - 1); i++, pos++) 

      sum += Close[pos];



   // Main calculation loop.

   while (pos < rates_total)

   {

      sum += Close[pos];

      ExtMapBuffer1[pos] = sum / MA_Period;

      ExtMapBuffer2[pos] = (ExtMapBuffer1[pos] / 100) * (100 + Percentage);

      ExtMapBuffer3[pos] = (ExtMapBuffer1[pos] / 100) * (100 - Percentage);

	   sum -= Close[pos - MA_Period + 1];

 	   pos++;

   }

}



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

//| Exponential Moving Average                                       |

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

void ema(const double &Close[], const int rates_total)

{

   double pr = 2.0 / (MA_Period + 1);

   int   pos = 1;



   // Main calculation loop.

   while (pos < rates_total)

   {

      if (pos == 1) ExtMapBuffer1[0] = Close[0];

      ExtMapBuffer1[pos] = Close[pos] * pr + ExtMapBuffer1[pos - 1] * (1 - pr);

      ExtMapBuffer2[pos] = (ExtMapBuffer1[pos] / 100) * (100 + Percentage);

      ExtMapBuffer3[pos] = (ExtMapBuffer1[pos] / 100) * (100 - Percentage);

 	   pos++;

   }

}



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

//| Smoothed Moving Average                                          |

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

void smma(const double &Close[], const int rates_total)

{

   double sum = 0;

   int i;

   int pos = MA_Period;



   // Main calculation loop.

   while (pos < rates_total)

   {

      if (pos == MA_Period)

      {

         // Initial accumulation.

         for(i = 0; i < MA_Period; i++)

         {

            sum += Close[i];

            // Zero initial bars.

            ExtMapBuffer1[i] = 0;

            ExtMapBuffer2[i] = 0;

            ExtMapBuffer3[i] = 0;

         }

      }

      else sum = ExtMapBuffer1[pos - 1] * (MA_Period-1) + Close[pos];

      

      ExtMapBuffer1[pos] = sum / MA_Period;

      ExtMapBuffer2[pos] = (ExtMapBuffer1[pos] / 100) * (100 + Percentage);

      ExtMapBuffer3[pos] = (ExtMapBuffer1[pos] / 100) * (100 - Percentage);

 	   pos++;

   }

}



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

//| Linear Weighted Moving Average                                   |

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

void lwma(const double &Close[], const int rates_total)

{

   double sum = 0.0, lsum = 0.0;

   double price;

   int    i, weight = 0, pos = 0;



   // Initial accumulation.

   for (i = 1; i <= MA_Period; i++, pos++)

   {

      price = Close[pos];

      sum += price * i;

      lsum += price;

      weight += i;

   }



   // Main calculation loop.

   i = pos - MA_Period;

   while (pos < rates_total)

   {

      ExtMapBuffer1[pos] = sum / weight;

      ExtMapBuffer2[pos] = (ExtMapBuffer1[pos] / 100) * (100 + Percentage);

      ExtMapBuffer3[pos] = (ExtMapBuffer1[pos] / 100) * (100 - Percentage);

      if (pos == (rates_total - 1)) break;

      pos++;

      i++;

      price = Close[pos];

      sum = sum - lsum + price * MA_Period;

      lsum -= Close[i];

      lsum += price;

   }

}

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

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