Files
MQL5Data/X121SMCEA/Strategy/x-121.smc.test.strategy.class.mq5
T
2024-12-16 08:29:07 +03:30

1893 lines
52 KiB
Plaintext

///////////////////////////////////////////////////////
//
// SaherElm IT Center MQL5 Class Library
// --------------------------------------
// Name: XCX121SMCTestStrategy
// Description: provides all based classes for use ...
//
//
// Maintainer:
// ------------
// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com)
//
//////////////////////////////////////////////////////
//
// Global Properties ...
#property library
#property copyright "Copyright 2023, SaherElm IT Center"
#property link "https://www.saherelm.ir"
#property version "1.00"
#property strict
//
// Imports ...
//
#include "../Classes/x-121.smc.base.strategy.class.mq5"
#include "../Classes/x-121.smc.market.cycle.helper.class.mq5"
//
// Definitions ...
//
// XStrategy Class Implementation(s) ...
class XCX121SMCTestStrategy : public XCX121SMCBaseStrategy
{
//
// Public ...
public:
//
//
// Constructor(s) ...
void XCX121SMCTestStrategy(
//
// Base ...
string _symbol, // Trading Symbol
ENUM_TIMEFRAMES _period // Trading TimeFrame
)
: XCX121SMCBaseStrategy(_symbol, _period)
{
InitialHelpers();
}
//
// Deconstructur ...
void ~XCX121SMCTestStrategy()
{
}
//
// Overrides Actions ...
/**
* Destroy All Class Implementations ...
*/
void Destroy() override
{
//
delete mTriggerCycleHelper;
delete mDecisionCycleHelper;
delete mAnalyseCycleHelper;
delete mVerificationCycleHelper;
delete mConsolidationCycleHelper;
delete mVisionCycleHelper;
}
/**
* Check Conditions For Signal ...
*/
bool HasSignal(
XSignal &signal,
X121SMCStrategyConditions &conditions //
) override
{
//
bool result = false;
//
signal.Clean();
conditions.Clean();
//
int pushers = 0;
//
double sl = 0;
double tp = 0;
double risk = 0;
double entry = 0;
double reward = 0;
double r2r = R2R();
string provider = "";
double volume = Volume();
ENUM_POSITION_TYPE type = POSITION_TYPE_BUY;
ENUM_X_ORDER_MODES mode = X_ORDER_MODE_MARKET;
//
bool hasLong = false;
bool hasShort = false;
//
double selectedSL = 0;
//
// Start Calculations ...
//
// Retrieve Common Data ...
string symbol = GetSymbol();
ENUM_TIMEFRAMES period = GetPeriod();
//
// Required Value For SL/TP Calculations ...
double points = GetPoints(symbol);
double pip = GetPipPrice(symbol);
double pip2 = 2 * pip;
//
// Retrieve and Fill Cycle Conditions ...
result = GetCyclesConditions(conditions);
if (!result)
{
//
conditions.Clean();
return result;
}
//
// Check Spread for Signalling Conditions ...
bool isSpreadPassed = IsSpreadPass();
result = isSpreadPassed;
if (!result)
{
//
conditions.Clean();
return result;
}
//
// Detect Signal Conditions ...
bool hasSignal = false;
//
bool hasSMPVSignal = false;
bool hasRJBPVSignal = false;
bool hasVWAPCSignal = false;
bool hasTestSignal = false;
//
// X_121_SMC_PROVIDER_SMPV ...
if (!hasSignal)
{
//
// hasSMPVSignal = DetectSamePeaksAndValesSignal(conditions);
// hasSignal = hasSMPVSignal;
}
//
// X_121_SMC_PROVIDER_RJBPV ...
if (!hasSignal)
{
// //
// hasRJBPVSignal = DetectRJBPVSignal(conditions);
// hasSignal = hasRJBPVSignal;
}
//
// X_121_SMC_PROVIDER_VWAPC ...
if (!hasSignal)
{
// //
// hasVWAPCSignal = DetectVWAPCSignal(conditions);
// hasSignal = hasVWAPCSignal;
}
//
if (!hasSignal)
{
//
hasTestSignal = DetectTestSignal(conditions);
hasSignal = hasTestSignal;
}
//
result = hasSignal;
if (!result)
{
//
conditions.Clean();
return result;
}
//
// Combine all Signals Conditions ...
selectedSL = conditions.sl;
provider = conditions.provider;
//
hasLong =
//
IsBullish(conditions.signalDir)
//
;
//
hasShort =
//
IsBearish(conditions.signalDir)
//
;
//
result = hasLong ||
hasShort;
//
// Rmove Signal Condition ...
if (result)
{
//
// TYPE ...
type =
hasLong
? POSITION_TYPE_BUY
: POSITION_TYPE_SELL;
ENUM_X_POSITION_TYPES xType =
hasLong
? X_POSITION_TYPE_LONG
: X_POSITION_TYPE_SHORT;
//
entry = GetEntry(
conditions.symbol,
type //
);
//
double slAddition = 0;
sl =
hasLong
? selectedSL - slAddition
: selectedSL + slAddition;
//
// RISK Reward ...
risk =
hasLong
? entry - sl
: sl - entry;
reward = risk * r2r;
tp =
hasLong
? entry + reward
: entry - reward;
//
signal.sl = sl;
signal.tp = tp;
signal.type = type;
signal.mode = mode;
signal.entry = entry;
signal.volume = volume;
signal.symbol = symbol;
signal.period = period;
signal.pushers = pushers;
signal.provider = provider;
signal.time = TimeCurrent();
//
result = PrepareSignal(signal);
if (result)
{
DrawSignal(signal);
}
//
hasLong = false;
hasShort = false;
}
//
return result;
}
/**
* Customize Strategy Identifier ...
*/
string GetTag() override
{
return X121SMCStrategyToken;
}
//
// Protected ...
protected:
//
//
// Props ...
//
// Trigger Order Flow ...
XPVPivot mOrderFlow[];
ENUM_X_DIRECTION mOrderFlowDir;
//
ENUM_X_CYCLE_EVENTS mTriggerCycleEvents[];
XC121SMCCycleHelper *mTriggerCycleHelper;
//
ENUM_X_CYCLE_EVENTS mDecisionCycleEvents[];
XC121SMCCycleHelper *mDecisionCycleHelper;
//
ENUM_X_CYCLE_EVENTS mAnalyseCycleEvents[];
XC121SMCCycleHelper *mAnalyseCycleHelper;
//
ENUM_X_CYCLE_EVENTS mVerificationCycleEvents[];
XC121SMCCycleHelper *mVerificationCycleHelper;
//
ENUM_X_CYCLE_EVENTS mConsolidationCycleEvents[];
XC121SMCCycleHelper *mConsolidationCycleHelper;
//
ENUM_X_CYCLE_EVENTS mVisionCycleEvents[];
XC121SMCCycleHelper *mVisionCycleHelper;
//
// Actions ...
/**
* Retrieve Cycles Conditions ...
*
* @param conditions: X121SMCStrategyConditions instance Reference ...
*
* @return ( bool )
*/
bool GetCyclesConditions(
X121SMCStrategyConditions &conditions //
)
{
//
bool result = false;
//
string symbol = GetSymbol();
ENUM_TIMEFRAMES period = GetPeriod();
//
int zIndex = 0;
int cIndex = zIndex + 1;
int pIndex = cIndex + 1;
int ppIndex = pIndex + 1;
//
datetime cTime = TimeCurrent();
//
conditions.time = cTime;
conditions.symbol = symbol;
conditions.period = period;
//
int conditionsLoopback = 7;
//
// Fill Cycles Conditions ...
//
// Trigger ...
result = mTriggerCycleHelper.GetConditions(
mTriggerCycleEvents,
conditions.triggerConditions,
zIndex,
conditionsLoopback //
);
if (!result)
{
//
conditions.Clean();
return result;
}
conditions.triggerConditions.state = mTriggerState;
//
// Decision ...
result = mDecisionCycleHelper.GetConditions(
mDecisionCycleEvents,
conditions.decisionConditions,
zIndex,
conditionsLoopback //
);
if (!result)
{
//
conditions.Clean();
return result;
}
conditions.decisionConditions.state = mDecisionState;
//
// Analyse ...
result = mAnalyseCycleHelper.GetConditions(
mAnalyseCycleEvents,
conditions.analyseConditions,
zIndex,
conditionsLoopback //
);
if (!result)
{
//
conditions.Clean();
return result;
}
conditions.analyseConditions.state = mAnalyseState;
//
// Verification ...
result = mVerificationCycleHelper.GetConditions(
mVerificationCycleEvents,
conditions.verificationConditions,
zIndex,
conditionsLoopback //
);
if (!result)
{
//
conditions.Clean();
return result;
}
conditions.verificationConditions.state = mVerificationState;
//
// Consolidation ...
result = mConsolidationCycleHelper.GetConditions(
mConsolidationCycleEvents,
conditions.consolidationConditions,
zIndex,
conditionsLoopback //
);
if (!result)
{
//
conditions.Clean();
return result;
}
conditions.consolidationConditions.state = mConsolidationState;
//
// Vision ...
result = mVisionCycleHelper.GetConditions(
mVisionCycleEvents,
conditions.visionConditions,
zIndex,
conditionsLoopback //
);
if (!result)
{
//
conditions.Clean();
return result;
}
conditions.visionConditions.state = mVisionState;
//
return result;
}
//
// Signalling Functions ...
//
// TODO: Remove this ...
XSMCStrategySetupConditions mTestConditions;
bool DetectTestSignal(
X121SMCStrategyConditions &conditions //
)
{
//
bool result = false;
//
string symbol = GetSymbol();
ENUM_TIMEFRAMES period = GetPeriod();
//
ENUM_X_121_SMC_PROVIDERS provider = X_121_SMC_PROVIDER_SMPV;
string providerStr = ToString(provider);
//
int zIndex = 0;
int cIndex = zIndex + 1;
int pIndex = cIndex + 1;
int ppIndex = pIndex + 1;
//
XOHCL zBar;
result = zBar.Init(
symbol,
period,
zIndex //
);
if (!result)
{
return result;
}
//
XOHCL cBar;
result = cBar.Init(
symbol,
period,
cIndex //
);
if (!result)
{
return result;
}
//
bool isBullish = false;
bool isBearish = false;
//
double ask = GetAsk(symbol);
double bid = GetBid(symbol);
datetime cTime = TimeCurrent();
//
double ll = cBar.FindLowest(9, MODE_LOW);
double hh = cBar.FindHighest(9, MODE_HIGH);
//
double selectedSL = 0;
//
X121SMCCycleConditions triggerConditions = conditions.triggerConditions;
X121SMCCycleConditions decisionConditions = conditions.decisionConditions;
X121SMCCycleConditions analyseConditions = conditions.analyseConditions;
X121SMCCycleConditions verificationConditions = conditions.verificationConditions;
X121SMCCycleConditions consolidationConditions = conditions.consolidationConditions;
X121SMCCycleConditions visionConditions = conditions.visionConditions;
//
XPOIState triggerState = triggerConditions.state;
XPOIState decisionState = decisionConditions.state;
XPOIState analyseState = analyseConditions.state;
XPOIState verificationState = verificationConditions.state;
XPOIState consolidationState = consolidationConditions.state;
XPOIState visionState = visionConditions.state;
//
// Retrieve Peak and Vale ...
double triggerPeak = triggerConditions.x121Conditions.peaksBuffer[0];
double triggerVale = triggerConditions.x121Conditions.valesBuffer[0];
//
int zoneValidationDivider = 10;
int validPivotRepetition = mTriggerCycleHelper.mX121Helper
.GetDonChainLength();
//
datetime setupTime = NULL;
bool isSetuped = mTestConditions.IsSetuped();
ENUM_X_DIRECTION setupDir = mTestConditions.dir;
if (!isSetuped)
{
//
// Detect Valid Peaks and Vales ...
//
// Peaks ...
XPVPivotPoint validPeak = mTestConditions.validPeak;
bool hasValidPeak = validPeak.IsValid();
if (!hasValidPeak)
{
//
// Detecte Valid Peaks ...
//
XPVPivotPoint triggerValidPeaks[];
int triggerValidPeaksCount = mTriggerCycleHelper
.FillPeakPivotPoints(triggerValidPeaks);
//
bool isValid =
IsValidSize(triggerValidPeaksCount);
if (isValid)
{
//
// Try to Find ...
for (int i = triggerValidPeaksCount - 1; i >= 0; i--)
{
//
XPVPivotPoint iPivot = triggerValidPeaks[i];
double iValue = iPivot.value;
//
bool isValid = iValue == triggerConditions.x121Conditions.peaksBuffer[0] &&
iValue == decisionConditions.x121Conditions.peaksBuffer[0] &&
iValue == analyseConditions.x121Conditions.peaksBuffer[0] &&
iValue == verificationConditions.x121Conditions.peaksBuffer[0];
if (isValid)
{
//
validPeak = iPivot;
break;
}
}
//
hasValidPeak = validPeak.IsValid();
if (hasValidPeak)
{
//
mTestConditions.validPeak = validPeak;
//
if (!mTestConditions.validVale.IsValid())
{
//
XValueChange valesChanges[];
int valeChangesCount = mTriggerCycleHelper.FillValesChanges(valesChanges);
if (IsValidSize(valeChangesCount))
{
//
XValueChange lastChange = valesChanges[valeChangesCount - 1];
if (lastChange.IsValid())
{
//
XPVPivotPoint iPivot;
iPivot.repetition = 1;
iPivot.type = XPV_VALE;
iPivot.time = lastChange.time;
iPivot.value = lastChange.after;
if (iPivot.IsValid())
{
mTestConditions.validVale = iPivot;
}
}
}
}
}
}
}
//
// Vales ...
XPVPivotPoint validVale = mTestConditions.validVale;
bool hasValidVale = validVale.IsValid();
if (!hasValidVale)
{
//
// Detecte Valid Vale ...
//
XPVPivotPoint triggerValidVales[];
int triggerValidValesCount = mTriggerCycleHelper
.FillValePivotPoints(triggerValidVales);
//
bool isValid =
IsValidSize(triggerValidValesCount);
if (isValid)
{
//
// Try to Find ...
for (int i = triggerValidValesCount - 1; i >= 0; i--)
{
//
XPVPivotPoint iPivot = triggerValidVales[i];
double iValue = iPivot.value;
//
bool isValid = iValue == triggerConditions.x121Conditions.valesBuffer[0] &&
iValue == decisionConditions.x121Conditions.valesBuffer[0] &&
iValue == analyseConditions.x121Conditions.valesBuffer[0] &&
iValue == verificationConditions.x121Conditions.valesBuffer[0];
if (isValid)
{
//
validVale = iPivot;
break;
}
}
//
hasValidVale = validVale.IsValid();
if (hasValidVale)
{
//
mTestConditions.validVale = validVale;
//
if (!mTestConditions.validPeak.IsValid())
{
//
XValueChange valesChanges[];
int valeChangesCount = mTriggerCycleHelper.FillPeaksChanges(valesChanges);
if (IsValidSize(valeChangesCount))
{
//
XValueChange lastChange = valesChanges[valeChangesCount - 1];
if (lastChange.IsValid())
{
//
XPVPivotPoint iPivot;
iPivot.repetition = 1;
iPivot.type = XPV_PEAK;
iPivot.time = lastChange.time;
iPivot.value = lastChange.after;
if (iPivot.IsValid())
{
mTestConditions.validPeak = iPivot;
}
}
}
}
}
}
}
bool hasValidPivot = hasValidPeak &&
hasValidVale;
result = hasValidPivot;
if (!result)
{
return result;
}
//
mTestConditions.peak = triggerPeak;
mTestConditions.vale = triggerVale;
//
// We Sure we Have Valid Peak and Valid Vale ...
// Create a Zone ...
bool hasZone = mTestConditions.zone.IsValid();
if (!hasZone)
{
//
double pvZoneUpper = validPeak.value;
double pvZoneLower = validVale.value;
datetime pvZoneFrom =
validPeak.time < validVale.time
? validPeak.time
: validVale.time;
int pvZoneLoopback = iBarShift(
symbol,
period,
pvZoneFrom //
);
//
XConsolidationZone pvZone;
result = pvZone.Init(
symbol,
period,
pvZoneUpper,
pvZoneLower,
pvZoneLoopback //
);
if (!result)
{
return result;
}
//
mTestConditions.zone = pvZone;
hasZone = mTestConditions.zone.IsValid();
}
if (hasZone)
{
//
// Update Zone ...
mTestConditions.UpdateZone();
//
XCConsolidationZoneObject *iPVZoneObj;
iPVZoneObj = new XCConsolidationZoneObject();
bool isCreated = iPVZoneObj.Create(
mPOIDrawer.ChartIdentification(),
mPOIDrawer.SubWindowIdentification(),
mTestConditions.zone //
);
if (isCreated)
{
//
iPVZoneObj.ZoneWidth(4);
iPVZoneObj.ZoneColor(clrGold);
//
AddObjectIfNotExists(iPVZoneObj);
}
}
//
// Here we Have to Check Price Go into Zone ...
bool isZoneBreaked = mTestConditions.zone.IsBreaked();
result = isZoneBreaked;
if (!result)
{
return result;
}
//
isSetuped = true;
setupTime = cTime;
mTestConditions.setupTime = setupTime;
setupDir = mTestConditions.zone.breakDirection;
mTestConditions.dir = setupDir;
}
//
// Setup Forms ...
bool canTrigger = mTestConditions.CanTrigger();
if (!canTrigger)
{
//
// Check Trigger Consitions ...
if (cTime - setupTime > 2400)
{
//
ClearDraws();
//
mTestConditions.Clean();
return false;
}
// //
// canTrigger = true;
// mTestConditions.triggerTime = cTime;
}
//
// Issues Signal on Conditions ...
// conditions.signalDir = mTestConditions.dir;
// conditions.provider = providerStr;
// conditions.sl = mTestConditions.sl;
//
// mTestConditions.Clean();
//
return result;
}
//
// Private ...
private:
//
// Props ...
/**
* Initial Required Indicators Helper ...
*/
void InitialHelpers()
{
//
string symbol = GetSymbol();
ENUM_TIMEFRAMES period = GetPeriod();
//
// Short ...
ENUM_X_PERIOD_METHOD scMethod = X_PERIOD_AUTO; // How to Find Period
ENUM_TIMEFRAMES scPeriod = NULL; // Time Period
//
// Medium ...
ENUM_X_PERIOD_METHOD mcMethod = X_PERIOD_AUTO; // How to Find Period
ENUM_TIMEFRAMES mcPeriod = NULL; // Time Period
//
// Long ...
ENUM_X_PERIOD_METHOD lcMethod = X_PERIOD_AUTO; // How to Find Period
ENUM_TIMEFRAMES lcPeriod = NULL; // Time Period
//
// Hind ...
ENUM_X_PERIOD_METHOD hcMethod = X_PERIOD_AUTO; // How to Find Period
ENUM_TIMEFRAMES hcPeriod = NULL; // Time Period
//
// XPV ...
X121Inputs x121Inputs;
//
x121Inputs.Default();
//
x121Inputs.scMethod = scMethod;
x121Inputs.scPeriod = scPeriod;
x121Inputs.mcMethod = mcMethod;
x121Inputs.mcPeriod = mcPeriod;
x121Inputs.lcMethod = lcMethod;
x121Inputs.lcPeriod = lcPeriod;
x121Inputs.hcMethod = hcMethod;
x121Inputs.hcPeriod = hcPeriod;
//
// Initialize Cycle Helpers ...
//
mTriggerCycleHelper = new XC121SMCCycleHelper();
mTriggerCycleHelper.Init(
symbol,
PERIOD_M1,
x121Inputs //
);
//
mDecisionCycleHelper = new XC121SMCCycleHelper();
mDecisionCycleHelper.Init(
symbol,
PERIOD_M5,
x121Inputs //
);
//
mAnalyseCycleHelper = new XC121SMCCycleHelper();
mAnalyseCycleHelper.Init(
symbol,
PERIOD_M15,
x121Inputs //
);
//
mVerificationCycleHelper = new XC121SMCCycleHelper();
mVerificationCycleHelper.Init(
symbol,
PERIOD_M30,
x121Inputs //
);
//
mConsolidationCycleHelper = new XC121SMCCycleHelper();
mConsolidationCycleHelper.Init(
symbol,
PERIOD_H1,
x121Inputs //
);
//
mVisionCycleHelper = new XC121SMCCycleHelper();
mVisionCycleHelper.Init(
symbol,
PERIOD_H4,
x121Inputs //
);
}
//
// SL Selector Methods ...
/**
* Select Specified Type of Stop Loss ...
*
* @param conditions: X121SMCStrategyConditions instance Reference ...
* @param forDir: ENUM_X_DIRECTION member, Signal Direction ...
* @param type: ENUM_X_121_SMC_SL_TYPES member, Specified Required SL Type ...
*
* @return ( double )
*/
double SelectSL(
X121SMCStrategyConditions &conditions,
ENUM_X_DIRECTION forDir,
ENUM_X_121_SMC_SL_TYPES type //
)
{
//
double result = 0;
//
string symbol = GetSymbol();
ENUM_TIMEFRAMES period = GetPeriod();
//
bool isValid =
//
HasDirection(forDir) &&
conditions.IsValid() &&
type != X_121_SMC_SL_TYPE_NONE
//
;
if (!isValid)
{
return result;
}
//
XOHCL zBar;
bool isInited = zBar.Init(
symbol,
period,
0 //
);
if (!isInited)
{
return result;
}
//
bool isBullish = IsBullish(forDir);
//
if (type == X_121_SMC_SL_TYPE_FIBO_LEVEL_3)
{
result = conditions.triggerConditions.x121Conditions.fl3Buffer[0];
}
else if (type == X_121_SMC_SL_TYPE_FIBO_LEVEL_1_5)
{
//
result =
isBullish
? conditions.triggerConditions.x121Conditions.fl1Buffer[0]
: conditions.triggerConditions.x121Conditions.fl5Buffer[0];
}
else if (type == X_121_SMC_SL_TYPE_DON_CLOSE_BOX)
{
//
result =
isBullish
? conditions.triggerConditions.x121Conditions.donCloseLowerBuffer[0]
: conditions.triggerConditions.x121Conditions.donCloseUpperBuffer[0];
}
else if (type == X_121_SMC_SL_TYPE_SWING)
{
//
int swingLowsCount = conditions.triggerConditions.state.CountSwingLows();
int swingHighsCount = conditions.triggerConditions.state.CountSwingHighs();
result =
isBullish
? conditions.triggerConditions.state.swingLows[swingLowsCount - 1].GetValue()
: conditions.triggerConditions.state.swingHighs[swingHighsCount - 1].GetValue();
}
else if (type == X_121_SMC_SL_TYPE_REJECTION)
{
//
result =
isBullish
? conditions.triggerConditions.state.bullishRejectionBars[conditions.triggerConditions.state.CountBullishRejectionBars() - 1].Lower()
: conditions.triggerConditions.state.bearishRejectionBars[conditions.triggerConditions.state.CountBearishRejectionBars() - 1].Upper();
}
else if (type == X_121_SMC_SL_TYPE_MOMENTUM)
{
//
result =
isBullish
? conditions.triggerConditions.state.bullishMomentumBars[conditions.triggerConditions.state.CountBullishMomentumBars() - 1].Lower()
: conditions.triggerConditions.state.bearishMomentumBars[conditions.triggerConditions.state.CountBearishMomentumBars() - 1].Upper();
}
else if (type == X_121_SMC_SL_TYPE_VWAP_FAST)
{
result = conditions.triggerConditions.x121Conditions.vwapFastBuffer[0];
}
else if (type == X_121_SMC_SL_TYPE_VWAP_MID)
{
result = conditions.triggerConditions.x121Conditions.vwapMidBuffer[0];
}
else if (type == X_121_SMC_SL_TYPE_VWAP_SLOW)
{
result = conditions.triggerConditions.x121Conditions.vwapSlowBuffer[0];
}
else if (type == X_121_SMC_SL_TYPE_CURRENT_SAR)
{
result = conditions.triggerConditions.x121Conditions.sarBuffer[0];
}
else if (type == X_121_SMC_SL_TYPE_TENKAN_SEN)
{
//
double hh = zBar.FindHighest(
9,
MODE_HIGH //
);
double ll = zBar.FindLowest(
9,
MODE_LOW //
);
double mid = (hh - ll) / 2;
result = isBullish
? ll - mid
: hh + mid;
}
else if (type == X_121_SMC_SL_TYPE_CURRENT_SAR_BOX ||
type == X_121_SMC_SL_TYPE_LAST_SAR_CHANGED_BAR ||
type == X_121_SMC_SL_TYPE_LAST_DIRECTIONAL_SAR)
{
//
XOHCL cSarChangeBar;
XOHCL pSarChangeBar;
XValueChange cSarChange; // Current Sar Change (IsDirect) ...
XValueChange pSarChange; // Prev Sar Change (Direct) ...
XValueChange sarChanges[];
int sarChangesCount = mTriggerCycleHelper
.FillSarChanges(sarChanges);
if (!IsValidSize(sarChangesCount) || sarChangesCount < 2)
{
return result;
}
//
//
cSarChange = sarChanges[sarChangesCount - 1];
pSarChange = sarChanges[sarChangesCount - 2];
//
bool isFilled = cSarChange.FillBar(
cSarChangeBar,
symbol,
period //
);
if (!isFilled)
{
return result;
}
//
isFilled = pSarChange.FillBar(
pSarChangeBar,
symbol,
period //
);
if (!isFilled)
{
return result;
}
//
if (type == X_121_SMC_SL_TYPE_LAST_SAR_CHANGED_BAR)
{
//
result = isBullish
? pSarChangeBar.low
: pSarChangeBar.high;
}
else if (type == X_121_SMC_SL_TYPE_CURRENT_SAR_BOX)
{
//
result =
isBullish
? zBar.FindLowest(
MathAbs(cSarChangeBar.Index() - 1),
MODE_LOW //
)
: zBar.FindHighest(
MathAbs(cSarChangeBar.Index() - 1),
MODE_HIGH //
);
}
else if (type == X_121_SMC_SL_TYPE_LAST_DIRECTIONAL_SAR)
{
//
XOHCL prevBar;
bool isInited = cSarChangeBar.GetPreviousBar(prevBar);
if (!isInited)
{
return result;
}
//
result = isBullish
? prevBar.low
: prevBar.high;
}
}
//
return result;
}
//
// Drawing Functions ...
/**
* Draw Pivot ...
*
* @param pivot: XPVPivot instance Reference ...
*/
void DrawPivot(XPVPivot &pivot)
{
//
if (!pivot.IsValid())
{
return;
}
//
XCXPVPivotObject *iObj;
iObj = new XCXPVPivotObject();
bool isCreated = iObj.Create(
mPOIDrawer.ChartIdentification(),
mPOIDrawer.SubWindowIdentification(),
pivot //
);
if (isCreated)
{
//
if (pivot.IsPeak())
{
//
iObj.PivotWidth(1);
iObj.PivotFill(false);
iObj.PivotColor(clrAqua);
iObj.PivotStyle(STYLE_SOLID);
}
//
if (pivot.IsVale())
{
//
iObj.PivotWidth(1);
iObj.PivotFill(false);
iObj.PivotStyle(STYLE_SOLID);
iObj.PivotColor(clrMagenta);
}
//
AddObjectIfNotExists(iObj);
}
}
/**
* Custom Drawing State ...
*
* @param state: XPOIState instance reference, Specified Which state to Draw ...
* @param forceDrawSamePeriod: Boolean ...
*/
void CustomStateDrawing(
XPOIState &state,
bool forceDrawSamePeriod = false,
ENUM_X_DIRECTION forDir = X_DIRECTION_NONE,
//
// Ignores List ...
bool ignoreSwingHighs = false,
bool ignoreSwingLows = false,
bool ignoreSupportZones = false,
bool ignoreResistanceZones = false,
bool ignoreSupplyZones = false,
bool ignoreDemandZones = false,
bool ignoreBullishOrderBlocks = false,
bool ignoreBearishOrderBlocks = false,
bool ignoreBullishFairValueGaps = false,
bool ignoreBearishFairValueGaps = false,
bool ignoreBullishRejectionBars = false,
bool ignoreBearishRejectionBars = false,
bool ignoreBullishMomentumBars = false,
bool ignoreBearishMomentumBars = false //
)
{
//
XPOIState tmpState = state;
if (forceDrawSamePeriod)
{
//
int count = 0;
ENUM_TIMEFRAMES period = GetPeriod();
//
count = state.CountSwingHighs();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCSwing iSwing = state.swingHighs[i];
//
XOHCL iBar;
bool isFilled = iSwing.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.swingHighs,
i,
1 //
);
}
}
}
//
count = state.CountSwingLows();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCSwing iSwing = state.swingLows[i];
//
XOHCL iBar;
bool isFilled = iSwing.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.swingLows,
i,
1 //
);
}
}
}
//
count = state.CountBullishMomentumBars();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCMomentumBar iMomentum = state.bullishMomentumBars[i];
//
XOHCL iBar;
bool isFilled = iMomentum.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.bullishMomentumBars,
i,
1 //
);
}
}
}
//
count = state.CountBearishMomentumBars();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCMomentumBar iMomentum = state.bearishMomentumBars[i];
//
XOHCL iBar;
bool isFilled = iMomentum.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.bearishMomentumBars,
i,
1 //
);
}
}
}
//
count = state.CountBullishRejectionBars();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCRejectionBar iRejection = state.bullishRejectionBars[i];
//
XOHCL iBar;
bool isFilled = iRejection.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.bullishRejectionBars,
i,
1 //
);
}
}
}
//
count = state.CountBearishRejectionBars();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCRejectionBar iRejection = state.bearishRejectionBars[i];
//
XOHCL iBar;
bool isFilled = iRejection.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.bearishRejectionBars,
i,
1 //
);
}
}
}
//
count = state.CountSupportZones();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCSupportZone iZone = state.supportZones[i];
//
XOHCL iBar;
bool isFilled = iZone.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.supportZones,
i,
1 //
);
}
}
}
//
count = state.CountResistanceZones();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCResistanceZone iZone = state.resistanceZones[i];
//
XOHCL iBar;
bool isFilled = iZone.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.resistanceZones,
i,
1 //
);
}
}
}
//
count = state.CountSupplyZones();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCSupplyZone iZone = state.supplyZones[i];
//
XOHCL iBar;
bool isFilled = iZone.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.supplyZones,
i,
1 //
);
}
}
}
//
count = state.CountDemandZones();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCDemandZone iZone = state.demandZones[i];
//
XOHCL iBar;
bool isFilled = iZone.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.demandZones,
i,
1 //
);
}
}
}
//
count = state.CountBullishOrderBlocks();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCOrderBlock iZone = state.bullishOrderBlocks[i];
//
XOHCL iBar;
bool isFilled = iZone.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.bullishOrderBlocks,
i,
1 //
);
}
}
}
//
count = state.CountBearishOrderBlocks();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCOrderBlock iZone = state.bearishOrderBlocks[i];
//
XOHCL iBar;
bool isFilled = iZone.FillBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.bearishOrderBlocks,
i,
1 //
);
}
}
}
//
count = state.CountBullishFairValueGaps();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCFVG iZone = state.bullishFairValueGaps[i];
//
XOHCL iBar;
bool isFilled = iZone.FillStartBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.bullishFairValueGaps,
i,
1 //
);
}
}
}
//
count = state.CountBearishFairValueGaps();
if (IsValidSize(count))
{
//
for (int i = 0; i < count; i++)
{
//
XCFVG iZone = state.bearishFairValueGaps[i];
//
XOHCL iBar;
bool isFilled = iZone.FillStartBar(iBar);
if (!isFilled)
{
continue;
}
//
bool isSamePeriod = iBar.period == period;
if (!isSamePeriod)
{
//
ArrayRemove(
tmpState.bearishFairValueGaps,
i,
1 //
);
}
}
}
//
}
//
bool drawSwingHighs = true;
bool drawSwingLows = true;
bool drawSupportZones = true;
bool drawResistanceZones = true;
bool drawSupplyZones = true;
bool drawDemandZones = true;
bool drawBullishOrderBlocks = true;
bool drawBearishOrderBlocks = true;
bool drawBullishFairValueGaps = true;
bool drawBearishFairValueGaps = true;
bool drawBullishRejectionBars = true;
bool drawBearishRejectionBars = true;
bool drawBullishMomentumBars = true;
bool drawBearishMomentumBars = true;
//
// Change Drawing Specs Conditions based on
// Provided Direction ...
if (forDir == X_DIRECTION_BULLISH)
{
//
drawSwingLows = true;
drawDemandZones = true;
drawSupportZones = true;
drawBullishOrderBlocks = true;
drawBullishFairValueGaps = true;
drawBullishRejectionBars = true;
drawBullishMomentumBars = true;
//
drawSwingHighs = false;
drawSupplyZones = false;
drawResistanceZones = false;
drawBearishOrderBlocks = false;
drawBearishFairValueGaps = false;
drawBearishRejectionBars = false;
drawBearishMomentumBars = false;
}
else if (forDir == X_DIRECTION_BEARISH)
{
//
drawSwingLows = false;
drawDemandZones = false;
drawSupportZones = false;
drawBullishOrderBlocks = false;
drawBullishFairValueGaps = false;
drawBullishRejectionBars = false;
drawBullishMomentumBars = false;
//
drawSwingHighs = true;
drawSupplyZones = true;
drawResistanceZones = true;
drawBearishOrderBlocks = true;
drawBearishFairValueGaps = true;
drawBearishRejectionBars = true;
drawBearishMomentumBars = true;
}
//
// Apply Ignore List ...
//
if (ignoreSwingHighs)
{
drawSwingHighs = false;
}
//
if (ignoreSwingLows)
{
drawSwingLows = false;
}
//
if (ignoreSupportZones)
{
drawSupportZones = false;
}
//
if (ignoreResistanceZones)
{
drawResistanceZones = false;
}
//
if (ignoreSupplyZones)
{
drawSupplyZones = false;
}
//
if (ignoreDemandZones)
{
drawDemandZones = false;
}
//
if (ignoreBullishOrderBlocks)
{
drawBullishOrderBlocks = false;
}
//
if (ignoreBearishOrderBlocks)
{
drawBearishOrderBlocks = false;
}
//
if (ignoreBullishFairValueGaps)
{
drawBullishFairValueGaps = false;
}
//
if (ignoreBearishFairValueGaps)
{
drawBearishFairValueGaps = false;
}
//
if (ignoreBullishRejectionBars)
{
drawBullishRejectionBars = false;
}
//
if (ignoreBearishRejectionBars)
{
drawBearishRejectionBars = false;
}
//
if (ignoreBullishMomentumBars)
{
drawBullishMomentumBars = false;
}
//
if (ignoreBearishMomentumBars)
{
drawBearishMomentumBars = false;
}
//
DrawState(
tmpState, // State ...
true, // Update To of all Drawings Till now ...
drawSwingHighs, // Draw SwingHighs ..
drawSwingLows, // Draw SwingLows ..
drawSupportZones, // Draw SupportZones ..
drawResistanceZones, // Draw ResistanceZones ..
drawSupplyZones, // Draw SupplyZones ..
drawDemandZones, // Draw DemandZones ..
drawBullishOrderBlocks, // Draw BullishOrderBlocks ..
drawBearishOrderBlocks, // Draw BearishOrderBlocks ..
drawBullishFairValueGaps, // Draw BullishFairValueGaps ..
drawBearishFairValueGaps, // Draw BearishFairValueGaps ..
drawBullishRejectionBars, // Draw BullishRejectionBars ..
drawBearishRejectionBars, // Draw BearishRejectionBars ..
drawBullishMomentumBars, // Draw BullishMomentumBars ..
drawBearishMomentumBars, // Draw BearishMomentumBars ..
true // Draw Ticks Zone ...
);
}
//
};
//