/////////////////////////////////////////////////////// // // 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; // ZeroMemory(this); } // // 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 TestDetectSignal( XCXCAEAHelper *helper, XCXCAEAPOIDrawer *drawer, XBoxZone &box, ENUM_X_DIRECTION &dir, XCAEAConditions &conditions, int barIndex = 0, int loopback = 10 // ) { // bool result = false; // int idx = -1; int count = 0; bool has = false; // box.Clean(); conditions.Clean(); dir = X_DIRECTION_NONE; barIndex = NormalizeInt(barIndex, 0); loopback = NormalizeInt(loopback, 5); // // Retrieve Some Requirements ... string symbol = helper.GetSymbol(); ENUM_TIMEFRAMES period = helper.GetPeriod(); double points = GetPoints(symbol); // // Retrieve Conditions for Processing ... result = helper.GetConditions( conditions, barIndex, loopback // ); if (!result) { // box.Clean(); conditions.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; // 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(); // return result; } // // Bars Conditions ... // // Score ... // double bullishScore = 0; double bearishScore = 0; conditions.GenerateScore( bullishScore, bearishScore // ); // bool isScoreBullish = bullishScore > bearishScore; // bool isScoreBearish = bearishScore > bullishScore; // bool isScoreNeutural = MathAbs(bullishScore - bearishScore) == 0; // // Calculating Range Volumes ... // double bullishVolume = 0; double bearishVolume = 0; helper.barAnalyser.CalculateRangeVolume( cBar, bullishVolume, bearishVolume, loopback // ); // bool isVolumeNeutural = MathAbs(bullishVolume - bearishVolume) == 0; // // Reading Values ... // // PEAK ... double zPeak = conditions.peakBuffer[zIDX]; double cPeak = conditions.peakBuffer[cIDX]; double pPeak = conditions.peakBuffer[pIDX]; double p2Peak = conditions.peakBuffer[p2IDX]; double p3Peak = conditions.peakBuffer[p3IDX]; double p4Peak = conditions.peakBuffer[p4IDX]; // // VALE ... double zVale = conditions.valeBuffer[zIDX]; double cVale = conditions.valeBuffer[cIDX]; double pVale = conditions.valeBuffer[pIDX]; double p2Vale = conditions.valeBuffer[p2IDX]; double p3Vale = conditions.valeBuffer[p3IDX]; double p4Vale = conditions.valeBuffer[p4IDX]; // // SWING Low ... double zSWL = conditions.swingLowBuffer[zIDX]; double cSWL = conditions.swingLowBuffer[cIDX]; double pSWL = conditions.swingLowBuffer[pIDX]; double p2SWL = conditions.swingLowBuffer[p2IDX]; double p3SWL = conditions.swingLowBuffer[p3IDX]; // // SWING High ... double zSWH = conditions.swingHighBuffer[zIDX]; double cSWH = conditions.swingHighBuffer[cIDX]; double pSWH = conditions.swingHighBuffer[pIDX]; double p2SWH = conditions.swingHighBuffer[p2IDX]; double p3SWH = conditions.swingHighBuffer[p3IDX]; // // SUPPORT ... double zSupport = conditions.supportBuffer[zIDX]; double cSupport = conditions.supportBuffer[cIDX]; double pSupport = conditions.supportBuffer[pIDX]; double p2Support = conditions.supportBuffer[p2IDX]; double p3Support = conditions.supportBuffer[p3IDX]; // // RESISTANCE ... double zResistance = conditions.resistanceBuffer[zIDX]; double cResistance = conditions.resistanceBuffer[cIDX]; double pResistance = conditions.resistanceBuffer[pIDX]; double p2Resistance = conditions.resistanceBuffer[p2IDX]; double p3Resistance = conditions.resistanceBuffer[p3IDX]; // // MAH ... double zMAH = conditions.mahBuffer[zIDX]; double cMAH = conditions.mahBuffer[cIDX]; double pMAH = conditions.mahBuffer[pIDX]; double p2MAH = conditions.mahBuffer[p2IDX]; double p3MAH = conditions.mahBuffer[p3IDX]; // // MAL ... double zMAL = conditions.malBuffer[zIDX]; double cMAL = conditions.malBuffer[cIDX]; double pMAL = conditions.malBuffer[pIDX]; double p2MAL = conditions.malBuffer[p2IDX]; double p3MAL = conditions.malBuffer[p3IDX]; // // MAC ... double zMAC = conditions.macBuffer[zIDX]; double cMAC = conditions.macBuffer[cIDX]; double pMAC = conditions.macBuffer[pIDX]; double p2MAC = conditions.macBuffer[p2IDX]; double p3MAC = conditions.macBuffer[p3IDX]; // // FIBO Level 1 ... double zFib1 = conditions.fiboLevel1Buffer[zIDX]; double cFib1 = conditions.fiboLevel1Buffer[cIDX]; double pFib1 = conditions.fiboLevel1Buffer[pIDX]; double p2Fib1 = conditions.fiboLevel1Buffer[p2IDX]; double p3Fib1 = conditions.fiboLevel1Buffer[p3IDX]; // // FIBO Level 2 ... double zFib2 = conditions.fiboLevel2Buffer[zIDX]; double cFib2 = conditions.fiboLevel2Buffer[cIDX]; double pFib2 = conditions.fiboLevel2Buffer[pIDX]; double p2Fib2 = conditions.fiboLevel2Buffer[p2IDX]; double p3Fib2 = conditions.fiboLevel2Buffer[p3IDX]; // // FIBO Level 3 ... double zFib3 = conditions.fiboLevel3Buffer[zIDX]; double cFib3 = conditions.fiboLevel3Buffer[cIDX]; double pFib3 = conditions.fiboLevel3Buffer[pIDX]; double p2Fib3 = conditions.fiboLevel3Buffer[p2IDX]; double p3Fib3 = conditions.fiboLevel3Buffer[p3IDX]; // // FIBO Level 4 ... double zFib4 = conditions.fiboLevel4Buffer[zIDX]; double cFib4 = conditions.fiboLevel4Buffer[cIDX]; double pFib4 = conditions.fiboLevel4Buffer[pIDX]; double p2Fib4 = conditions.fiboLevel4Buffer[p2IDX]; double p3Fib4 = conditions.fiboLevel4Buffer[p3IDX]; // // FIBO Level 5 ... double zFib5 = conditions.fiboLevel5Buffer[zIDX]; double cFib5 = conditions.fiboLevel5Buffer[cIDX]; double pFib5 = conditions.fiboLevel5Buffer[pIDX]; double p2Fib5 = conditions.fiboLevel5Buffer[p2IDX]; double p3Fib5 = conditions.fiboLevel5Buffer[p3IDX]; // // Create Custom Conditions ... // // Bar and Fibo Conditions ... // // Bearish ... // // Strong Reversal ... bool isZBarOnFiboStrongBearish = zBar.low > zFib5; bool isCBarOnFiboStrongBearish = cBar.low > cFib5; bool isPBarOnFiboStrongBearish = pBar.low > pFib5; bool isP2BarOnFiboStrongBearish = p2Bar.low > p2Fib5; bool isP3BarOnFiboStrongBearish = p3Bar.low > p3Fib5; // // Golden Zone Reversal ... bool isZBarOnFiboGoldenBearish = zBar.low > zFib3 && zBar.high < zFib4; bool isCBarOnFiboGoldenBearish = cBar.low > cFib3 && cBar.high < cFib4; bool isPBarOnFiboGoldenBearish = pBar.low > pFib3 && pBar.high < pFib4; bool isP2BarOnFiboGoldenBearish = p2Bar.low > p2Fib3 && p2Bar.high < p2Fib4; bool isP3BarOnFiboGoldenBearish = p3Bar.low > p3Fib3 && p3Bar.high < p3Fib4; // // Bullish ... // // Strong Reversal ... bool isZBarOnFiboStrongBullish = zBar.high < zFib1; bool isCBarOnFiboStrongBullish = cBar.high < cFib1; bool isPBarOnFiboStrongBullish = pBar.high < pFib1; bool isP2BarOnFiboStrongBullish = p2Bar.high < p2Fib1; bool isP3BarOnFiboStrongBullish = p3Bar.high < p3Fib1; // // Golden Zone Reversal ... bool isZBarOnFiboGoldenBullish = zBar.low > zFib2 && zBar.high < zFib3; bool isCBarOnFiboGoldenBullish = cBar.low > cFib2 && cBar.high < cFib3; bool isPBarOnFiboGoldenBullish = pBar.low > pFib2 && pBar.high < pFib3; bool isP2BarOnFiboGoldenBullish = p2Bar.low > p2Fib2 && p2Bar.high < p2Fib3; bool isP3BarOnFiboGoldenBullish = p3Bar.low > p3Fib2 && p3Bar.high < p3Fib3; // // Score and Volume Conditions ... // bool isScoreVolumeNeutural = isScoreNeutural || isVolumeNeutural; // bool isScoreVolumeNeuturalInFiboStrongBullish = isScoreNeutural && isCBarOnFiboStrongBullish; bool isScoreVolumeNeuturalInFiboGoldenBullish = isScoreNeutural && isCBarOnFiboGoldenBullish; // bool isScoreVolumeNeuturalInFiboStrongBearish = isScoreNeutural && isCBarOnFiboStrongBearish; bool isScoreVolumeNeuturalInFiboGoldenBearish = isScoreNeutural && isCBarOnFiboGoldenBearish; // bool isScoreVolumeNeuturalBullishPowered = isScoreVolumeNeuturalInFiboStrongBullish || isScoreVolumeNeuturalInFiboGoldenBullish; bool isScoreVolumeNeuturalBearishPowered = isScoreVolumeNeuturalInFiboStrongBearish || isScoreVolumeNeuturalInFiboGoldenBearish; // // PEAK and VALES ... // // PEAK Pivot ... bool isZIsPeakPivot = zPeak == cPeak && zPeak == zSWH && zPeak == zResistance && isZBarOnFiboStrongBearish; bool isCIsPeakPivot = cPeak == pPeak && cPeak == cSWH && cPeak == cResistance && isCBarOnFiboStrongBearish; bool isPIsPeakPivot = pPeak == p2Peak && pPeak == pSWH && pPeak == pResistance && isPBarOnFiboStrongBearish; bool isP2IsPeakPivot = p2Peak == p3Peak && p2Peak == p2SWH && p2Peak == p2Resistance && isP2BarOnFiboStrongBearish; bool isP3IsPeakPivot = p3Peak == p4Peak && p3Peak == p3SWH && p3Peak == p3Resistance && isP3BarOnFiboStrongBearish; // // VALE Pivot ... bool isZIsValePivot = zVale == cVale && zVale == zSWL && zVale == zSupport && isZBarOnFiboStrongBullish; bool isCIsValePivot = cVale == pVale && cVale == cSWL && cVale == cSupport && isCBarOnFiboStrongBullish; bool isPIsValePivot = pVale == p2Vale && pVale == pSWL && pVale == pSupport && isPBarOnFiboStrongBullish; bool isP2IsValePivot = p2Vale == p3Vale && p2Vale == p2SWL && p2Vale == p2Support && isP2BarOnFiboStrongBullish; bool isP3IsValePivot = p3Vale == p4Vale && p3Vale == p3SWL && p3Vale == p3Support && isP3BarOnFiboStrongBullish; // // Testing Conditions ... // // Score and Volume Conditions ... if (isScoreVolumeNeuturalBullishPowered || isScoreVolumeNeuturalBearishPowered) { // ENUM_X_DIRECTION iScoreVolumeDir = isScoreVolumeNeuturalBullishPowered ? X_DIRECTION_BULLISH : X_DIRECTION_BEARISH; // int timeOffset = (int)cBar.time; string iName = ToString(iScoreVolumeDir) + "_SCVM_" + ToString(timeOffset); color iColor = isScoreVolumeNeuturalBullishPowered ? clrAqua : clrMagenta; ENUM_LINE_STYLE iStyle = STYLE_DOT; // // CChartObjectVLine *iObj; // iObj = new CChartObjectVLine(); // has = iObj.Create( // 0, // iName, // 0, // cBar.time // // ); // if (has) // { // // // iObj.Color(iColor); // iObj.Style(iStyle); // } // // // Print("Conditions Finder ..."); } // // PVPivot Conditions ... if (isCIsPeakPivot || isCIsValePivot) { // ENUM_X_DIRECTION iPVPivotDir = isCIsValePivot ? X_DIRECTION_BULLISH : X_DIRECTION_BEARISH; // int timeOffset = (int)cBar.time; string iName = ToString(iPVPivotDir) + "_PVPVT_" + ToString(timeOffset); color iColor = isCIsValePivot ? clrAqua : clrMagenta; ENUM_LINE_STYLE iStyle = STYLE_DOT; // // // CChartObjectVLine *iObj; // iObj = new CChartObjectVLine(); // has = iObj.Create( // 0, // iName, // 0, // cBar.time // // ); // if (has) // { // // // iObj.Color(iColor); // iObj.Style(iStyle); // } // // // Print("Conditions Finder ..."); } // // Summarise Result ... // bool isBullish = false; bool isBearish = false; // result = isBullish || isBearish; if (result) { // // Do Signal Preparing ... // // Check Box is Prepared or Not ... result = box.IsValid(); } // // Cleaning Up ... // zBar.Clean(); cBar.Clean(); pBar.Clean(); p2Bar.Clean(); p3Bar.Clean(); p4Bar.Clean(); // if (!result) { // box.Clean(); conditions.Clean(); } // return result; } // // Cond 2 ... // - a PV Box is Sweep Liquidity; // - a Directional FVg Occures Exactly after Liquidity Sweep; // - Price Action Go Inside FVG; // - SL behind FVG; // bool DetectXCAEAConditions( XCXCAEAPOIDrawer *drawer, XBoxZone &pivots[], XCAEAConditions &conditions, XBoxZone &pivotBox, XBoxZone &box, double &targets[], 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; // bool isScoreNeutural = MathAbs(bullishScore - bearishScore) == 0; // // Calculating Range Volumes ... // double bullishVolume = 0; double bearishVolume = 0; int volumeRangeLoopback = loopback; helper.barAnalyser.CalculateRangeVolume( cBar, bullishVolume, bearishVolume, volumeRangeLoopback // ); // bool isVolumeNeutural = MathAbs(bullishVolume - bearishVolume) == 0; // double rangeVolume = bullishVolume == bearishVolume; double rangeVolumeAvg = rangeVolume / volumeRangeLoopback; // bool isVolumeBullish = bullishVolume > bearishVolume; bool isVolumeBearish = bullishVolume < bearishVolume; bool isVolumeOverLast = cBar.volume > pBar.volume; bool isVolumeOverAvg = cBar.volume > rangeVolumeAvg; // // Conditions ... // // SAR ... double zSar = conditions.sarBuffer[zIDX]; double cSar = conditions.sarBuffer[cIDX]; double pSar = conditions.sarBuffer[pIDX]; double p2Sar = conditions.sarBuffer[p2IDX]; // // 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]; // // PEAKGOLDEN ... double zPeakGolden = conditions.peakGoldenBuffer[zIDX]; double cPeakGolden = conditions.peakGoldenBuffer[cIDX]; double pPeakGolden = conditions.peakGoldenBuffer[pIDX]; double p2PeakGolden = conditions.peakGoldenBuffer[p2IDX]; // // VALEGOLDEN ... double zValeGolden = conditions.valeGoldenBuffer[zIDX]; double cValeGolden = conditions.valeGoldenBuffer[cIDX]; double pValeGolden = conditions.valeGoldenBuffer[pIDX]; double p2ValeGolden = conditions.valeGoldenBuffer[p2IDX]; // // SUPPORT ... double zSupport = conditions.supportBuffer[zIDX]; double cSupport = conditions.supportBuffer[cIDX]; double pSupport = conditions.supportBuffer[pIDX]; double p2Support = conditions.supportBuffer[p2IDX]; // // RESISTANCE ... double zResistance = conditions.resistanceBuffer[zIDX]; double cResistance = conditions.resistanceBuffer[cIDX]; double pResistance = conditions.resistanceBuffer[pIDX]; double p2Resistance = conditions.resistanceBuffer[p2IDX]; // // SWING LOW ... double zSwingLow = conditions.swingLowBuffer[zIDX]; double cSwingLow = conditions.swingLowBuffer[cIDX]; double pSwingLow = conditions.swingLowBuffer[pIDX]; double p2SwingLow = conditions.swingLowBuffer[p2IDX]; // // SWING HIGH ... double zSwingHigh = conditions.swingHighBuffer[zIDX]; double cSwingHigh = conditions.swingHighBuffer[cIDX]; double pSwingHigh = conditions.swingHighBuffer[pIDX]; double p2SwingHigh = conditions.swingHighBuffer[p2IDX]; // // TREND ... double zTrend = conditions.trendBuffer[zIDX]; double cTrend = conditions.trendBuffer[cIDX]; double pTrend = conditions.trendBuffer[pIDX]; double p2Trend = conditions.trendBuffer[p2IDX]; // // KI ... double zKI = conditions.kiBuffer[zIDX]; double cKI = conditions.kiBuffer[cIDX]; double pKI = conditions.kiBuffer[pIDX]; double p2KI = conditions.kiBuffer[p2IDX]; // // TKI ... double zTKI = conditions.tkiBuffer[zIDX]; double cTKI = conditions.tkiBuffer[cIDX]; double pTKI = conditions.tkiBuffer[pIDX]; double p2TKI = conditions.tkiBuffer[p2IDX]; // // VIDYA ... double zVIDYA = conditions.vidyaBuffer[zIDX]; double cVIDYA = conditions.vidyaBuffer[cIDX]; double pVIDYA = conditions.vidyaBuffer[pIDX]; double p2VIDYA = conditions.vidyaBuffer[p2IDX]; // // RSI ... double zRSI = conditions.rsiBuffer[zIDX]; double cRSI = conditions.rsiBuffer[cIDX]; double pRSI = conditions.rsiBuffer[pIDX]; double p2RSI = conditions.rsiBuffer[p2IDX]; // // CCI ... double zCCI = conditions.cciBuffer[zIDX]; double cCCI = conditions.cciBuffer[cIDX]; double pCCI = conditions.cciBuffer[pIDX]; double p2CCI = conditions.cciBuffer[p2IDX]; // // ATR ... double zATR = conditions.atrBuffer[zIDX]; double cATR = conditions.atrBuffer[cIDX]; double pATR = conditions.atrBuffer[pIDX]; double p2ATR = conditions.atrBuffer[p2IDX]; // // ADX ... double zADX = conditions.adxBuffer[zIDX]; double cADX = conditions.adxBuffer[cIDX]; double pADX = conditions.adxBuffer[pIDX]; double p2ADX = conditions.adxBuffer[p2IDX]; // // ADX P ... double zADXP = conditions.adxpBuffer[zIDX]; double cADXP = conditions.adxpBuffer[cIDX]; double pADXP = conditions.adxpBuffer[pIDX]; double p2ADXP = conditions.adxpBuffer[p2IDX]; // // ADX N ... double zADXN = conditions.adxnBuffer[zIDX]; double cADXN = conditions.adxnBuffer[cIDX]; double pADXN = conditions.adxnBuffer[pIDX]; double p2ADXN = conditions.adxnBuffer[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; // double cTrendValues[7] = { cKI, cTKI, cTrend, cVIDYA, c3MAFast, c3MASlow, c3MAMedium, }; double pTrendValues[7] = { pKI, pTKI, pTrend, pVIDYA, p3MAFast, p3MASlow, p3MAMedium, }; // double minCTrendValue = GetMin(cTrendValues); double maxCTrendValue = GetMax(cTrendValues); // double minPTrendValue = GetMin(pTrendValues); double maxPTrendValue = GetMax(pTrendValues); // double cTrendValuesRange = (maxCTrendValue - minCTrendValue); double cTrendValuesRangePoint = (cTrendValuesRange / points); // double pTrendValuesRange = (maxPTrendValue - minPTrendValue); double pTrendValuesRangePoint = (pTrendValuesRange / points); // // Create Conditions ... // bool isPRSIOB = pRSI > conditions.rsiOBLevel; // bool isPRSIOS = pRSI < conditions.rsiOSLevel; // bool isRSIBullish = cRSI > pRSI && !conditions.isRSIOB; // bool isRSIBearish = cRSI < pRSI && !conditions.isRSIOS; // bool isPCCIOB = pCCI > conditions.cciOBLevel; // bool isPCCIOS = pCCI < conditions.cciOSLevel; // bool isCCIBullish = cCCI > pCCI && !conditions.isCCIOB; // bool isCCIBearish = cCCI < pCCI && !conditions.isCCIOS; // bool isADXBullish = cADX > cADXN; bool isADXBullishPrev = pADX > pADXN; // bool isADXSwitchedToBullish = isADXBullish && !isADXBullishPrev; // bool isADXBearish = cADX > cADXN; bool isADXBearishPrev = pADX > pADXN; // bool isADXSwitchedToBearish = isADXBearish && !isADXBearishPrev; // double barStrongAtrMult = 1.5; // bool isCBarRangeHasStrongATR = cBar.GetRange() > cATR * barStrongAtrMult; // bool isCBarBodyHasStrongATR = cBar.GetBody() > cATR * barStrongAtrMult; // bool isCBarHasStrongATR = isCBarRangeHasStrongATR && isCBarBodyHasStrongATR; // bool isCBarIsStrongBullish = isCBarHasStrongATR && cBar.IsBullish(); // bool isCBarIsStrongBearish = isCBarHasStrongATR && cBar.IsBearish(); // bool isLowOverMax = cBar.low > maxCTrendValue; bool isHighUnderMin = cBar.high < minCTrendValue; bool isCloseOverMax = cBar.close > maxCTrendValue; bool isCloseUnderMin = cBar.close < minCTrendValue; // bool isCTrendRangeValid = cTrendValuesRangePoint <= 50; bool isPTrendRangeValid = pTrendValuesRangePoint <= 50; // bool isTrendRangeSwitchedToValid = isCTrendRangeValid && !isPTrendRangeValid; bool isTrendRangeFinishedFromValid = !isCTrendRangeValid && isPTrendRangeValid; // bool isPeakGoldenRejected = cBar.high > cPeakGolden && cBar.GetUp() <= cPeakGolden; // bool isValeGoldenRejected = cBar.low < cValeGolden && cBar.GetDown() >= cValeGolden; // bool isX3MaBullishState = // z3MAFast > z3MAMedium && c3MAFast > c3MAMedium && z3MAMedium > z3MASlow && c3MAMedium > c3MASlow // ; // bool isX3MaBearishState = // z3MAFast < z3MAMedium && c3MAFast < c3MAMedium && z3MAMedium < z3MASlow && c3MAMedium < c3MASlow // ; // bool isX3MaValidForBullishRejection = // c3MASlowState > 0 && z3MASlowState > 0 && z3MAMediumState > 0 && c3MAMediumState > 0 && z3MAMedium > z3MASlow && c3MAMedium > c3MASlow && conditions.isVidyaBullish // ; // bool isX3MaValidForBearishRejection = // c3MASlowState < 0 && z3MASlowState < 0 && z3MAMediumState < 0 && c3MAMediumState < 0 && z3MAMedium < z3MASlow && c3MAMedium < c3MASlow && conditions.isVidyaBearish // ; // // Parsing Pivots ... XBoxZone upperPivot; XBoxZone lowerPivot; double providedSL = 0; XBoxZone rejectedPivot; XBoxZone insidePivots[]; int insidePivotsCount = 0; XBoxZone fakeBreakedPivot; bool isRejectedOnMid = false; bool hasInsidePivots = false; bool hasPivots = HasChild(pivots); if (hasPivots) { // // Select Inside Boxes ... ENUM_XCA_PIVOTS allowedInsidePivots[] = { XCA_FVG_BULL, XCA_FVG_BEAR, }; insidePivotsCount = SelectInsideBoxes( allowedInsidePivots, insidePivots, pivots, zBar, cBar, pBar, p2Bar // ); Clean(allowedInsidePivots); hasInsidePivots = IsValidSize(insidePivotsCount); // // Detect Rejected Pivot ... ENUM_XCA_PIVOTS allowedRejectedPivots[] = { XCA_FVG_BULL, XCA_FVG_BEAR, }; has = SelectRejectedBox( allowedRejectedPivots, rejectedPivot, isRejectedOnMid, pivots, zBar, cBar, pBar, p2Bar, false, // Ignore Mid Rejection ... true, true // ); Clean(allowedRejectedPivots); // // Select Fake Breakout Box ... ENUM_XCA_PIVOTS allowedFakeBreakedPivots[] = { XCA_PEAK, XCA_VALE, }; has = SelectFakeBreakedBox( allowedFakeBreakedPivots, fakeBreakedPivot, pivots, helper, zBar, cBar, pBar, p2Bar // ); Clean(allowedFakeBreakedPivots); // // Select Boundary Boxes ... ENUM_XCA_PIVOTS allowedBoundarydPivots[] = { XCA_PEAK, XCA_VALE, }; has = SelectBoundaryBoxes( allowedBoundarydPivots, upperPivot, lowerPivot, pivots, helper, zBar, cBar, pBar, p2Bar // ); Clean(allowedBoundarydPivots); } // // Signaller Summarization ... // // Cond1 Act Using FVG Rejections ... // bool isCond1Bullish = // false && // TODO: Remove this ... isRSIBullish && isVolumeOverAvg && isVolumeOverLast && conditions.isSarBullish && rejectedPivot.IsValid() && rejectedPivot.IsBullish() && isX3MaValidForBullishRejection // ; // bool isCond1Bearish = // false && // TODO: Remove this ... isRSIBearish && isVolumeOverAvg && isVolumeOverLast && conditions.isSarBearish && rejectedPivot.IsValid() && rejectedPivot.IsBearish() && isX3MaValidForBearishRejection // ; // bool isCond1 = isCond1Bullish || isCond1Bearish; if (isCond1) { pivotBox = rejectedPivot; } // // Cond2 Act Using OSC Box and Vydia ... // bool isCond2Bullish = // upperPivot.IsValid() && lowerPivot.IsValid() && fakeBreakedPivot.IsValid() && fakeBreakedPivot.IsBullish() // ; // bool isCond2Bearish = // upperPivot.IsValid() && lowerPivot.IsValid() && fakeBreakedPivot.IsValid() && fakeBreakedPivot.IsBearish() // ; // bool isCond2 = isCond2Bullish || isCond2Bearish; if (isCond2) { Print("Cond2 ..."); } // // Cond3 Act Using CCi Peaks and Vales ... // bool isCond3Bullish = // false // ; // bool isCond3Bearish = // false // ; // bool isCond3 = isCond3Bullish || isCond3Bearish; if (isCond3) { } // // 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 sls[]; // // Preparing SLs ... // // For Cond 1 ... // For Cond 2 ... if (isCond1 || isCond2) { // if (isCond1Bullish) { // // Rejected Pivot ... Add( rejectedPivot.lower, sls // ); // if (!isRejectedOnMid) { // Add( rejectedPivot.GetMid(), sls // ); } } else { // // Rejected Pivot ... Add( rejectedPivot.upper, sls // ); // if (!isRejectedOnMid) { // Add( rejectedPivot.GetMid(), sls // ); } } // providedSL = isCond1Bullish ? GetMax(sls) : GetMin(sls); // } // double risk = MathAbs(providedSL - entry); double riskPoint = risk / points; // 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"; // // Preparing Targets ... if (isCond1 || isCond2) { // // Add Reward 1 ... // double rewardPrice = 1 * risk; double rewardTP = isBullish ? entry + rewardPrice : entry - rewardPrice; // Add( rewardTP, targets // ); } // Clean(sls); } // 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(); upperPivot.Clean(); lowerPivot.Clean(); Clean(cTrendValues); Clean(pTrendValues); Clean(insidePivots); pConditions.Clean(); rejectedPivot.Clean(); fakeBreakedPivot.Clean(); // return result; } // // Select Inside Boxes ... int SelectInsideBoxes( ENUM_XCA_PIVOTS &allowedTypes[], 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]; // ENUM_XCA_PIVOTS iType = GetPivotType(iBox); bool isAllowedType = IsValid(iType) && !HasChild(allowedTypes) ? true : Contains( iType, allowedTypes // ); if (!isAllowedType) { // 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( ENUM_XCA_PIVOTS &allowedTypes[], XBoxZone &box, bool &rejectOnMid, XBoxZone &boxes[], XOHCL &zBar, XOHCL &cBar, XOHCL &pBar, XOHCL &p2Bar, bool ignoreMidRejection = true, bool forceBarType = false, bool forcePressure = false // ) { // bool result = false; // box.Clean(); rejectOnMid = false; // // 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]; // ENUM_XCA_PIVOTS iType = GetPivotType(iBox); bool isAllowedType = IsValid(iType) && !HasChild(allowedTypes) ? true : Contains( iType, allowedTypes // ); if (!isAllowedType) { // iBox.Clean(); // continue; } // bool isBullish = iBox.IsBullish(); bool isBearish = iBox.IsBearish(); // double boundaryPrice = iBox.GetRejection(); // double midPrice = iBox.GetMid(); // 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 // ); // if (ignoreMidRejection) { // isMidBullishRejected = false; isMidBearishRejected = false; } // bool isBullishRejected = isBullish && (isMidBullishRejected || isBoundaryBullishRejected); // bool isBearishRejected = isBearish && (isMidBearishRejected || isBoundaryBearishRejected); // bool isRejected = isBullishRejected || isBearishRejected; if (isRejected) { // box = iBox; rejectOnMid = isBullishRejected ? isMidBullishRejected : isMidBearishRejected; break; } // iBox.Clean(); } // result = box.IsValid(); // return result; } // bool SelectFakeBreakedBox( ENUM_XCA_PIVOTS &allowedTypes[], XBoxZone &box, XBoxZone &boxes[], XCXCAEAHelper *helper, XOHCL &zBar, XOHCL &cBar, XOHCL &pBar, XOHCL &p2Bar // ) { // bool result = false; // box.Clean(); // // Validate ... result = zBar.IsValid() && cBar.IsValid() && pBar.IsValid() && p2Bar.IsValid() && HasChild(boxes); if (!result) { return result; } // XBoxZone tmp[]; Copy( boxes, tmp // ); // int idx = -1; XBoxZone iBox; while (HasChild(tmp)) { // idx = GetYoungest(tmp); result = IsValidIndex(idx); if (!result) { break; } // iBox = tmp[idx]; ArrayRemove( tmp, idx, 1 // ); // // Checking Box Type Allowed ... ENUM_XCA_PIVOTS iType = GetPivotType(iBox); result = IsValid(iType) && (!HasChild(allowedTypes) ? true : Contains( iType, allowedTypes // )); if (!result) { // iBox.Clean(); continue; } // // Check Box Fake Breakeout ... result = IsFakeBreakeout( iBox, helper, cBar.Index() // ); if (result) { // box = iBox; break; } // iBox.Clean(); } // Clean(tmp); iBox.Clean(); // result = box.IsValid(); // return result; } // bool SelectBoundaryBoxes( ENUM_XCA_PIVOTS &allowedTypes[], XBoxZone &upperBox, XBoxZone &lowerBox, XBoxZone &boxes[], XCXCAEAHelper *helper, XOHCL &zBar, XOHCL &cBar, XOHCL &pBar, XOHCL &p2Bar // ) { // bool result = false; // upperBox.Clean(); lowerBox.Clean(); // // Validate ... result = zBar.IsValid() && cBar.IsValid() && pBar.IsValid() && p2Bar.IsValid() && HasChild(boxes); if (!result) { return result; } // XBoxZone tmp[]; Copy( boxes, tmp // ); // int idx = -1; XBoxZone iBox; while (HasChild(tmp)) { // idx = GetYoungest(tmp); result = IsValidIndex(idx); if (!result) { break; } // iBox = tmp[idx]; ArrayRemove( tmp, idx, 1 // ); // // Checking Box Type Allowed ... ENUM_XCA_PIVOTS iType = GetPivotType(iBox); result = IsValid(iType) && (!HasChild(allowedTypes) ? true : Contains( iType, allowedTypes // )); if (!result) { // iBox.Clean(); continue; } // // Upper ... bool canSetUpper = iType == XCA_PEAK && (!upperBox.IsValid() ? true : upperBox.lower > iBox.lower); if (canSetUpper) { upperBox = iBox; } // // Lower ... bool canSetLower = iType == XCA_VALE && (!lowerBox.IsValid() ? true : lowerBox.upper < iBox.upper); if (canSetLower) { lowerBox = iBox; } // iBox.Clean(); } // Clean(tmp); iBox.Clean(); // result = upperBox.IsValid() && lowerBox.IsValid(); // return result; } // int ExtractValues( double &values[], XBoxZone &pivots[], bool forceClean = true // ) { // int result = 0; // if (forceClean) { Clean(values); } // int count = ArraySize(pivots); for (int i = 0; i < count; i++) { // XBoxZone iPivot = pivots[i]; // Add( iPivot.upper, values // ); // Add( iPivot.lower, values // ); // iPivot.Clean(); } // result = ArraySize(values); // return result; } // double GetMax(XBoxZone &pivots[]) { // double values[]; ExtractValues( values, pivots // ); // double result = GetMax(values); // Clean(values); // return result; } // double GetMin(XBoxZone &pivots[]) { // double values[]; ExtractValues( values, pivots // ); // double result = GetMin(values); // Clean(values); // return result; } //