Files
xMQL5/Indicators/x-saherelm.xchma.oscillator.mq5
T
2024-01-25 04:09:42 +03:30

1154 lines
28 KiB
Plaintext

///////////////////////////////////////////////////////////////////
//
// SaherElm IT Center MQL5 Cycle Channel Moving Averages Oscillator
// ----------------------------------------------------------------
// Name: XCHMA
// Description: trend detecting based on cycles ...
//
//
// Maintainer:
// ------------
// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com)
//
//////////////////////////////////////////////////////
//
// Global Properties ...
#property copyright "Copyright 2023, SaherElm IT Center"
#property link "https://saherelm.ir"
#property version "1.00"
#property description "SaherElm XCHMA Oscillator"
#property strict
//
// START Constants ...
//
#define ShortName "XCHMA"
//
// XCHMA Oscillator Cycles State Presentation ...
enum ENUM_XCHMA_CYCLE_STATES
{
X_XCHMA_FAST_CROSSED_OVER_SLOW = 2,
X_XCHMA_FAST_OVER_SLOW = 1,
X_XCHMA_NEUTURAL = 0,
X_XCHMA_FAST_UNDER_SLOW = -1,
X_XCHMA_FAST_CROSSED_UNDER_SLOW = -2,
};
//
// END Constants ...
//
//
// START Inputs ...
//
//
// Common ...
input group "Hot Areas";
input bool drawHotAreas = true; // Draw Hot Areas Symbol
input uchar hotBullishArrowCode = 228; // Hot Bullish Arrow Code
input color hotBullishArrowColor = clrAqua; // Hot Bullish Arrow Color
input uchar hotBearishArrowCode = 230; // Hot Bearish Arrow Code
input color hotBearishArrowColor = clrFuchsia; // Hot Bearish Arrow Color
//
// LC Inputs ...
input group "Long Cycle";
input group "LC Market";
input int lcFastLength = 20; // Fast Length
input int lcSlowLength = 50; // Slow Length
input ENUM_MA_METHOD lcMethod = MODE_EMA; // Calculation Method
input ENUM_APPLIED_PRICE lcAppliedTo = PRICE_CLOSE; // Applied To
input group "LC Style";
input int lcDrawWidth = 1; // Draw Width
input ENUM_DRAW_TYPE lcDrawType = DRAW_LINE; // Draw Type
input ENUM_LINE_STYLE lcDrawStyle = STYLE_DOT; // Draw Style
input color lcFastColor = clrAqua; // Fast Color
input color lcSlowColor = clrFuchsia; // Slow Color
input group "LC Drawings";
input bool lcDrawFast = true; // Draw Fast
input bool lcDrawSlow = true; // Draw Slow
input bool lcDrawCrosses = true; // Draw Cross Lines
//
// MC Inputs ...
input group "Medium Cycle";
input group "MC Market";
input int mcFastLength = 10; // Fast Length
input int mcSlowLength = 30; // Slow Length
input ENUM_MA_METHOD mcMethod = MODE_EMA; // Calculation Method
input ENUM_APPLIED_PRICE mcAppliedTo = PRICE_CLOSE; // Applied To
input group "MC Style";
input int mcDrawWidth = 1; // Draw Width
input ENUM_DRAW_TYPE mcDrawType = DRAW_LINE; // Draw Type
input ENUM_LINE_STYLE mcDrawStyle = STYLE_DOT; // Draw Style
input color mcFastColor = clrLime; // Fast Color
input color mcSlowColor = clrRed; // Slow Color
input group "MC Drawings";
input bool mcDrawFast = true; // Draw Fast
input bool mcDrawSlow = true; // Draw Slow
input bool mcDrawCrosses = false; // Draw Cross Lines
//
// SC Inputs ...
input group "Short Cycle";
input group "SC Market";
input int scFastLength = 7; // Fast Length
input int scSlowLength = 14; // Slow Length
input ENUM_MA_METHOD scMethod = MODE_EMA; // Calculation Method
input ENUM_APPLIED_PRICE scAppliedTo = PRICE_CLOSE; // Applied To
input group "SC Style";
input int scDrawWidth = 1; // Draw Width
input ENUM_DRAW_TYPE scDrawType = DRAW_LINE; // Draw Type
input ENUM_LINE_STYLE scDrawStyle = STYLE_SOLID; // Draw Style
input color scFastColor = clrLightBlue; // Fast Color
input color scSlowColor = clrLightSalmon; // Slow Color
input group "SC Drawings";
input bool scDrawFast = true; // Draw Fast
input bool scDrawSlow = true; // Draw Slow
input bool scDrawCrosses = false; // Draw Cross Lines
//
// END Inputs ...
//
//
// Includes Logging Library ...
#include "../Libraries/x-saherelm.log.lib.mq5";
//
// Includes Common Library ...
#include "../Libraries/x-saherelm.common.lib.mq5";
//
// Includes Draw Library ...
#include "../Libraries/x-saherelm.draw.lib.mq5";
//
// START Buffers ...
//
#property indicator_separate_window
//
#property indicator_buffers 7
#property indicator_plots 6
//
// LC ...
#define lcFastBufferIndex 0
#define lcSlowBufferIndex 1
//
double lcFastBuffer[];
double lcSlowBuffer[];
//
// MC ...
#define mcFastBufferIndex 2
#define mcSlowBufferIndex 3
//
double mcFastBuffer[];
double mcSlowBuffer[];
//
// SC ...
#define scFastBufferIndex 4
#define scSlowBufferIndex 5
//
double scFastBuffer[];
double scSlowBuffer[];
//
// Hot State ...
//
#define hotStateBufferIndex 6
//
double hotStateBuffer[];
//
// END Buffers ...
//
//
// START Global Definitions: Variables, Properties and etc ...
//
//
// LC ...
int lcFastHandler = INVALID_HANDLE;
int lcSlowHandler = INVALID_HANDLE;
//
// MC ...
int mcFastHandler = INVALID_HANDLE;
int mcSlowHandler = INVALID_HANDLE;
//
// SC ...
int scFastHandler = INVALID_HANDLE;
int scSlowHandler = INVALID_HANDLE;
//
// END Global Definitions: Variables, Properties and etc ...
//
//
// START Event Handlers ...
//
//
// Initialization ...
int OnInit()
{
//
// Validate Inputs ...
if (!ValidateInputs())
{
return INIT_PARAMETERS_INCORRECT;
}
//
logTag = ShortName;
drawPrefix = ShortName;
//
// Define Index Buffers ...
DefineBuffers();
//
// Set Indicator ShortName ...
SetIndicatorName();
//
// Init All Required Handlers ...
if (!InitHandlers())
{
return INIT_FAILED;
}
//
// Init Succeed ...
return INIT_SUCCEEDED;
}
//
// DeInitialization ...
void OnDeinit(const int reason)
{
//
// REASON_PROGRAM 0 The EA has stopped working calling the ExpertRemove() function
// REASON_REMOVE 1 Program removed from a chart
// REASON_RECOMPILE 2 Program recompiled
// REASON_CHARTCHANGE 3 A symbol or a chart period is changed
// REASON_CHARTCLOSE 4 Chart closed
// REASON_PARAMETERS 5 Inputs changed by a user
// REASON_ACCOUNT 6 Another account has been activated or reconnection to the trade server has occurred due to changes in the account settings
// REASON_TEMPLATE 7 Another chart template applied
// REASON_INITFAILED 8 The OnInit() handler returned a non-zero value
// REASON_CLOSE 9 Terminal closed
//
// Here we can handle De Initialization Reasons ...
//
// ReDraw Chart ...
ChartRedraw();
//
// De Init Draw Library ...
OnDeinitDrawLibrary();
//
Comment("");
}
//
// Calculations ...
//
// Calculating what we want ...
int OnCalculate(
//
// total Candles on chart ...
const int rates_total,
//
// total calculated Candles on charts ...
const int prev_calculated,
//
// history of Candles Open Time ...
const datetime &time[],
//
// history of Candles Open Price ...
const double &open[],
//
// history of Candles High Price ...
const double &high[],
//
// history of Candles Low Price ...
const double &low[],
//
// history of Candles Close Price ...
const double &close[],
//
// history of Tick Volumes on Candle ...
const long &tick_volume[],
//
// history of Trade Volumes ...
const long &volume[],
//
// history of Candles Spread Price ...
const int &spread[])
{
//
// Prepare Buffers ...
ArraySetAsSeries(time, true);
ArraySetAsSeries(open, true);
ArraySetAsSeries(high, true);
ArraySetAsSeries(low, true);
ArraySetAsSeries(close, true);
ArraySetAsSeries(tick_volume, true);
ArraySetAsSeries(volume, true);
ArraySetAsSeries(spread, true);
//
// this counts Available Bars ...
int limit;
//
// because in some cases we may have more than one input for
// calculation and we must prevent any calculation
// untill we pass the biggest input length, here we get max Input length
// and then wait until pass it ...
int maxLength = MathMax(lcFastLength, lcSlowLength);
//
// Get Retrieved Values from indicators ...
//
// LC ...
int lcFastCalculatedBars = BarsCalculated(lcFastHandler);
int lcSlowCalculatedBars = BarsCalculated(lcSlowHandler);
//
// MC ...
int mcFastCalculatedBars = BarsCalculated(mcFastHandler);
int mcSlowCalculatedBars = BarsCalculated(mcSlowHandler);
//
// SC ...
int scFastCalculatedBars = BarsCalculated(scFastHandler);
int scSlowCalculatedBars = BarsCalculated(scSlowHandler);
//
// Check Calculated Bars ...
if (
//
// LC ...
lcFastCalculatedBars < maxLength ||
lcSlowCalculatedBars < maxLength ||
//
// MC ...
mcFastCalculatedBars < maxLength ||
mcSlowCalculatedBars < maxLength ||
//
// SC ...
scFastCalculatedBars < maxLength ||
scSlowCalculatedBars < maxLength)
{
return prev_calculated;
}
//
limit = prev_calculated < maxLength ? rates_total - (maxLength + 1) : rates_total - prev_calculated;
//
// Copy Buffers from indicators ...
//
// LC ...
int lcFastCopiedItems = CopyBuffer(lcFastHandler, 0, 0, limit + 1, lcFastBuffer);
int lcSlowCopiedItems = CopyBuffer(lcSlowHandler, 0, 0, limit + 1, lcSlowBuffer);
//
// MC ...
int mcFastCopiedItems = CopyBuffer(mcFastHandler, 0, 0, limit + 1, mcFastBuffer);
int mcSlowCopiedItems = CopyBuffer(mcSlowHandler, 0, 0, limit + 1, mcSlowBuffer);
//
// SC ...
int scFastCopiedItems = CopyBuffer(scFastHandler, 0, 0, limit + 1, scFastBuffer);
int scSlowCopiedItems = CopyBuffer(scSlowHandler, 0, 0, limit + 1, scSlowBuffer);
//
// Check Copied Items Number ...
if (
//
// LC ...
lcFastCopiedItems <= 0 ||
lcSlowCopiedItems <= 0 ||
//
// MC ...
mcFastCopiedItems <= 0 ||
mcSlowCopiedItems <= 0 ||
//
// MC ...
mcFastCopiedItems <= 0 ||
mcSlowCopiedItems <= 0)
{
return prev_calculated;
}
//
// Main Loop ...
for (int i = limit; i >= 0 && !IsStopped(); i--)
{
//
CalculateBuffers(i);
}
//
return rates_total;
}
//
// END Event Handlers ...
//
//
// START Functions ...
//
//
// Validate Input Args for Initialization ...
bool ValidateInputs()
{
//
bool result = false;
//
// Validate Args ...
bool isLCInputsValid = lcFastLength >= 4 && lcSlowLength > lcFastLength;
bool isMCInputsValid = mcFastLength >= 4 && mcSlowLength > mcFastLength;
bool isSCInputsValid = scFastLength >= 4 && scSlowLength > scFastLength;
if (
isLCInputsValid &&
isMCInputsValid &&
isSCInputsValid &&
lcFastLength > mcFastLength &&
mcFastLength > scFastLength)
{
result = true;
}
//
return result;
}
//
// Define Indexes and Styles ...
void DefineBuffers()
{
//
// LC ...
LCDefineBuffers();
//
// MC ...
MCDefineBuffers();
//
// SC ...
SCDefineBuffers();
//
// Hot State Buffer ...
HotStateDefineBuffers();
}
//
// Init Handlers ...
bool InitHandlers()
{
//
bool result = false;
//
// LC ...
result = LCInitHandlers();
if (!result)
{
return result;
}
//
// MC ...
result = MCInitHandlers();
if (!result)
{
return result;
}
//
// SC ...
result = SCInitHandlers();
if (!result)
{
return result;
}
//
return result;
}
//
// Set Indicator Short Name and also we can define Buffers Labels ...
void SetIndicatorName()
{
//
string indicatorShortName = "";
StringConcatenate(indicatorShortName, ShortName, "");
//
IndicatorSetString(INDICATOR_SHORTNAME, indicatorShortName);
}
//
// Calculate Buffers ...
void CalculateBuffers(
int bar_index // Current Candle Index ...
)
{
//
// HOT State Buffer ...
HotStateCalculateBuffers(bar_index);
//
// After all Calculations we are ready to Draw what we want ...
DrawBuffers(bar_index);
}
//
// LC Buffers Definitions ...
void LCDefineBuffers()
{
//
// LC Fast Buffer ...
string lcFastBufferLabel = ShortName + " LC Fast (" + (string)lcFastLength + ")";
ENUM_DRAW_TYPE lcFastDrawType = lcDrawFast ? lcDrawType : DRAW_NONE;
ArraySetAsSeries(lcFastBuffer, true);
SetIndexBuffer(lcFastBufferIndex, lcFastBuffer, INDICATOR_DATA);
PlotIndexSetString(lcFastBufferIndex, PLOT_LABEL, lcFastBufferLabel);
PlotIndexSetInteger(lcFastBufferIndex, PLOT_LINE_COLOR, lcFastColor);
PlotIndexSetInteger(lcFastBufferIndex, PLOT_LINE_STYLE, lcDrawStyle);
PlotIndexSetInteger(lcFastBufferIndex, PLOT_LINE_WIDTH, lcDrawWidth);
PlotIndexSetInteger(lcFastBufferIndex, PLOT_DRAW_BEGIN, lcFastLength);
PlotIndexSetInteger(lcFastBufferIndex, PLOT_DRAW_TYPE, lcFastDrawType);
//
// LC Slow Buffer ...
string lcSlowBufferLabel = ShortName + " LC Slow (" + (string)lcSlowLength + ")";
ENUM_DRAW_TYPE lcSlowDrawType = lcDrawSlow ? lcDrawType : DRAW_NONE;
ArraySetAsSeries(lcSlowBuffer, true);
SetIndexBuffer(lcSlowBufferIndex, lcSlowBuffer, INDICATOR_DATA);
PlotIndexSetString(lcSlowBufferIndex, PLOT_LABEL, lcSlowBufferLabel);
PlotIndexSetInteger(lcSlowBufferIndex, PLOT_LINE_COLOR, lcSlowColor);
PlotIndexSetInteger(lcSlowBufferIndex, PLOT_LINE_STYLE, lcDrawStyle);
PlotIndexSetInteger(lcSlowBufferIndex, PLOT_LINE_WIDTH, lcDrawWidth);
PlotIndexSetInteger(lcSlowBufferIndex, PLOT_DRAW_BEGIN, lcSlowLength);
PlotIndexSetInteger(lcSlowBufferIndex, PLOT_DRAW_TYPE, lcSlowDrawType);
}
//
// MC Buffers Definitions ...
void MCDefineBuffers()
{
//
// MC Fast Buffer ...
string mcFastBufferLabel = ShortName + " MC Fast (" + (string)mcFastLength + ")";
ENUM_DRAW_TYPE mcFastDrawType = mcDrawFast ? lcDrawType : DRAW_NONE;
ArraySetAsSeries(mcFastBuffer, true);
SetIndexBuffer(mcFastBufferIndex, mcFastBuffer, INDICATOR_DATA);
PlotIndexSetString(mcFastBufferIndex, PLOT_LABEL, mcFastBufferLabel);
PlotIndexSetInteger(mcFastBufferIndex, PLOT_LINE_COLOR, mcFastColor);
PlotIndexSetInteger(mcFastBufferIndex, PLOT_LINE_STYLE, mcDrawStyle);
PlotIndexSetInteger(mcFastBufferIndex, PLOT_LINE_WIDTH, mcDrawWidth);
PlotIndexSetInteger(mcFastBufferIndex, PLOT_DRAW_BEGIN, mcFastLength);
PlotIndexSetInteger(mcFastBufferIndex, PLOT_DRAW_TYPE, mcFastDrawType);
//
// MC Slow Buffer ...
string mcSlowBufferLabel = ShortName + " MC Slow (" + (string)mcSlowLength + ")";
ENUM_DRAW_TYPE mcSlowDrawType = mcDrawSlow ? lcDrawType : DRAW_NONE;
ArraySetAsSeries(mcSlowBuffer, true);
SetIndexBuffer(mcSlowBufferIndex, mcSlowBuffer, INDICATOR_DATA);
PlotIndexSetString(mcSlowBufferIndex, PLOT_LABEL, mcSlowBufferLabel);
PlotIndexSetInteger(mcSlowBufferIndex, PLOT_LINE_COLOR, mcSlowColor);
PlotIndexSetInteger(mcSlowBufferIndex, PLOT_LINE_STYLE, mcDrawStyle);
PlotIndexSetInteger(mcSlowBufferIndex, PLOT_LINE_WIDTH, mcDrawWidth);
PlotIndexSetInteger(mcSlowBufferIndex, PLOT_DRAW_BEGIN, mcSlowLength);
PlotIndexSetInteger(mcSlowBufferIndex, PLOT_DRAW_TYPE, mcSlowDrawType);
}
//
// SC Buffers Definitions ...
void SCDefineBuffers()
{
//
// SC Fast Buffer ...
string scFastBufferLabel = ShortName + " SC Fast (" + (string)scFastLength + ")";
ENUM_DRAW_TYPE scFastDrawType = scDrawFast ? lcDrawType : DRAW_NONE;
ArraySetAsSeries(scFastBuffer, true);
SetIndexBuffer(scFastBufferIndex, scFastBuffer, INDICATOR_DATA);
PlotIndexSetString(scFastBufferIndex, PLOT_LABEL, scFastBufferLabel);
PlotIndexSetInteger(scFastBufferIndex, PLOT_LINE_COLOR, scFastColor);
PlotIndexSetInteger(scFastBufferIndex, PLOT_LINE_STYLE, scDrawStyle);
PlotIndexSetInteger(scFastBufferIndex, PLOT_LINE_WIDTH, scDrawWidth);
PlotIndexSetInteger(scFastBufferIndex, PLOT_DRAW_BEGIN, scFastLength);
PlotIndexSetInteger(scFastBufferIndex, PLOT_DRAW_TYPE, scFastDrawType);
//
// SC Slow Buffer ...
string scSlowBufferLabel = ShortName + " SC Slow (" + (string)scSlowLength + ")";
ENUM_DRAW_TYPE scSlowDrawType = scDrawSlow ? lcDrawType : DRAW_NONE;
ArraySetAsSeries(scSlowBuffer, true);
SetIndexBuffer(scSlowBufferIndex, scSlowBuffer, INDICATOR_DATA);
PlotIndexSetString(scSlowBufferIndex, PLOT_LABEL, scSlowBufferLabel);
PlotIndexSetInteger(scSlowBufferIndex, PLOT_LINE_COLOR, scSlowColor);
PlotIndexSetInteger(scSlowBufferIndex, PLOT_LINE_STYLE, scDrawStyle);
PlotIndexSetInteger(scSlowBufferIndex, PLOT_LINE_WIDTH, scDrawWidth);
PlotIndexSetInteger(scSlowBufferIndex, PLOT_DRAW_BEGIN, scSlowLength);
PlotIndexSetInteger(scSlowBufferIndex, PLOT_DRAW_TYPE, scSlowDrawType);
}
//
// Hot State Buffer ...
void HotStateDefineBuffers()
{
//
// Hot State Buffer ...
ArraySetAsSeries(hotStateBuffer, true);
SetIndexBuffer(hotStateBufferIndex, hotStateBuffer, INDICATOR_CALCULATIONS);
}
//
// LC Init Handlers ...
bool LCInitHandlers()
{
//
ResetLastError();
//
// LC Fast Handler ...
lcFastHandler = iMA(
_Symbol,
_Period,
lcFastLength,
0,
lcMethod,
lcAppliedTo);
if (lcFastHandler == INVALID_HANDLE)
{
//
LogMessage("LC Fast Indicator initialization failed: " + (string)GetLastError());
//
return false;
}
//
// LC Slow Handler ...
lcSlowHandler = iMA(
_Symbol,
_Period,
lcSlowLength,
0,
lcMethod,
lcAppliedTo);
if (lcSlowHandler == INVALID_HANDLE)
{
//
LogMessage("LC Slow Indicator initialization failed: " + (string)GetLastError());
//
return false;
}
//
return true;
}
//
// MC Init Handlers ...
bool MCInitHandlers()
{
//
ResetLastError();
//
// MC Fast Handler ...
mcFastHandler = iMA(
_Symbol,
_Period,
mcFastLength,
0,
mcMethod,
mcAppliedTo);
if (mcFastHandler == INVALID_HANDLE)
{
//
LogMessage("MC Fast Indicator initialization failed: " + (string)GetLastError());
//
return false;
}
//
// MC Slow Handler ...
mcSlowHandler = iMA(
_Symbol,
_Period,
mcSlowLength,
0,
mcMethod,
mcAppliedTo);
if (mcSlowHandler == INVALID_HANDLE)
{
//
LogMessage("MC Slow Indicator initialization failed: " + (string)GetLastError());
//
return false;
}
//
return true;
}
//
// SC Init Handlers ...
bool SCInitHandlers()
{
//
ResetLastError();
//
// SC Fast Handler ...
scFastHandler = iMA(
_Symbol,
_Period,
scFastLength,
0,
scMethod,
scAppliedTo);
if (scFastHandler == INVALID_HANDLE)
{
//
LogMessage("SC Fast Indicator initialization failed: " + (string)GetLastError());
//
return false;
}
//
// SC Slow Handler ...
scSlowHandler = iMA(
_Symbol,
_Period,
scSlowLength,
0,
scMethod,
scAppliedTo);
if (scSlowHandler == INVALID_HANDLE)
{
//
LogMessage("SC Slow Indicator initialization failed: " + (string)GetLastError());
//
return false;
}
//
return true;
}
//
// LC State ...
double GetLCState(
int bar_index // Current Candle Index ...
)
{
//
// Fast Cross Over Slow Detection ...
bool isFastCrossedOverSlow = IsCrossOver(
lcFastBuffer,
lcSlowBuffer,
bar_index);
//
// Fast Over Slow Detection ...
bool isFastOverSlow = IsOver(
lcFastBuffer,
lcSlowBuffer,
bar_index);
//
// Fast Cross Under Slow Detection ...
bool isFastCrossedUnderSlow = IsCrossUnder(
lcFastBuffer,
lcSlowBuffer,
bar_index);
//
// Fast Under Slow Detection ...
bool isFastUnderSlow = IsUnder(
lcFastBuffer,
lcSlowBuffer,
bar_index);
//
// Generate state value which represent curren bar index
// state between fast and slow lines ...
double result = X_XCHMA_NEUTURAL;
//
// Filling state value based on Market Conditions ...
if (isFastCrossedOverSlow)
{
result = X_XCHMA_FAST_CROSSED_OVER_SLOW;
}
else if (isFastCrossedUnderSlow)
{
result = X_XCHMA_FAST_CROSSED_UNDER_SLOW;
}
else if (isFastOverSlow)
{
result = X_XCHMA_FAST_OVER_SLOW;
}
else if (isFastUnderSlow)
{
result = X_XCHMA_FAST_UNDER_SLOW;
}
//
return result;
}
//
// MC State ...
double GetMCState(
int bar_index // Current Candle Index ...
)
{
//
// Fast Cross Over Slow Detection ...
bool isFastCrossedOverSlow = IsCrossOver(
mcFastBuffer,
mcSlowBuffer,
bar_index);
//
// Fast Over Slow Detection ...
bool isFastOverSlow = IsOver(
mcFastBuffer,
mcSlowBuffer,
bar_index);
//
// Fast Cross Under Slow Detection ...
bool isFastCrossedUnderSlow = IsCrossUnder(
mcFastBuffer,
mcSlowBuffer,
bar_index);
//
// Fast Under Slow Detection ...
bool isFastUnderSlow = IsUnder(
mcFastBuffer,
mcSlowBuffer,
bar_index);
//
// Generate state value which represent curren bar index
// state between fast and slow lines ...
double result = X_XCHMA_NEUTURAL;
//
// Filling state value based on Market Conditions ...
if (isFastCrossedOverSlow)
{
result = X_XCHMA_FAST_CROSSED_OVER_SLOW;
}
else if (isFastCrossedUnderSlow)
{
result = X_XCHMA_FAST_CROSSED_UNDER_SLOW;
}
else if (isFastOverSlow)
{
result = X_XCHMA_FAST_OVER_SLOW;
}
else if (isFastUnderSlow)
{
result = X_XCHMA_FAST_UNDER_SLOW;
}
//
return result;
}
//
// SC State ...
double GetSCState(
int bar_index // Current Candle Index ...
)
{
//
// Fast Cross Over Slow Detection ...
bool isFastCrossedOverSlow = IsCrossOver(
scFastBuffer,
scSlowBuffer,
bar_index);
//
// Fast Over Slow Detection ...
bool isFastOverSlow = IsOver(
scFastBuffer,
scSlowBuffer,
bar_index);
//
// Fast Cross Under Slow Detection ...
bool isFastCrossedUnderSlow = IsCrossUnder(
scFastBuffer,
scSlowBuffer,
bar_index);
//
// Fast Under Slow Detection ...
bool isFastUnderSlow = IsUnder(
scFastBuffer,
scSlowBuffer,
bar_index);
//
// Generate state value which represent curren bar index
// state between fast and slow lines ...
double result = X_XCHMA_NEUTURAL;
//
// Filling state value based on Market Conditions ...
if (isFastCrossedOverSlow)
{
result = X_XCHMA_FAST_CROSSED_OVER_SLOW;
}
else if (isFastCrossedUnderSlow)
{
result = X_XCHMA_FAST_CROSSED_UNDER_SLOW;
}
else if (isFastOverSlow)
{
result = X_XCHMA_FAST_OVER_SLOW;
}
else if (isFastUnderSlow)
{
result = X_XCHMA_FAST_UNDER_SLOW;
}
//
return result;
}
//
// HOT State Calculate Buffers ...
void HotStateCalculateBuffers(
int bar_index // Current Candle Index ...
)
{
//
// LC ...
double lcFast = lcFastBuffer[bar_index];
double lcSlow = lcSlowBuffer[bar_index];
//
double lcFastPrev = lcFastBuffer[bar_index + 1];
double lcSlowPrev = lcSlowBuffer[bar_index + 1];
//
double lcState = GetLCState(bar_index);
//
// MC ...
double mcFast = mcFastBuffer[bar_index];
double mcSlow = mcSlowBuffer[bar_index];
//
double mcFastPrev = mcFastBuffer[bar_index + 1];
double mcSlowPrev = mcSlowBuffer[bar_index + 1];
//
double mcState = GetMCState(bar_index);
//
// SC ...
double scFast = scFastBuffer[bar_index];
double scSlow = scSlowBuffer[bar_index];
//
double scFastPrev = scFastBuffer[bar_index + 1];
double scSlowPrev = scSlowBuffer[bar_index + 1];
//
double scState = GetSCState(bar_index);
//
// Detect HOT Bearish Area ...
bool isHotBearishArea =
lcFast < lcSlow &&
mcFast < mcSlow &&
scFast < scSlow;
//
bool isPrevHotBearishArea =
lcFastPrev < lcSlowPrev &&
mcFastPrev < mcSlowPrev &&
scFastPrev < scSlowPrev;
//
// Detect HOT Bearish Area ...
bool isHotBullishArea =
lcFast > lcSlow &&
mcFast > mcSlow &&
scFast > scSlow;
//
bool isPrevHotBullishArea =
lcFastPrev > lcSlowPrev &&
mcFastPrev > mcSlowPrev &&
scFastPrev > scSlowPrev;
//
// Generate HotState Value ...
double hotStateValue =
isHotBullishArea && !isPrevHotBullishArea
? 1
: isHotBearishArea && !isPrevHotBearishArea
? -1
: 0;
hotStateBuffer[bar_index] = hotStateValue;
}
//
// Draw Buffers ...
void DrawBuffers(
int bar_index // Current Candle Index ...
)
{
//
// General Requirements ...
//
// Retrieve Candle Model ...
XOHCL candle = GetCandle(bar_index);
datetime time = iTime(_Symbol, _Period, bar_index);
//
// Draw Arrow on Hot Areas ...
if (drawHotAreas)
{
//
double hotStateValue = hotStateBuffer[bar_index];
bool isHotBullishArea = hotStateValue == 1;
bool isHotBearishArea = hotStateValue == -1;
if (isHotBullishArea || isHotBearishArea)
{
//
bool isBull = isHotBullishArea;
//
double price = isBull ? candle.low : candle.high;
ENUM_ARROW_ANCHOR anchor = isBull ? ANCHOR_TOP : ANCHOR_BOTTOM;
color clr = isBull ? hotBullishArrowColor : hotBearishArrowColor;
uchar arrowCode = isBull ? hotBullishArrowCode : hotBearishArrowCode;
string name = "HOT " + (isBull ? "Bullish" : "Bearish") + "_" + (string)price + "_" + (string)time;
//
DrawArrow(
0,
name,
0,
time,
price,
arrowCode,
anchor,
clr);
}
}
//
// Draw LC Crosses ...
if (lcDrawCrosses)
{
//
double lcStateValue = GetLCState(bar_index);
bool isLcFastCrossedOverSlow = lcStateValue == X_XCHMA_FAST_CROSSED_OVER_SLOW;
bool isLcFastCrossedUnderSlow = lcStateValue == X_XCHMA_FAST_CROSSED_UNDER_SLOW;
if (isLcFastCrossedOverSlow || isLcFastCrossedUnderSlow)
{
//
bool isBull = isLcFastCrossedOverSlow;
//
color clr = isBull ? lcFastColor : lcSlowColor;
string name = "LC Fast Cross " + (isBull ? "Over" : "Under") + "_" + (string)time;
//
DrawVerticalLine(
0,
name,
0,
time,
clr);
}
}
//
// Draw MC Crosses ...
if (mcDrawCrosses)
{
//
double mcStateValue = GetMCState(bar_index);
bool isMcFastCrossedOverSlow = mcStateValue == X_XCHMA_FAST_CROSSED_OVER_SLOW;
bool isMcFastCrossedUnderSlow = mcStateValue == X_XCHMA_FAST_CROSSED_UNDER_SLOW;
if (isMcFastCrossedOverSlow || isMcFastCrossedUnderSlow)
{
//
bool isBull = isMcFastCrossedOverSlow;
//
color clr = isBull ? mcFastColor : mcSlowColor;
string name = "MC Fast Cross " + (isBull ? "Over" : "Under") + "_" + (string)time;
//
DrawVerticalLine(
0,
name,
0,
time,
clr);
}
}
//
// Draw SC Crosses ...
if (scDrawCrosses)
{
//
double scStateValue = GetSCState(bar_index);
bool isScFastCrossedOverSlow = scStateValue == X_XCHMA_FAST_CROSSED_OVER_SLOW;
bool isScFastCrossedUnderSlow = scStateValue == X_XCHMA_FAST_CROSSED_UNDER_SLOW;
if (isScFastCrossedOverSlow || isScFastCrossedUnderSlow)
{
//
bool isBull = isScFastCrossedOverSlow;
//
color clr = isBull ? scFastColor : scSlowColor;
string name = "SC Fast Cross " + (isBull ? "Over" : "Under") + "_" + (string)time;
//
DrawVerticalLine(
0,
name,
0,
time,
clr);
}
}
}
//
// END Functions ...
//