Files
MQL5Data/XCAEA/Libraries/xcaea.signaller.lib.mq5
T
2025-04-27 02:16:59 +03:30

1233 lines
23 KiB
Plaintext

///////////////////////////////////////////////////////
//
// SaherElm IT Center MQL5 Indicator
// -------------------------------------------------
// Name: XCAEASignaller Lib
// Description: Library for XCAEA Signaller ...
//
//
// Maintainer:
// ------------
// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com)
//
//////////////////////////////////////////////////////
//
// Global Properties ...
#property library
#property copyright "Copyright 2023, SaherElm IT Center"
#property link "https://saherelm.ir"
#property version "1.00"
#property description "SaherElm Library for XCAEA Signaller"
#property strict
//
// Imports ...
#include "../../Libraries/x-saherelm.common.lib.mq5"
#include "../../Libraries/x-saherelm.x-poi.lib.mq5"
#include "../../Libraries/x-saherelm.x-trade.lib.mq5"
#include "../Classes/xcaea.x-poi.detector.class.mq5"
#include "../Classes/xcaea.x-poi.drawer.class.mq5"
#include "../Helpers/xcaea.helper.mq5"
//
// Enumeration ...
//
// Guard Actions ...
enum ENUM_GUARD_ACTIONS
{
X_GUARD_ACTION_NONE, // Nothing to Do
X_GUARD_ACTION_CLOSE, // Close Specified Position
X_GUARD_ACTION_CLOSE_ALL, // Close All Positions
X_GUARD_ACTION_CLOSE_LONGS, // Close All Long Positions
X_GUARD_ACTION_CLOSE_SHORTS, // Close All Short Position
X_GUARD_ACTION_PARTIAL_CLOSE, // Partial Close Specified Position
X_GUARD_ACTION_TRAIL_STOP, // Trail Stop of Specified Position
X_GUARD_ACTION_TRAIL_TARGET, // Trail Target of Specified Position
X_GUARD_ACTION_HEDGE, // Hedge Specified Positions
};
//
// Definitions ...
//
// Conditions Struct ...
struct XCAEAStrategyConditions
{
//
// Props ...
//
string symbol;
ENUM_TIMEFRAMES period;
//
// Setup Props ...
//
double sl;
double tp;
double pivot;
double point;
string provider;
double targets[];
//
datetime time;
datetime setupTime;
datetime triggerTime;
//
XBoxZone signalBox;
ENUM_X_DIRECTION dir;
ENUM_X_POSITION_TYPES type;
XCAEAConditions conditions;
//
// Constructor ...
XCAEAStrategyConditions()
{
Clean();
}
//
// Tools ...
/**
* Cleaning Up ...
*/
void Clean()
{
//
sl = 0;
tp = 0;
pivot = 0;
point = 0;
//
symbol = NULL;
period = NULL;
provider = NULL;
//
time = NULL;
setupTime = NULL;
triggerTime = NULL;
//
Clean(targets);
//
signalBox.Clean();
conditions.Clean();
//
dir = X_DIRECTION_NONE;
type = X_POSITION_TYPE_NONE;
//
}
//
// Signalling ...
/**
* Validate ...
*
* @return ( bool )
*/
bool IsValid()
{
//
bool result = false;
//
result = IsSpecifiedValid(symbol) &&
IsSpecifiedValid(period) &&
IsSpecifiedValid(time);
//
return result;
}
/**
* Check Conditions Has Valid Bullish Signal ...
*
* @return ( bool )
*/
bool HasBullishSignal()
{
//
bool result = false;
//
result =
(sl > 0 ||
tp > 0) &&
IsValid() &&
HasDirection(dir);
if (!result)
{
return result;
}
//
result =
IsBullish(dir);
//
return result;
}
/**
* Check Conditions Has Valid Bearish Signal ...
*
* @return ( bool )
*/
bool HasBearishSignal()
{
//
bool result = false;
//
result =
(sl > 0 ||
tp > 0) &&
IsValid() &&
HasDirection(dir);
if (!result)
{
return result;
}
//
result =
IsBearish(dir);
//
return result;
}
//
// Setting Up and Triggering Up ...
/**
* Check Condition is Setting Up ...
*
* @param dir: ENUM_X_DIRECTION member, Setting Up Direction ...
*
* @return ( bool )
*/
bool IsSetuped()
{
//
bool result = false;
//
result = IsValid(setupTime) &&
HasDirection(dir);
if (!result)
{
return result;
}
//
return result;
}
/**
* Calculate Setup Age ...
*
* @return ( int )
*/
int GetSetupAge()
{
//
int result = 0;
//
if (!IsSetuped())
{
return result;
}
//
result = (int)(TimeCurrent() - setupTime) / PeriodSeconds(period);
//
return result;
}
/**
* Detect How we Can Trigger Signal ...
*
* @return ( bool )
*/
bool CanTrigger()
{
//
bool result = false;
//
result =
//
sl > 0 &&
IsValid(symbol) &&
IsValid(period) &&
IsValid(triggerTime) &&
type != X_POSITION_TYPE_ALL &&
type != X_POSITION_TYPE_NONE
//
;
//
return result;
}
//
};
//
// Model a Guard Action ...
struct XCAEAGuard
{
//
// Props ...
ENUM_GUARD_ACTIONS action;
datetime time;
//
string symbol;
string provider;
//
// Specified Position ...
ulong ticket;
//
// Partial Close ...
double volumeMultiplier;
//
// SL Trial ...
double sl;
//
// TP Trial ...
double tp;
//
// Constructor ...
XCAEAGuard()
{
Clean();
}
//
// Tools ...
/**
* Cleanup ...
*/
void Clean()
{
//
time = NULL;
action = X_GUARD_ACTION_NONE;
//
symbol = NULL;
provider = NULL;
//
ticket = 0;
//
volumeMultiplier = 0;
//
sl = 0;
tp = 0;
//
ZeroMemory(this);
}
/**
* Validate ...
*
* @return ( bool )
*/
bool IsValid()
{
//
bool result = false;
//
result =
//
IsValid(time) &&
IsValid(symbol) &&
IsValid(provider) &&
action != X_GUARD_ACTION_NONE
//
;
if (!result)
{
return result;
}
//
// Validate Model Based On Specified Guard Actions ...
//
return result;
}
};
/**
* Add Guard to Collection ...
*
* @param guard: XCAEAGuard instance ...
* @param guards: XCAEAGuard instance Collection ...
*
* @return ( int )
*/
int AddGuard(
XCAEAGuard &guard,
XCAEAGuard &guards[] //
)
{
//
int result = 0;
//
if (!guard.IsValid())
{
return result;
}
//
AddRef(
guard,
guards //
);
//
result = ArraySize(guards);
//
return result;
}
//
bool DetectXCAEAConditions(
XCXCAEAPOIDrawer *drawer,
ENUM_X_DIRECTION trend,
XBoxZone &pivots[],
XCAEAConditions &conditions,
XBoxZone &pivotBox,
XBoxZone &box,
double &additionalSL,
ENUM_X_DIRECTION &dir,
XCXCAEAHelper *helper,
int barIndex = 0,
int loopback = 10 //
)
{
//
bool result = false;
//
int idx = -1;
int count = 0;
bool has = false;
//
box.Clean();
additionalSL = 0;
conditions.Clean();
dir = X_DIRECTION_NONE;
//
if (barIndex < 0)
{
barIndex = 0;
}
loopback = NormalizeInt(loopback, 5);
//
// Retrieve Some Requirements ...
string symbol = helper.GetSymbol();
ENUM_TIMEFRAMES period = helper.GetPeriod();
double points = GetPoints(symbol);
//
// Trend Parsing ...
bool hasTrend = HasDirection(trend);
bool hasBullishTrend = hasTrend &&
IsBullish(trend);
bool hasBearishTrend = hasTrend &&
IsBearish(trend);
//
// Retrieve Previous and Current Bar Conditions ...
XCAEAConditions pConditions;
result = helper.GetConditions(
conditions,
barIndex,
loopback //
);
result = result &&
helper.GetConditions(
pConditions,
barIndex + 1,
loopback //
);
if (!result)
{
//
conditions.Clean();
pConditions.Clean();
//
return result;
}
//
// Define IDXses ...
int zIDX = barIndex;
int cIDX = zIDX + 1;
int pIDX = cIDX + 1;
int p2IDX = pIDX + 1;
int p3IDX = p2IDX + 1;
int p4IDX = p3IDX + 1;
//
// Reading Bars ...
//
XOHCL zBar;
XOHCL cBar;
XOHCL pBar;
XOHCL p2Bar;
XOHCL p3Bar;
XOHCL p4Bar;
result = zBar.Init(
symbol,
period,
zIDX //
);
result =
result &&
zBar.GetPreviousBar(cBar);
result =
result &&
cBar.GetPreviousBar(pBar);
result =
result &&
pBar.GetPreviousBar(p2Bar);
result =
result &&
p2Bar.GetPreviousBar(p3Bar);
result =
result &&
p3Bar.GetPreviousBar(p4Bar);
if (!result)
{
//
zBar.Clean();
cBar.Clean();
pBar.Clean();
p2Bar.Clean();
p3Bar.Clean();
p4Bar.Clean();
//
box.Clean();
conditions.Clean();
pConditions.Clean();
//
return result;
}
//
// Bars Conditions ...
//
// Temparory Bar Direction ...
ENUM_X_DIRECTION cBarDir;
//
// Hammer ...
bool isCBarHammer = helper
.barAnalyser
.IsHammer(
cBar,
cBarDir //
);
bool isCBarBullishHammer =
isCBarHammer &&
IsBullish(cBarDir);
bool isCBarBearishHammer =
isCBarHammer &&
IsBearish(cBarDir);
//
// Rejected ...
bool isCBarRejected = helper
.barAnalyser
.IsRejected(
cBar,
cBarDir,
false, // Force Type ...
true // Force Fibo Pressure ...
);
bool isCBarBullishRejected =
isCBarRejected &&
IsBullish(cBarDir);
bool isCBarBearishRejected =
isCBarRejected &&
IsBearish(cBarDir);
//
// Engulfed ...
bool isCBarEngulfed = helper
.barAnalyser
.IsEngulfed(
cBar,
cBarDir //
);
bool isCBarBullishEngulfed =
isCBarEngulfed &&
IsBullish(cBarDir);
bool isCBarBearishEngulfed =
isCBarEngulfed &&
IsBearish(cBarDir);
//
// Momentum ...
bool isCBarMomentum = helper
.barAnalyser
.IsMomentum(
cBar,
cBarDir,
1 //
);
bool isCBarBullishMomentum =
isCBarMomentum &&
IsBullish(cBarDir);
bool isCBarBearishMomentum =
isCBarMomentum &&
IsBearish(cBarDir);
//
// Bar Sumarise ...
//
bool isCBarValidForBullish =
(isCBarBullishHammer ||
isCBarBullishRejected ||
isCBarBullishMomentum ||
isCBarBullishEngulfed);
//
bool isCBarValidForBearish =
(isCBarBearishHammer ||
isCBarBearishRejected ||
isCBarBearishMomentum ||
isCBarBearishEngulfed);
//
// Score ...
//
double bullishScore = 0;
double bearishScore = 0;
conditions.GenerateScore(
bullishScore,
bearishScore //
);
//
bool isScoreBullish =
bullishScore > bearishScore;
//
bool isScoreBearish =
bearishScore > bullishScore;
//
// Generating Conditions Summary ...
string summary =
conditions
.GenerateSummary();
//
// Conditions ...
//
// PEAK ...
double zPeak = conditions.peakBuffer[zIDX];
double cPeak = conditions.peakBuffer[cIDX];
double pPeak = conditions.peakBuffer[pIDX];
double p2Peak = conditions.peakBuffer[p2IDX];
//
// VALE ...
double zVale = conditions.valeBuffer[zIDX];
double cVale = conditions.valeBuffer[cIDX];
double pVale = conditions.valeBuffer[pIDX];
double p2Vale = conditions.valeBuffer[p2IDX];
//
// X3MA ...
//
// FAST ...
//
double z3MAFast = conditions.fastBuffer[zIDX];
double c3MAFast = conditions.fastBuffer[cIDX];
double p3MAFast = conditions.fastBuffer[pIDX];
double p23MAFast = conditions.fastBuffer[p2IDX];
//
double z3MAFastState = conditions.fastStateBuffer[zIDX];
double c3MAFastState = conditions.fastStateBuffer[cIDX];
double p3MAFastState = conditions.fastStateBuffer[pIDX];
double p23MAFastState = conditions.fastStateBuffer[p2IDX];
//
// MEDIUM ...
//
double z3MAMedium = conditions.mediumBuffer[zIDX];
double c3MAMedium = conditions.mediumBuffer[cIDX];
double p3MAMedium = conditions.mediumBuffer[pIDX];
double p23MAMedium = conditions.mediumBuffer[p2IDX];
//
double z3MAMediumState = conditions.mediumStateBuffer[zIDX];
double c3MAMediumState = conditions.mediumStateBuffer[cIDX];
double p3MAMediumState = conditions.mediumStateBuffer[pIDX];
double p23MAMediumState = conditions.mediumStateBuffer[p2IDX];
//
// SLOW ...
//
double z3MASlow = conditions.slowBuffer[zIDX];
double c3MASlow = conditions.slowBuffer[cIDX];
double p3MASlow = conditions.slowBuffer[pIDX];
double p23MASlow = conditions.slowBuffer[p2IDX];
//
double z3MASlowState = conditions.slowStateBuffer[zIDX];
double c3MASlowState = conditions.slowStateBuffer[cIDX];
double p3MASlowState = conditions.slowStateBuffer[pIDX];
double p23MASlowState = conditions.slowStateBuffer[p2IDX];
//
double x3maBullishGapUpper = c3MAMedium;
double x3maBullishGapLower = c3MASlow;
//
double x3maBearishGapUpper = c3MASlow;
double x3maBearishGapLower = c3MAMedium;
//
// Create Conditions ...
//
bool isX3MABullishState =
z3MAFast > c3MAFast &&
isCBarValidForBullish &&
c3MAFast > c3MAMedium &&
isCBarBullishRejected &&
c3MAMedium > c3MASlow &&
cBar.low < x3maBullishGapLower &&
cBar.GetDown() > x3maBullishGapLower;
//
bool isX3MABearishState =
z3MAFast < c3MAFast &&
isCBarValidForBearish &&
c3MAFast < c3MAMedium &&
isCBarBearishRejected &&
c3MAMedium < c3MASlow &&
cBar.high > x3maBearishGapLower &&
cBar.GetUp() < x3maBearishGapLower;
//
// Parsing Pivots ...
//
// Select Inside Boxes ...
XBoxZone insidePivots[];
int insidePivotsCount = SelectInsideBoxes(
insidePivots,
pivots,
zBar,
cBar,
pBar,
p2Bar //
);
bool hasInsidePivots = IsValidSize(insidePivotsCount);
if (hasInsidePivots) {
//
drawer.DrawBoxes(insidePivots, TimeCurrent());
}
//
// Detect Selected Pivot ...
XBoxZone rejectedPivot;
double providedSL = 0;
bool hasPivots = HasChild(pivots);
if (hasPivots)
{
//
has = SelectRejectedBox(
rejectedPivot,
pivots,
zBar,
cBar,
pBar,
p2Bar,
true,
true //
);
}
//
// Signaller Summarization ...
//
// Cond1 Act Using PEAK VALE Box Activation or Rejection ...
//
bool isCond1Bullish =
//
false
//
;
//
bool isCond1Bearish =
//
false
//
;
//
bool isCond1 = isCond1Bullish ||
isCond1Bearish;
if (isCond1)
{
//
providedSL =
isCond1Bullish
? MathMin(pBar.low, pivotBox.lower)
: MathMax(pBar.high, pivotBox.upper);
//
additionalSL = 0.5 * conditions.atrBuffer[cIDX];
//
Print("Cond1");
isCond1Bullish = false;
isCond1Bearish = false;
}
//
// Cond2 Act Using OSC Box and Vydia ...
//
bool isCond2Bullish =
//
false
//
;
//
bool isCond2Bearish =
//
false
//
;
//
bool isCond2 = isCond2Bullish ||
isCond2Bearish;
if (isCond2)
{
//
providedSL =
isCond2Bullish
? MathMin(pBar.low, pivotBox.lower)
: MathMax(pBar.high, pivotBox.upper);
//
Print("Cond2");
}
//
// Cond3 Act Using CCi Peaks and Vales ...
//
bool isCond3Bullish =
//
false
//
;
//
bool isCond3Bearish =
//
false
//
;
//
bool isCond3 = isCond3Bullish ||
isCond3Bearish;
if (isCond3)
{
//
providedSL =
isCond3Bullish
? MathMin(pBar.low, pivotBox.lower)
: MathMax(pBar.high, pivotBox.upper);
//
Print("Cond3");
}
//
// Summarise Conditions ...
//
bool isBullish =
//
isCond1Bullish ||
isCond2Bullish ||
isCond3Bullish;
//
;
//
bool isBearish =
//
isCond1Bearish ||
isCond2Bearish ||
isCond3Bearish
//
;
//
result = isBullish ||
isBearish;
if (result)
{
//
dir =
isBullish
? X_DIRECTION_BULLISH
: X_DIRECTION_BEARISH;
//
double entry = GetEntry(
conditions.symbol,
dir //
);
//
double sl =
providedSL > 0
? providedSL
: isBullish
? pivotBox.lower
: pivotBox.upper;
//
box.dir = dir;
box.symbol = conditions.symbol;
box.period = conditions.period;
//
box.upper =
isBullish
? entry
: sl;
//
box.lower =
isBullish
? sl
: entry;
//
box.to = zBar.time;
box.from = p4Bar.time;
//
box.type = "XCASignal";
}
//
result = box.IsValid() &&
HasDirection(dir);
//
// Cleanup Resources ...
//
if (!result)
{
//
box.Clean();
pivotBox.Clean();
conditions.Clean();
}
//
zBar.Clean();
cBar.Clean();
pBar.Clean();
p2Bar.Clean();
p3Bar.Clean();
p4Bar.Clean();
pConditions.Clean();
rejectedPivot.Clean();
//
return result;
}
//
// Select Inside Boxes ...
int SelectInsideBoxes(
XBoxZone &insideBoxes[],
XBoxZone &boxes[],
XOHCL &zBar,
XOHCL &cBar,
XOHCL &pBar,
XOHCL &p2Bar //
)
{
//
int result = 0;
//
Clean(insideBoxes);
//
bool has =
zBar.IsValid() &&
cBar.IsValid() &&
pBar.IsValid() &&
p2Bar.IsValid() &&
HasChild(boxes);
if (!has)
{
return result;
}
//
int count = ArraySize(boxes);
for (int i = 0; i < count; i++)
{
//
XBoxZone iBox = boxes[i];
//
// Check Box Type ...
bool isTypePassed =
//
iBox.type == GetBoxType(XCA_TREND_BULL) ||
iBox.type == GetBoxType(XCA_TREND_BEAR)
//
;
if (!isTypePassed)
{
//
iBox.Clean();
//
continue;
}
//
bool isBullish = iBox.IsBullish();
bool isBearish = iBox.IsBearish();
//
// Check Inside Conditions ...
//
bool isBullishInside =
//
isBullish &&
//
((cBar.low < iBox.upper &&
cBar.low > iBox.lower) ||
(cBar.GetDown() < iBox.upper &&
cBar.GetDown() > iBox.lower))
//
;
//
bool isBearishInside =
//
isBearish &&
//
((cBar.high > iBox.lower &&
cBar.high < iBox.upper) ||
(cBar.GetUp() > iBox.lower &&
cBar.GetUp() < iBox.upper))
//
;
//
has = isBullishInside ||
isBearishInside;
if (has)
{
//
AddRef(
iBox,
insideBoxes //
);
}
//
iBox.Clean();
}
//
result = ArraySize(insideBoxes);
//
return result;
}
//
bool SelectRejectedBox(
XBoxZone &box,
XBoxZone &boxes[],
XOHCL &zBar,
XOHCL &cBar,
XOHCL &pBar,
XOHCL &p2Bar,
bool forceBarType = false,
bool forcePressure = false //
)
{
//
bool result = false;
//
box.Clean();
//
// Validate ...
result = HasChild(boxes) &&
zBar.IsValid() &&
cBar.IsValid() &&
pBar.IsValid() &&
p2Bar.IsValid();
if (!result)
{
return result;
}
//
int count = ArraySize(boxes);
for (int i = 0; i < count; i++)
{
//
XBoxZone iBox = boxes[i];
//
bool isBullish = iBox.IsBullish();
bool isBearish = iBox.IsBearish();
//
double boundaryPrice =
isBullish
? iBox.upper
: iBox.lower;
//
double midPrice =
iBox.lower +
((iBox.upper - iBox.lower) / 2);
//
bool isMidBullishRejected = cBar.IsRejected(
midPrice,
X_DIRECTION_BULLISH,
forceBarType,
forcePressure //
);
//
bool isBoundaryBullishRejected = cBar.IsRejected(
boundaryPrice,
X_DIRECTION_BULLISH,
forceBarType,
forcePressure //
);
//
bool isMidBearishRejected = cBar.IsRejected(
midPrice,
X_DIRECTION_BEARISH,
forceBarType,
forcePressure //
);
//
bool isBoundaryBearishRejected = cBar.IsRejected(
boundaryPrice,
X_DIRECTION_BEARISH,
forceBarType,
forcePressure //
);
//
bool isBullishRejected =
isBullish &&
(isMidBullishRejected ||
isBoundaryBullishRejected);
//
bool isBearishRejected =
isBearish &&
(isMidBearishRejected ||
isBoundaryBearishRejected);
//
bool isRejected =
isBullishRejected ||
isBearishRejected;
if (isRejected)
{
//
box = iBox;
break;
}
//
iBox.Clean();
}
//
result = box.IsValid();
//
return result;
}
//