HMA MTF
Download scriptThis script is designed to provide traders with a specialized moving average called the Hull Moving Average (HMA). Unlike standard moving averages which often lag behind price action—meaning they show you what happened in the past rather than what is happening now—the Hull Moving Average is engineered to follow price trends more closely while remaining smooth and stable.
How the Logic Works
To achieve this balance of speed and smoothness, the script processes market data through a multi-step mathematical sequence:
1. Data Selection The tool begins by identifying a specific price point for each candle (such as the Opening price, Closing price, or High/Low averages) based on the user's preference. It then looks back over a designated timeframe (the "Period") to gather historical data.
2. The Weighted Calculation Instead of treating all past prices equally, the script uses a "Linear Weighted Moving Average" (LWMA). This gives more importance to the most recent price points, allowing the indicator to react faster to sudden market shifts. It calculates two different versions of this weighted average:
- One based on the full timeframe.
- One based on half of that timeframe.
3. The "Hull" Transformation The script performs a unique calculation where it doubles the value of the shorter (half) timeframe average and subtracts the longer timeframe average from it. This specific mathematical combination is designed to significantly reduce the delay typically found in moving averages, effectively "pulling" the indicator toward the current price.
4. Final Smoothing To ensure the resulting line isn't too jagged or erratic for easy reading, the script performs one final calculation. It takes the result of the previous step and applies a smoothing process based on the square root of the timeframe. This produces the final "Silver" line seen on the chart, which offers a clean, fluid visual of the trend.
Summary for the User
In plain terms, this script acts as a sophisticated "trend-tracker." It filters out the small "noise" of the market to show you the overall direction of price movement. Because it uses weighted math and multiple layers of processing, it aims to provide a smoother path than a standard moving average while reacting much quicker to new price changes.
/*-----------------------------+
| |
| Shared by www.Aptrafx.com |
| |
+------------------------------*/
/*+------------------------------------------------------------------+
| FileName: i_Hull_MA.mq4
| Description: This indicator calculates the Hull Moving Average
|
| Original equation is:
| ---------------------
| waverage(2*waverage(close,period/2)-waverage(close,period), SquareRoot(Period)
Implementation below is more efficient with lengthy Weighted Moving Averages.
In addition, the length needs to be converted to an integer value after it is halved and
its square root is obtained in order for this to work with Weighted Moving Averaging
| Version: 000 20050903 17:06 GMT
+------------------------------------------------------------------------------------------+*/
#property link "http://www.justdata.com.au/Journals/AlanHull/hull_ma.htm"
#property indicator_separate_window
#property indicator_buffers 1
#property indicator_color1 Silver
//---- External parameters
extern int _maPeriod=120;
extern int price = PRICE_OPEN;
/*
PRICE_CLOSE 0 Close price.
PRICE_OPEN 1 Open price.
PRICE_HIGH 2 High price.
PRICE_LOW 3 Low price.
PRICE_MEDIAN 4 Median price, (high+low)/2.
PRICE_TYPICAL 5 Typical price, (high+low+close)/3.
PRICE_WEIGHTED 6 Weighted close price, (high+low+close+close)/4.
*/
//---- indicator buffers
double _hma[];
double _wma[];
//----
int ExtCountedBars=0;
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init() {
int draw_begin;
string short_name;
IndicatorBuffers(2);
//---- indicator buffers mapping
SetIndexBuffer(0, _hma);
SetIndexEmptyValue(0, 0.0);
SetIndexStyle(0, DRAW_LINE);
SetIndexBuffer(1, _wma);
SetIndexEmptyValue(1, 0.0);
IndicatorDigits(MarketInfo(Symbol(),MODE_DIGITS));
//---- initialization done
return(0);
}
int start() {
int i, shift, countedBars=IndicatorCounted();
int maxBars=_maPeriod*2;
int period=_maPeriod;
double sqrtPeriod = MathSqrt(period*1.00);
int halfPeriod=period/2;
if(Bars<_maPeriod) return(-1);
if(countedBars == 0) countedBars = maxBars;
int limit=Bars-countedBars+maxBars;
//---- moving average
double wma1;
double wma2;
for(i=limit; i>=0; i--) {
wma1 = iMA(Symbol(), 60, period, 0, MODE_LWMA, price, i);
wma2 = iMA(Symbol(), 60, halfPeriod, 0, MODE_LWMA, price, i);
_wma[i] = 2*wma2-wma1;
}
for(i=limit; i>=0; i--) {
_hma[i]=iMAOnArray(_wma, 60, sqrtPeriod, 0, MODE_LWMA, i);
}
return(0);
}
Comments