This tool is designed to transform the standard price movements of a financial market into a specialized visual format known as Heiken Ashi. Unlike traditional charts that show raw price fluctuations, which can often appear "noisy" or jagged, this script recalculates price data to create a smoother, more readable trend visualization.
Core Logic and Functionality
Trend Smoothing The primary purpose of the logic is to filter out minor market fluctuations. It accomplishes this by calculating new "synthetic" price points for each bar on your chart. Instead of simply looking at where the price opened and closed in a vacuum, it averages the previous data with the current price movement. This helps traders identify the underlying direction of the market more clearly.
Visual Representation The script translates these calculations into a series of visual elements:
- Body Construction: It determines the "body" of each bar based on the calculated opening and closing prices.
- Wick Placement: It calculates the highest and lowest points reached during that period to draw the "shadows" or wicks above and below the body.
- Dynamic Coloring: The tool automatically assigns colors based on the direction of the trend. If the synthetic closing price is higher than the opening price, it applies one color (representing upward momentum); if it is lower, it applies a contrasting color (representing downward momentum).
Customization Options The logic includes a toggle for users to choose how they want to view this data:
- Directional Mode: The default setting, where the colors change dynamically to highlight bullish and bearish moves.
- Uniform Mode: A single-color setting that removes color-based cues, allowing the user to focus purely on the shape of the bars and the trend lines without the influence of color psychology.
User Experience
When active, the script draws these specialized bars as distinct objects on your chart. It ensures that the visual data remains consistent by recalculating the history of the chart whenever new price data arrives, providing a continuous, flowing representation of market sentiment rather than a series of disconnected jumps.
//+------------------------------------------------------------------+
//| Heiken Ashi.mq4 |
//| Copyright c 2004, MetaQuotes Software Corp. |
//| http://www.metaquotes.net |
//+------------------------------------------------------------------+
//| For Heiken Ashi we recommend next chart settings ( press F8 or |
//| select on menu 'Charts'->'Properties...'): |
//| - On 'Color' Tab select 'Black' for 'Line Graph' |
//| - On 'Common' Tab disable 'Chart on Foreground' checkbox and |
//| select 'Line Chart' radiobutton |
//+------------------------------------------------------------------+
//2009forextsd HeikenAshi.obj.sw.mq4
#property copyright "Copyright © 2004, MetaQuotes Software Corp."
#property link "http://www.metaquotes.net"
// ha bars from Kakenzo CustomBar2
#property copyright "Kalenzo"
#property link "http://www.fxservice.eu, bartlomiej.gorski@gmail.com"
#property indicator_separate_window
#property indicator_buffers 4
extern color OneColor = Blue,
UpColor = Green,
DnColor = Red;
extern bool UseOneColor = false;
//----
//---- buffers
double ExtMapBuffer1[];
double ExtMapBuffer2[];
double ExtMapBuffer3[];
double ExtMapBuffer4[];
//----
int ExtCountedBars=0;
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//|------------------------------------------------------------------|
int init()
{
//---- indicators
IndicatorBuffers(4);
// SetIndexStyle(0,DRAW_HISTOGRAM);
SetIndexBuffer(0, ExtMapBuffer1);
// SetIndexStyle(1,DRAW_HISTOGRAM);
SetIndexBuffer(1, ExtMapBuffer2);
// SetIndexStyle(2,DRAW_HISTOGRAM);
SetIndexBuffer(2, ExtMapBuffer3);
// SetIndexStyle(3,DRAW_HISTOGRAM);
SetIndexBuffer(3, ExtMapBuffer4);
//----
//---- indicator buffers mapping
IndicatorShortName("HeikenAshi.obj.sw ");
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+
int deinit()
{
//---- TODO: add your code here
ObjectsDeleteAll();
//----
return(0);
}
//+------------------------------------------------------------------+
//| Custom indicator iteration function |
//+------------------------------------------------------------------+
int start()
{
double haOpen, haHigh, haLow, haClose;
if(Bars<=10) return(0);
ExtCountedBars=IndicatorCounted();
//---- check for possible errors
if (ExtCountedBars<0) return(-1);
//---- last counted bar will be recounted
if (ExtCountedBars>0) ExtCountedBars--;
int pos=Bars-ExtCountedBars-1;
while(pos>=0)
{
haOpen=(ExtMapBuffer3[pos+1]+ExtMapBuffer4[pos+1])/2;
haClose=(Open[pos]+High[pos]+Low[pos]+Close[pos])/4;
haHigh=MathMax(High[pos], MathMax(haOpen, haClose));
haLow=MathMin(Low[pos], MathMin(haOpen, haClose));
if (haOpen<haClose)
{
ExtMapBuffer1[pos]=haLow;
ExtMapBuffer2[pos]=haHigh;
}
else
{
ExtMapBuffer1[pos]=haHigh;
ExtMapBuffer2[pos]=haLow;
}
ExtMapBuffer3[pos]=haOpen;
ExtMapBuffer4[pos]=haClose;
if(UseOneColor)// double haOpen, haHigh, haLow, haClose;
{
drawLine("BB"+pos,Time[pos],haOpen,haClose,3,OneColor);
drawLine("SB"+pos,Time[pos],haHigh,haLow,1,OneColor);
}
else
{
if(haClose<haOpen)
{
drawLine("BB"+pos,Time[pos],haOpen,haClose,3,DnColor);
drawLine("SB"+pos,Time[pos],haHigh,haLow,1,DnColor);
}
else
{
drawLine("BB"+pos,Time[pos],haOpen,haClose,3,UpColor);
drawLine("SB"+pos,Time[pos],haHigh,haLow,1,UpColor);
}
}
pos--;
}
//----
return(0);
}
//----
void drawLine(string name,datetime time, double pfrom, double pto, int width,color Col)
{
if(ObjectFind(name) != 0)
{
ObjectCreate(name, OBJ_TREND, WindowFind("HeikenAshi.obj.sw "), time, pfrom,time,pto);
ObjectSet(name, OBJPROP_STYLE, STYLE_SOLID);
ObjectSet(name, OBJPROP_COLOR, Col);
ObjectSet(name,OBJPROP_WIDTH,width);
ObjectSet(name,OBJPROP_RAY,0);
}
else
{
ObjectDelete(name);
ObjectCreate(name, OBJ_TREND, WindowFind("HeikenAshi.obj.sw "), time, pfrom,time,pto);
ObjectSet(name, OBJPROP_STYLE, STYLE_SOLID);
ObjectSet(name, OBJPROP_COLOR, Col);
ObjectSet(name,OBJPROP_WIDTH,width);
ObjectSet(name,OBJPROP_RAY,0);
}
}
//+------------------------------------------------------------------+
Comments