MACD_Color Indicator MQL5 Code -
Hassam - 09-28-2022
I use MACD a lot in my trading. I use MACD as a momentum indicator. I need to now when the momentum is becoming strong and when the momentum is becoming weak. The default MACD indicator provided on MT5 has no color. So I have coded a new indicator that uses the default MT5 MACD indicator and colors the bar. When the momentum is strong in up direction it will color the bar as green and when the momentum is strong in the down direction it will color the bar in red. When the momentum increase and the MACD is below zero the bar will be light green and when the momentum increases and MACD is above zero, the bar will be dark green. In the same manner, when the momentum increases in down direction the MACD is above zero, bar color will be light red and when momentum increases in down direction and MACD is below zero, bar color will be dark red. Below is the MQL5 code for this MACD_Color Indicator:
Code:
//+------------------------------------------------------------------+
//| MACD_Color.mq5 |
//| Copyright 2019, Ahmad Hassam |
//| https://www.doubledoji.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2019, Ahmad Hassam"
#property link "https://www.doubledoji.com"
#property version "1.00"
#property description "Moving Average Convergence/Divergence"
#property indicator_separate_window
#property indicator_buffers 4
#property indicator_plots 2
//--- plot MACD HISTOGRAM
#property indicator_label1 "MACD"
#property indicator_type1 DRAW_COLOR_HISTOGRAM
#property indicator_color1 clrLightGreen, clrDarkGreen, clrPink, clrRed
#property indicator_style1 STYLE_SOLID
#property indicator_width1 3
//--- plot MACD Signal
#property indicator_label2 "Signal"
#property indicator_type2 DRAW_LINE
#property indicator_color2 clrRed
#property indicator_style2 STYLE_SOLID
#property indicator_width2 2
//--- input parameters
input int fastEMA=12;
input int slowEMA=26;
input int signalPeriod=9;
input ENUM_APPLIED_PRICE MAPrice = PRICE_CLOSE;
//--- indicator buffers
double macd_main[]; //MACD Histogram
double macd_color[]; //MACD Histogram bar colors
double macd_signal[]; //MACD Signal
double macd_signal_color[];
//--declare MACD Handle
int macdHandle;
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int OnInit()
{
//--- indicator subwindow label
IndicatorSetString(INDICATOR_SHORTNAME,
"MACD("+string(fastEMA)+", "+string(slowEMA)+","+string(signalPeriod)+")");
//--- indicator buffers mapping
//--- Bind the color buffer immediately below the data buffer
SetIndexBuffer(0,macd_main,INDICATOR_DATA);
ArraySetAsSeries(macd_main,true);
SetIndexBuffer(1,macd_color,INDICATOR_COLOR_INDEX);
ArraySetAsSeries(macd_color,true);
SetIndexBuffer(2,macd_signal,INDICATOR_DATA);
ArraySetAsSeries(macd_signal,true);
SetIndexBuffer(3,macd_signal_color,INDICATOR_COLOR_INDEX);
ArraySetAsSeries(macd_signal_color,true);
//--Initialize the MACD
macdHandle = iMACD(_Symbol,_Period,fastEMA,
slowEMA,signalPeriod, MAPrice);
return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
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[])
{
int end;
if(prev_calculated < rates_total)
end=rates_total - prev_calculated - 2;
else
end = 1;
//--- Data preparation
CopyBuffer(macdHandle,0,0,end+2,macd_main);
CopyBuffer(macdHandle,1,0,end+2,macd_signal);
//---
for(int i = 0; i < end; i++)
{
//--color code the MACD bars
if( macd_main[i] < 0 && macd_main[i] > macd_main[i+1])macd_color[i]=0;
else if( macd_main[i] > 0 && macd_main[i] > macd_main[i+1])macd_color[i]=1;
else if( macd_main[i] > 0 && macd_main[i] < macd_main[i+1])macd_color[i]=2;
else if( macd_main[i] < 0 && macd_main[i] < macd_main[i+1])macd_color[i]=3;
}
//--- return value of prev_calculated for next call
return(rates_total);
}
//+------------------------------------------------------------------+
//| Indicator deinitialization function |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
if(macdHandle!=INVALID_HANDLE)
IndicatorRelease(macdHandle);
//--- clear the chart after deleting the indicator
Comment("");
}
//+------------------------------------------------------------------+
RE: MACD_Color Indicator MQL5 Code -
Hassam - 10-03-2022
MQL5 is a quirky language. Maybe I am not very good at it. Anyway it is no comparison to Python and C#. These two languages are very powerful. I have further improved the above code and made sure that the macdHandle is calculated before the indicator gets displayed. This is what was happening. On first rendition, the indicator was given wrong lines. So I looked into the problem and modified the code to make sure that the data is properly calculated before it is displayed. Below is the modified code:
Code:
//+------------------------------------------------------------------+
//| MACD_Color.mq5 |
//| Copyright 2019, Ahmad Hassam |
//| https://www.doubledoji.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2019, Ahmad Hassam"
#property link "https://www.doubledoji.com"
#property version "1.00"
#property description "Moving Average Convergence/Divergence"
#property indicator_separate_window
#property indicator_buffers 4
#property indicator_plots 2
//--- plot MACD HISTOGRAM
#property indicator_label1 "MACD"
#property indicator_type1 DRAW_COLOR_HISTOGRAM
#property indicator_color1 clrLightGreen, clrDarkGreen, clrPink, clrRed
#property indicator_style1 STYLE_SOLID
#property indicator_width1 3
//--- plot MACD Signal
#property indicator_label2 "Signal"
#property indicator_type2 DRAW_LINE
#property indicator_color2 clrRed
#property indicator_style2 STYLE_SOLID
#property indicator_width2 2
//--- input parameters
input int fastEMA=12;
input int slowEMA=26;
input int signalPeriod=9;
input ENUM_APPLIED_PRICE MAPrice = PRICE_CLOSE;
//--- indicator buffers
double macd_main[]; //MACD Histogram
double macd_color[]; //MACD Histogram bar colors
double macd_signal[]; //MACD Signal
double macd_signal_color[];
//--declare MACD Handle
int macdHandle;
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int OnInit()
{
//--- indicator subwindow label
IndicatorSetString(INDICATOR_SHORTNAME,
"MACD("+string(fastEMA)+", "+string(slowEMA)+","+string(signalPeriod)+")");
//--- indicator buffers mapping
//--- Bind the color buffer immediately below the data buffer
SetIndexBuffer(0,macd_main,INDICATOR_DATA);
ArraySetAsSeries(macd_main,true);
SetIndexBuffer(1,macd_color,INDICATOR_COLOR_INDEX);
ArraySetAsSeries(macd_color,true);
SetIndexBuffer(2,macd_signal,INDICATOR_DATA);
ArraySetAsSeries(macd_signal,true);
SetIndexBuffer(3,macd_signal_color,INDICATOR_COLOR_INDEX);
ArraySetAsSeries(macd_signal_color,true);
//--Initialize the MACD
macdHandle = iMACD(_Symbol,_Period,fastEMA,
slowEMA,signalPeriod, MAPrice);
return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
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[])
{
if(rates_total < signalPeriod)
return(0);
//--- not all data may be calculated
int calculated=BarsCalculated(macdHandle);
if(calculated < rates_total)
{
Print("Not all data of macdHandle is calculated (",calculated," bars). Error ",GetLastError());
return(0);
}
int end;
if(prev_calculated < rates_total)
end=rates_total - prev_calculated - 1;
else
end = 1;
//--- Data preparation
if(IsStopped()) // checking for stop flag
return(0);
if(CopyBuffer(macdHandle,0,0,end+1,macd_main)<=0)
{
Print("Getting macd_main is failed! Error ",GetLastError());
return(0);
}
//--- get macd_signal buffer
if(IsStopped()) // checking for stop flag
return(0);
if(CopyBuffer(macdHandle,1,0,end+1,macd_signal)<=0)
{
Print("Getting macd_signal is failed! Error ",GetLastError());
return(0);
}
//---
for(int i = 0; i < end; i++)
{
//--color code the MACD bars
if( macd_main[i] < 0 && macd_main[i] > macd_main[i+1])macd_color[i]=0;
else if( macd_main[i] > 0 && macd_main[i] > macd_main[i+1])macd_color[i]=1;
else if( macd_main[i] > 0 && macd_main[i] < macd_main[i+1])macd_color[i]=2;
else if( macd_main[i] < 0 && macd_main[i] < macd_main[i+1])macd_color[i]=3;
}
//--- return value of prev_calculated for next call
return(rates_total);
}
//+------------------------------------------------------------------+
//| Indicator deinitialization function |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
if(macdHandle!=INVALID_HANDLE)
IndicatorRelease(macdHandle);
//--- clear the chart after deleting the indicator
Comment("");
}
//+------------------------------------------------------------------+