Aroon_Horn_Oscillator_v1_001
Download scriptTechnical Overview: Aroon Horn Oscillator Logic
This script functions as a custom technical analysis tool designed to help traders identify market trends by measuring the relationship between recent high and low price points. Instead of simply showing raw price action, it processes data into a visual "oscillator" that filters out minor market noise to highlight significant directional movements.
Core Data Processing
The logic operates by analyzing a specific window of time (defined by the AroonPeriod). For every point on the chart, the script performs two primary calculations:
- It identifies the highest price reached within that period.
- It identifies the lowest price reached within that period.
Using these two values, it calculates a numerical "Oscillator" value. This number represents the intensity of the price movement relative to the time frame provided. A positive result indicates upward pressure, while a negative result indicates downward pressure.
Signal Filtering and Visualization
The most distinctive feature of this tool is its "Horn" logic, which categorizes the market into three distinct visual states based on a pre-defined sensitivity threshold (the Filter). Rather than displaying a single continuous line, the script separates the data into three different visual outputs:
- Bullish Momentum: If the oscillator exceeds the positive filter limit, the script highlights the data in a specific color (DodgerBlue), signaling strong upward momentum.
- Bearish Momentum: If the oscillator falls below the negative filter limit, the script highlights the data in another color (Red), signaling strong downward momentum.
- Neutral/Consolidation Zone: If the oscillator stays within the boundaries of the filter (between the positive and negative limits), it is displayed in a third color (Snow). This indicates that the market is currently lacking a clear trend or is moving sideways.
Summary for Traders
By using this logic, a user can quickly distinguish between three market conditions at a glance:
- Active Trends: When the indicator "switches" colors to the extreme top or bottom, it suggests the market is trending strongly in that direction.
- Market Equilibrium: When the indicator occupies the center/neutral zone, it warns the trader that the current price action is not strong enough to establish a definitive trend, potentially suggesting a period of stability or indecision.
//+------------------------------------------------------------------+
//| Custom Aroon_Horn_Oscillator_v1.mq4 |
//| www.forex-tsd.com ik | rafcamara |
//| Has corrected - Ramdass |
//+------------------------------------------------------------------+
#property copyright "rafcamara"
#property link "rafcamara@yahoo.com www.forex-tsd.com"
//---- indicator settings
#property indicator_separate_window
#property indicator_buffers 4
#property indicator_color1 DodgerBlue
#property indicator_color2 Red
#property indicator_color3 Snow
#property indicator_color4 Green
#property indicator_style1 0
#property indicator_style2 0
#property indicator_style3 0
#property indicator_style4 0
#property indicator_width1 1
#property indicator_width2 1
#property indicator_width3 1
#property indicator_width4 1
//---- indicator parameters
extern int AroonPeriod = 10;
extern int Filter = 50;
extern int CountBars = 500;
//---- indicator buffers
double ind_buffer1[];
double ind_buffer2[];
double ind_buffer3[];
double HighBarBuffer[];
double LowBarBuffer[];
double ArOscBuffer[];
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
int init()
{
//---- additional buffers are used for counting.
IndicatorBuffers(6);
SetIndexBuffer(4, HighBarBuffer);
SetIndexBuffer(5, LowBarBuffer);
SetIndexBuffer(3, ArOscBuffer);
SetIndexBuffer(0, ind_buffer1);
SetIndexBuffer(1, ind_buffer2);
SetIndexBuffer(2, ind_buffer3);
//---- drawing settings
SetIndexStyle(0, DRAW_HISTOGRAM);
SetIndexStyle(1, DRAW_HISTOGRAM);
SetIndexStyle(2, DRAW_HISTOGRAM);
SetIndexStyle(3, DRAW_LINE);
//----
IndicatorDigits(0);
//-- indicator buffers mapping
if(!SetIndexBuffer(0, ind_buffer1) && !SetIndexBuffer(1, ind_buffer2)
&& !SetIndexBuffer(2, ind_buffer3))
Print("cannot set indicator buffers!");
//---- name for DataWindow and indicator subwindow label
IndicatorShortName("AroonOsc_v1 ("+AroonPeriod+"("+Filter+")");
//---- initialization done
return(0);
}
//+------------------------------------------------------------------+
//| Aroon Oscilator |
//+------------------------------------------------------------------+
int start()
{
if(CountBars >= Bars)
CountBars=Bars;
SetIndexDrawBegin(0, Bars - CountBars + AroonPeriod + 1);
SetIndexDrawBegin(1, Bars - CountBars + AroonPeriod + 1);
SetIndexDrawBegin(2, Bars - CountBars + AroonPeriod + 1);
SetIndexDrawBegin(3, Bars - CountBars + AroonPeriod + 1);
SetIndexLabel(0,"AroonUp("+AroonPeriod+"("+Filter+")");
SetIndexLabel(1,"AroonDown("+AroonPeriod+"("+Filter+")");
SetIndexLabel(2,"AroonOsc("+AroonPeriod+"("+Filter+")");
double ArOsc, HighBar = 0, LowBar = 0;
int ArPer;
int limit, i;
// bool up,dn;
int counted_bars = IndicatorCounted();
//----
ArPer = AroonPeriod;
//---- check for possible errors
if(counted_bars < 0)
return(-1);
//---- initial zero
if(counted_bars < 1)
{
for(i = 1; i <= ArPer; i++)
HighBarBuffer[CountBars-i] = 0.0;
for(i = 1; i <= ArPer; i++)
LowBarBuffer[CountBars-i] = 0.0;
for(i = 1; i <= ArPer; i++)
ArOscBuffer[CountBars-i] = 0.0;
for(i = 1; i <= ArPer; i++)
ind_buffer1[CountBars-i] = 0.0;
for(i = 1; i <= ArPer; i++)
ind_buffer2[CountBars-i] = 0.0;
for(i = 1; i <= ArPer; i++)
ind_buffer3[CountBars-i] = 0.0;
}
//---- last counted bar will be recounted
//if(counted_bars>0) counted_bars--;
limit = CountBars - AroonPeriod;
//----Calculation---------------------------
for(i = 0; i < limit; i++)
{
HighBarBuffer[i] = Highest(NULL, 0, MODE_HIGH, ArPer, i); //Periods from HH
LowBarBuffer[i] = Lowest(NULL, 0, MODE_LOW, ArPer, i); //Periods from LL
ArOscBuffer[i] = 100*(LowBarBuffer[i] - HighBarBuffer[i]) / ArPer; //Short formulation
}
//---- dispatch values between 2 buffers
for(i = limit - 1; i >= 0; i--)
{
ArOsc=ArOscBuffer[i];
if(ArOsc > Filter)
{
ind_buffer1[i] = ArOsc;
ind_buffer2[i] = 0.0;
ind_buffer3[i] = 0.0;
}
if(ArOsc < -Filter)
{
ind_buffer1[i] = 0.0;
ind_buffer2[i] = ArOsc;
ind_buffer3[i] = 0.0;
}
if(ArOsc <= Filter && ArOsc >= -Filter)
{
ind_buffer1[i] = 0.0;
ind_buffer2[i] = 0.0;
ind_buffer3[i] = ArOsc;
}
}
//---- done
return(0);
}
//+------------------------------------------------------------------+
Comments