From 41fb71d63d6da82f3b3e450c3a96f28acd654a89 Mon Sep 17 00:00:00 2001 From: Hadi Khazaee Asl Date: Fri, 9 Jan 2026 22:41:21 +0330 Subject: [PATCH] last ... --- Documents/BKP/X121XKI/tmp.poi.mq5 | 3378 +++++++++++++++++ Documents/BKP/X121XKI/tmps.bkp.mq5 | 945 +++++ .../x-saherelm.x121.xki.parser.class.mq5 | 446 +-- ...saherelm.x121.xki.x-poi.detector.class.mq5 | 4 +- 4 files changed, 4346 insertions(+), 427 deletions(-) diff --git a/Documents/BKP/X121XKI/tmp.poi.mq5 b/Documents/BKP/X121XKI/tmp.poi.mq5 index d73516d2..0b002a22 100644 --- a/Documents/BKP/X121XKI/tmp.poi.mq5 +++ b/Documents/BKP/X121XKI/tmp.poi.mq5 @@ -1724,3 +1724,3381 @@ void CountTouches( } } // #endregion + +// #region POI(s) ... + +// #region Zone Detectors ... +int DetectSupports( + XBoxZone &zones[], + int barIndex, + int loopback = 50, + bool forceValidation = true, + int validationLength = 7, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + XClean(zones); + + // + // Normalize ... + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + + // + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + + // + if (loopback < 2) + { + loopback = 2; + } + + // + if (validationLength < 2) + { + validationLength = 2; + } + + // + // Preparing Loops ... + XOHCL tmpBar; + bool has = false; + double upper = 0; + double lower = 0; + XBoxZone tmpZone; + string type = NULL; + double tmpValue = 0; + datetime from = NULL; + int start = barIndex; + int end = barIndex + loopback; + datetime to = GetBarTime(forSymbol, forPeriod, barIndex); + for (int i = start; i < end; i++) + { + // + // Initialize Bar ... + if (tmpBar.Init(forSymbol, forPeriod, i)) + { + // + // Check Has Shadow ... + has = tmpBar.GetHighShadow() > 0 || + tmpBar.GetLowShadow() > 0; + if (has) + { + // + // Check Support or Resistance ... + + // + // Support ... + tmpValue = tmpBar.FindLowest(validationLength, MODE_LOW); + has = NotEmptyZero(tmpValue) && + tmpValue == tmpBar.low; + + // + if (has) + { + // + tmpZone.Clean(); + lower = tmpValue; + from = tmpBar.time; + upper = tmpBar.GetDown(); + type = ToXString(X_BAR_PATTERN_SUPPORT); + has = tmpZone.Init( + forSymbol, + forPeriod, + upper, + lower, + from, + to, + X_DIRECTION_BULLISH, + type // + ); + if (has) + { + // + AddRef( + tmpZone, + zones // + ); + + // + tmpZone.Clean(); + } + } + } + + // + tmpBar.Clean(); + } + } + + // + // Validate ... + if (HasChild(zones) && forceValidation) + { + // + ValidateZones( + zones, + barIndex // + ); + } + + // + result = ArraySize(zones); + + // + return result; +} + +int DetectResistances( + XBoxZone &zones[], + int barIndex, + int loopback = 50, + bool forceValidation = true, + int validationLength = 7, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + XClean(zones); + + // + // Normalize ... + + // + if (barIndex < 0) + { + barIndex = 0; + } + + // + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + + // + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + + // + if (loopback < 2) + { + loopback = 2; + } + + // + if (validationLength < 2) + { + validationLength = 2; + } + + // + // Preparing Loops ... + XOHCL tmpBar; + bool has = false; + double upper = 0; + double lower = 0; + XBoxZone tmpZone; + string type = NULL; + double tmpValue = 0; + datetime from = NULL; + int start = barIndex; + int end = barIndex + loopback; + datetime to = GetBarTime(forSymbol, forPeriod, barIndex); + for (int i = start; i < end; i++) + { + // + // Initialize Bar ... + if (tmpBar.Init(forSymbol, forPeriod, i)) + { + // + // Check Has Shadow ... + has = tmpBar.GetHighShadow() > 0 || + tmpBar.GetLowShadow() > 0; + if (has) + { + // + // Check Support or Resistance ... + + // + // Resistance ... + tmpValue = tmpBar.FindHighest(validationLength, MODE_HIGH); + has = NotEmptyZero(tmpValue) && + tmpValue == tmpBar.high; + if (has) + { + // + tmpZone.Clean(); + upper = tmpValue; + from = tmpBar.time; + lower = tmpBar.GetUp(); + type = ToXString(X_BAR_PATTERN_RESISTANCE); + has = tmpZone.Init( + forSymbol, + forPeriod, + upper, + lower, + from, + to, + X_DIRECTION_BEARISH, + type // + ); + if (has) + { + // + AddRef( + tmpZone, + zones // + ); + + // + tmpZone.Clean(); + } + } + } + + // + tmpBar.Clean(); + } + } + + // + // Validate ... + if (HasChild(zones) && forceValidation) + { + // + ValidateZones( + zones, + barIndex // + ); + } + + // + result = ArraySize(zones); + + // + return result; +} + +void ValidateZones( + XBoxZone &zones[], + int barIndex = 0, + ENUM_X_BOUNDARY_PRICE forPriceType = X_BOUNDARY_PRICE_UP_DOWN // +) +{ + // + bool has = false; + + // + // Validation ... + has = HasChild(zones) && + IsXValid(forPriceType); + if (!has) + { + return; + } + + // + // Normalizetion ... + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL tmpBar; + XBoxZone tmp; + XBoxZone tmps[]; + double tmpValue = 0; + for (int i = 0; i < ArraySize(zones); i++) + { + // + tmp = zones[i]; + + // + // Validate Zone ... + has = false; + for (int j = barIndex; j < tmp.FromIndex(); j++) + { + // + // Initial Bar ... + if (tmpBar.Init(tmp.symbol, tmp.period, j)) + { + // + tmpValue = forPriceType == X_BOUNDARY_PRICE_UP_DOWN + ? tmp.IsBullish() + ? tmpBar.GetDown() + : tmpBar.GetUp() + : forPriceType == X_BOUNDARY_PRICE_HIGH_LOW + ? tmp.IsBullish() + ? tmpBar.low + : tmpBar.high + : EMPTY_VALUE; + if (NotEmptyZero(tmpValue)) + { + // + // Check Break ... + has = tmp.IsBullish() + ? tmpValue < tmp.lower + : tmpValue > tmp.upper; + + // + // If Breakes ... + if (has) + { + break; + } + } + + // + tmpBar.Clean(); + } + } + + // + // Not Breaked ... + if (!has) + { + // + AddIfNotExists( + tmp, + tmps // + ); + } + + // + tmp.Clean(); + } + + // + // Update Zones ... + XClean(zones); + Copy( + tmps, + zones // + ); + XClean(tmps); +} + +void GetCurrentStructure( + XBoxZone &supports[], + XBoxZone &resistances[], + XBoxZone &minorSupport, + XBoxZone &majorSupport, + XBoxZone &minorResistance, + XBoxZone &majorResistance, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forMinorPeriod = NULL, + ENUM_TIMEFRAMES forMajorPeriod = NULL, + int loopback = 50, + int minorValidation = 7, + int majorValidation = 14 // +) +{ + // + bool has = false; + + // + XClean(supports); + XClean(resistances); + minorSupport.Clean(); + majorSupport.Clean(); + minorResistance.Clean(); + majorResistance.Clean(); + + // + // Normalize ... + barIndex = kiParser.NormalizeBarIndex(barIndex); + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forMinorPeriod)) + { + forMinorPeriod = period; + } + if (!IsXValid(forMajorPeriod)) + { + forMajorPeriod = period; + } + + // + int tmpIDX = -1; + int supportsCount = 0; + XBoxZone tmpSupports[]; + int resistancesCount = 0; + XBoxZone tmpResistances[]; + + // + // Detect Minors ... + + // + supportsCount = DetectSupports( + tmpSupports, + barIndex, + loopback, + true, // Force Validation ... + minorValidation, + forSymbol, + forMinorPeriod // + ); + if (IsValidSize(supportsCount)) + { + // + FillNotExists( + supports, + tmpSupports // + ); + + // + tmpIDX = GetYoungest(tmpSupports); + if (IsValidIndex(tmpIDX)) + { + minorSupport = tmpSupports[tmpIDX]; + } + } + + // + resistancesCount = DetectResistances( + tmpResistances, + barIndex, + loopback, + true, // Force Validation ... + minorValidation, + forSymbol, + forMinorPeriod // + ); + if (IsValidSize(resistancesCount)) + { + // + FillNotExists( + resistances, + tmpResistances // + ); + + // + tmpIDX = GetYoungest(tmpResistances); + if (IsValidIndex(tmpIDX)) + { + minorResistance = tmpResistances[tmpIDX]; + } + } + + // + XClean(tmpSupports); + XClean(tmpResistances); + + // + // Detect Majors ... + + // + supportsCount = DetectSupports( + tmpSupports, + barIndex, + loopback, + true, // Force Validation ... + majorValidation, + forSymbol, + forMajorPeriod // + ); + if (IsValidSize(supportsCount)) + { + // + UpdateToTime(tmpSupports); + + // + FillNotExists( + supports, + tmpSupports // + ); + + // + tmpIDX = GetLowest(tmpSupports); + if (IsValidIndex(tmpIDX)) + { + majorSupport = tmpSupports[tmpIDX]; + } + } + + // + resistancesCount = DetectResistances( + tmpResistances, + barIndex, + loopback, + true, // Force Validation ... + majorValidation, + forSymbol, + forMajorPeriod // + ); + if (IsValidSize(resistancesCount)) + { + // + UpdateToTime(tmpResistances); + + // + FillNotExists( + resistances, + tmpResistances // + ); + + // + tmpIDX = GetHighest(tmpResistances); + if (IsValidIndex(tmpIDX)) + { + majorResistance = tmpResistances[tmpIDX]; + } + } + + // + XClean(tmpSupports); + XClean(tmpResistances); +} + +bool HasStructure( + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forMinorPeriod = NULL, + ENUM_TIMEFRAMES forMajorPeriod = NULL, + int loopback = 50, + int minorValidation = 7, + int majorValidation = 14 // +) +{ + // + XBoxZone supports[]; + XBoxZone resistances[]; + XBoxZone minorSupport; + XBoxZone majorSupport; + XBoxZone minorResistance; + XBoxZone majorResistance; + + // + GetCurrentStructure( + supports, + resistances, + minorSupport, + majorSupport, + minorResistance, + majorResistance, + barIndex, + forSymbol, + forMinorPeriod, + forMajorPeriod, + loopback, + minorValidation, + majorValidation // + ); + + // + bool result = + majorSupport.IsValid() && + majorResistance.IsValid(); + + // + XClean(supports); + XClean(resistances); + minorSupport.Clean(); + majorSupport.Clean(); + minorResistance.Clean(); + majorResistance.Clean(); + + // + return result; +} + +void RefineStructure( + XBoxZone &supports[], + XBoxZone &resistances[], + XBoxZone &minorSupport, + XBoxZone &majorSupport, + XBoxZone &minorResistance, + XBoxZone &majorResistance, + int loopback = 500, + double breakThreshold = 5, + ENUM_X_PRICE breakBy = X_PRICE_CLOSE // +) +{ + // + // Support ... + if (HasChild(supports)) + { + // + for (int i = 0; i < ArraySize(supports); i++) + { + // + RefineZone( + supports[i], + loopback, + breakThreshold, + breakBy // + ); + } + } + + // + // Resistance ... + if (HasChild(resistances)) + { + // + for (int i = 0; i < ArraySize(resistances); i++) + { + // + RefineZone( + resistances[i], + loopback, + breakThreshold, + breakBy // + ); + } + } + + // + RefineZone( + minorSupport, + loopback, + breakThreshold, + breakBy // + ); + + // + RefineZone( + majorSupport, + loopback, + breakThreshold, + breakBy // + ); + + // + RefineZone( + minorResistance, + loopback, + breakThreshold, + breakBy // + ); + + // + RefineZone( + majorResistance, + loopback, + breakThreshold, + breakBy // + ); +} + +void RefineZone( + XBoxZone &zone, + int loopback = 500, + double breakThreshold = 5, + ENUM_X_PRICE breakBy = X_PRICE_CLOSE // +) +{ + // + bool has = + zone.IsValid() && + IsXValid(breakBy); + if (!has) + { + return; + } + + // + // Normalize ... + loopback = NormalizeInt(loopback, 1); + breakThreshold = NormalizeDouble(breakThreshold, 0, 50); + + // + XOHCL iBar; + int start = zone.FromIndex(); + int end = start + loopback; + double point = GetPoints(zone.symbol); + double breakDistance = point * breakThreshold; + for (int i = start; i < end; i++) + { + // + has = iBar.Init(zone.symbol, zone.period, i); + if (has) + { + // + // Check Rejections ... + has = zone.IsBullish() + ? iBar.low < zone.upper && + iBar.GetDown() > zone.upper + : iBar.high > zone.upper && + iBar.GetUp() < zone.upper; + if (has) + { + // + Add( + iBar.time, + zone.tests // + ); + } + + // + // Check Break ... + double bPrice = iBar.GetPrice(breakBy); + has = + zone.IsBullish() + ? bPrice < zone.lower - breakDistance + : bPrice > zone.upper + breakDistance; + if (has) + { + // + zone.breakAt = iBar.time; + break; + } + } + + // + iBar.Clean(); + } + + // + has = IsXValid(zone.breakAt); + if (has) + { + // + zone.at = zone.from; + zone.from = zone.breakAt; + } +} + +bool DetectRecentSwings( + XBoxZone &swingHigh, + XBoxZone &swingLow, + int barIndex = 0, + int swingsValidationLength = 50, + int loopback = 500, + ENUM_TIMEFRAMES forPeriod = NULL, + bool forceRefineZones = true // +) +{ + // + swingLow.Clean(); + swingHigh.Clean(); + + // + loopback = NormalizeInt(loopback, 5); + barIndex = kiParser.NormalizeBarIndex(barIndex); + swingsValidationLength = NormalizeInt(swingsValidationLength, 5); + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + + // + XOHCL iBar; + int iIDX = -1; + double low = 0; + double high = 0; + int lowIDX = -1; + int highIDX = -1; + bool has = false; + double iValue = 0; + datetime lowAt = NULL; + datetime highAt = NULL; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + has = iBar.Init(symbol, forPeriod, i); + if (!has) + { + continue; + } + + // + iIDX = iBar.FindLowestIndex(swingsValidationLength, MODE_LOW); + has = IsValidIndex(iIDX); + if (has) + { + // + iValue = iLow(iBar.symbol, iBar.period, iIDX); + + // + // Check Can Set Low ... + has = (!NotEmptyZero(low) || + (NotEmptyZero(low) && iValue < low)) && + IsValidSwing( + iValue, + iIDX, + barIndex, + iBar.symbol, + iBar.period, + X_SWING_LOW // + ); + if (has) + { + // + low = iValue; + lowIDX = iIDX; + lowAt = iBar.time; + } + } + + // + iIDX = iBar.FindHighestIndex(swingsValidationLength, MODE_HIGH); + has = IsValidIndex(iIDX); + if (has) + { + // + iValue = iHigh(iBar.symbol, iBar.period, iIDX); + + // + // Check Can Set High ... + has = (!NotEmptyZero(high) || + (NotEmptyZero(high) && iValue > high)) && + IsValidSwing( + iValue, + iIDX, + barIndex, + iBar.symbol, + iBar.period, + X_SWING_HIGH // + ); + if (has) + { + // + high = iValue; + highIDX = iIDX; + highAt = iBar.time; + } + } + + // + iBar.Clean(); + } + + // + // Recent Low Swing ... + has = + IsXValid(lowAt) && + NotEmptyZero(low) && + IsValidIndex(lowIDX); + if (has) + { + // + has = iBar.Init(symbol, forPeriod, lowIDX); + has = has && + swingLow.Init( + iBar.symbol, + iBar.period, + iBar.GetDown(), + low, + GetBarTime(iBar.symbol, iBar.period, lowIDX + swingsValidationLength - 1), + GetBarTime(iBar.symbol, iBar.period, barIndex), + X_DIRECTION_BULLISH, + ToXString(X_BAR_PATTERN_LOW), + lowAt // + ); + if (has && forceRefineZones) + { + RefineZone(swingLow, 500, 5, X_PRICE_CLOSE); + } + } + + // + // Recent High Swing ... + has = + IsXValid(highAt) && + NotEmptyZero(high) && + IsValidIndex(highIDX); + if (has) + { + // + has = iBar.Init(symbol, forPeriod, highIDX); + has = has && + swingHigh.Init( + iBar.symbol, + iBar.period, + high, + iBar.GetUp(), + GetBarTime(iBar.symbol, iBar.period, lowIDX + swingsValidationLength - 1), + GetBarTime(iBar.symbol, iBar.period, barIndex), + X_DIRECTION_BEARISH, + ToXString(X_BAR_PATTERN_HIGH), + highAt // + ); + if (has && forceRefineZones) + { + RefineZone(swingHigh, 500, 5, X_PRICE_CLOSE); + } + } + + // + bool result = swingLow.IsValid() && + swingHigh.IsValid(); + + // + return result; +} + +bool HasOrderFlow( + XBoxZone &flow[], + int barIndex = 0, + int flowValidationLength = 5, + ENUM_X_DIRECTION flowDir = X_DIRECTION_NONE, + int loopback = 50, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL, + ENUM_X_BOUNDARY_PRICE priceType = X_BOUNDARY_PRICE_HIGH_LOW // +) +{ + // + bool result = false; + + // + XClean(flow); + + // + // Validate ... + result = + IsXValid(priceType); + if (!result) + { + return result; + } + + // + // Normalizing Data ... + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + loopback = NormalizeInt(loopback, 5); + barIndex = kiParser.NormalizeBarIndex(barIndex); + flowValidationLength = NormalizeInt(flowValidationLength, 2); + + // + // Handle Works ... + + // + XOHCL iBar; + int iIndex = -1; + bool has = false; + XBoxZone tmpZone; + double iPrice = 0; + ENUM_X_PRICE iPriceType; + bool isBullish = !HasDirection(flowDir) || IsXBullish(flowDir); + bool isBearish = !HasDirection(flowDir) || IsXBearish(flowDir); + + // + // Looping Reversal ... + int start = barIndex + loopback; + int end = barIndex; + for (int i = start; i > end; i--) + { + // + has = iBar.Init(forSymbol, forPeriod, i); + if (!has) + { + continue; + } + + // + // Check iBar is Low Swing ... + if (isBullish) + { + // + iPriceType = priceType == X_BOUNDARY_PRICE_HIGH_LOW + ? X_PRICE_LOW + : X_PRICE_DOWN; + iPrice = iBar.GetPrice(iPriceType); + has = iPrice == iBar.FindLowest(iIndex, flowValidationLength, iPriceType); + has = has && + IsValidSwing( + iPrice, + iBar.Index(), + barIndex, + iBar.symbol, + iBar.period, + X_SWING_LOW // + ); + if (has) + { + // + // Flow Detected ... + tmpZone.Clean(); + iPriceType = priceType == X_BOUNDARY_PRICE_HIGH_LOW + ? X_PRICE_DOWN + : X_PRICE_UP; + has = tmpZone.Init( + iBar.symbol, + iBar.period, + iBar.GetPrice(iPriceType), + iPrice, + iBar.time, + GetBarTime(iBar.symbol, iBar.period, barIndex), + X_DIRECTION_BULLISH, + ToXString(X_BAR_PATTERN_LOW) // + ); + if (has) + { + // + AddIfNotExists( + tmpZone, + flow // + ); + + // + tmpZone.Clean(); + } + } + } + + // + // Check iBar is High Swing ... + if (isBearish) + { + // + iPriceType = priceType == X_BOUNDARY_PRICE_HIGH_LOW + ? X_PRICE_HIGH + : X_PRICE_UP; + iPrice = iBar.GetPrice(iPriceType); + has = iPrice == iBar.FindHighest(iIndex, flowValidationLength, iPriceType); + has = has && + IsValidSwing( + iPrice, + iBar.Index(), + barIndex, + iBar.symbol, + iBar.period, + X_SWING_HIGH // + ); + if (has) + { + // + // Flow Detected ... + tmpZone.Clean(); + iPriceType = priceType == X_BOUNDARY_PRICE_HIGH_LOW + ? X_PRICE_UP + : X_PRICE_DOWN; + has = tmpZone.Init( + iBar.symbol, + iBar.period, + iPrice, + iBar.GetPrice(iPriceType), + iBar.time, + GetBarTime(iBar.symbol, iBar.period, barIndex), + X_DIRECTION_BEARISH, + ToXString(X_BAR_PATTERN_HIGH) // + ); + if (has) + { + // + AddIfNotExists( + tmpZone, + flow // + ); + + // + tmpZone.Clean(); + } + } + } + + // + iBar.Clean(); + tmpZone.Clean(); + } + + // + result = HasChild(flow); + if (result) + { + Sort(flow); + } + + // + return result; +} + +bool IsValidSwing( + double price, + int swingIDX, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL, + ENUM_X_SWING_TYPE swingType = X_SWING_NONE // +) +{ + // + bool result = false; + + // + result = + NotEmptyZero(price) && + IsXValid(swingType) && + IsValidIndex(swingIDX) && + swingIDX >= barIndex; + if (!result) + { + return result; + } + + // + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL iBar; + bool has = false; + for (int i = barIndex; i <= (swingIDX - barIndex); i++) + { + // + has = iBar.Init(forSymbol, forPeriod, i); + if (!has) + { + continue; + } + + // + // Check Price Break ... + has = + (swingType == X_SWING_LOW && + iBar.low < price) || + (swingType == X_SWING_HIGH && + iBar.high > price); + if (has) + { + break; + } + + // + iBar.Clean(); + } + + // + result = !has && !iBar.IsValid(); + + // + iBar.Clean(); + + // + return result; +} +// #endregion + +// #region Hasers ... +bool HasVolatilitySwitchedHigh( + int barIndex = 0, + int loopback = 3 // +) +{ + // + bool result = false; + + // + barIndex = kiParser.NormalizeBarIndex(barIndex); + loopback = NormalizeInt(loopback, 1); + + // + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + result = kiParser.IsVolatilitySwitchdToHigh(i); + if (result) + { + break; + } + } + + // + return result; +} +// #endregion + +// #region Bar Patterns ... +void FillStrategy1Patterns( + ENUM_X_BAR_PATTERN &patterns[], + ENUM_X_DIRECTION &dirs[], + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + XClean(dirs); + XClean(patterns); + + // + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + + // + GetAllBarPatters(patterns, dirs); + + // + // Add(X_BAR_PATTERN_FVG, patterns); + // Add(forDir, dirs); +} + +void RefactorStrategy1OperationalZone(XBoxZone &zone) +{ + + // + if (!zone.IsValid()) + { + return; + } + + // + // Refine Zone ... + RefineZone(zone); + + // + // SL Refactoring ... + + // + XOHCL toBar; + if (zone.ToBar(toBar)) + { + // + int to = zone.ToIndex(); + int from = zone.FromIndex(); + int length = from - to; + double iValue = + zone.IsBullish() + ? toBar.FindLowest(length, MODE_LOW) + : zone.IsBearish() + ? toBar.FindHighest(length, MODE_HIGH) + : EMPTY_VALUE; + if (NotEmptyZero(iValue)) + { + // + if (zone.IsBullish()) + { + zone.lower = MathMin(zone.lower, iValue); + } + + // + if (zone.IsBearish()) + { + zone.upper = MathMax(zone.upper, iValue); + } + } + } + toBar.Clean(); +} + +/* + * Check Recently Pattern Zone is Rejected or not ... + * + * @param zone: XBoxZone, Touched Zone ... + * @param patterns: ENUM_X_BAR_PATTERN, Allowed to Check Patterns ... + * @param patternsDir: ENUM_X_DIRECTION, Allowed Directions ... + * @param price: double, a Price to Check Toch or Reject ... + * @param barIndex: int, Bar Index to Start Checking ... + * @param loopback: int, Loopback for Pattern Formations ... + * @param forPeriod: ENUM_TIMEFRAMES, Time Frame to Check Patterns ... + * @param forDir: ENUM_X_DIRECTION, Directions for Pattern's Formation Check ... + * + * @return ( bool ) + */ +bool HasRecentPatternRejected( + XBoxZone &zone, + ENUM_X_BAR_PATTERN &patterns[], + ENUM_X_DIRECTION &patternsDir[], + int barIndex = 0, + int loopback = 5, + ENUM_TIMEFRAMES forPeriod = NULL, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + bool result = false; + + // + zone.Clean(); + + // + // Validate ... + result = + HasChild(patterns) && + HasChild(patternsDir) && + ArraySize(patterns) == ArraySize(patternsDir); + if (!result) + { + return result; + } + + // + // Normalize ... + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + if (IsXValid(forPeriod)) + { + forPeriod = period; + } + + // + XOHCL bar; + result = bar.Init(symbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + XOHCL iBar; + bool has = false; + int iBullishIDX = -1; + int iBearishIDX = -1; + bool isBullish = false; + bool isBearish = false; + XBoxZone iBullishZones[]; + XBoxZone iBearishZones[]; + XPatternAnalysis iAnalysis; + XPatternAnalysisConfig iConfig; + + // + // Preparing Pattern Analysis Config ... + iConfig.Default(); + + // + Copy( + patterns, + iConfig.allowedPatterns // + ); + Copy( + patternsDir, + iConfig.allowedDirs // + ); + + // + // Looping Back ... + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Initialize Bar ... + has = iBar.Init(symbol, forPeriod, i); + if (!has) + { + continue; + } + + // + // Analyse Patterns ... + has = AnalyseBarPatterns(iBar, iAnalysis, iConfig); + if (!has) + { + // + iBar.Clean(); + continue; + } + + // + // Bullish ... + has = iAnalysis.Count(X_DIRECTION_BULLISH) > 0; + if (has) + { + // + iAnalysis.GetPatterns(iBullishZones, X_DIRECTION_BULLISH); + isBullish = + HasChild(iBullishZones) && + HasRejected(iBullishIDX, bar, iBullishZones); + } + + // + // Bearish ... + has = iAnalysis.Count(X_DIRECTION_BEARISH) > 0; + if (has) + { + // + iAnalysis.GetPatterns(iBearishZones, X_DIRECTION_BEARISH); + isBearish = + HasChild(iBearishZones) && + HasRejected(iBearishIDX, bar, iBearishZones); + } + + // + // Summarizing Result ... + has = + HasDirection(forDir) + ? (isBullish && !isBearish && IsXBullish(forDir)) || + (isBearish && !isBullish && IsXBearish(forDir)) + : (isBullish && !isBearish) || (isBearish && !isBullish); + if (has) + { + // + // Fill Zones ... + if (isBullish) + { + zone = iBullishZones[iBullishIDX]; + } + else + { + zone = iBearishZones[iBearishIDX]; + } + break; + } + + // + // Cleanup Resource ... + iBar.Clean(); + iAnalysis.Clean(); + XClean(iBullishZones); + XClean(iBearishZones); + } + + // + // Cleanup Resources ... + bar.Clean(); + iBar.Clean(); + iConfig.Clean(); + iAnalysis.Clean(); + XClean(iBullishZones); + XClean(iBearishZones); + + // + result = zone.IsValid(); + + // + return result; +} +// #endregion + +// #region Switches ... +int HasKIFastSwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsKIFastSwitchedToBullish(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_FAST), + GetBarTime(symbol, period, i), + kiHelper.GetKIFast(i), + kiHelper.GetKIFast(i + 1), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsKIFastSwitchedToBearish(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_FAST), + GetBarTime(symbol, period, i), + kiHelper.GetKIFast(i), + kiHelper.GetKIFast(i + 1), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} + +int HasKISlowSwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsKISlowSwitchedToBullish(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_SLOW), + GetBarTime(symbol, period, i), + kiHelper.GetKISlow(i), + kiHelper.GetKISlow(i + 1), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsKISlowSwitchedToBearish(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_SLOW), + GetBarTime(symbol, period, i), + kiHelper.GetKIFast(i), + kiHelper.GetKIFast(i + 1), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} + +int HasKISuperSlowSwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsKISuperSlowSwitchedToBullish(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_SUPER_SLOW), + GetBarTime(symbol, period, i), + kiHelper.GetKISuperSlow(i), + kiHelper.GetKISuperSlow(i + 1), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsKISuperSlowSwitchedToBearish(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_SUPER_SLOW), + GetBarTime(symbol, period, i), + kiHelper.GetKIFast(i), + kiHelper.GetKIFast(i + 1), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} + +int HasKIWaveSwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsKIWaveSwitchedToBullish(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_WAVE), + GetBarTime(symbol, period, i), + kiHelper.GetKIWave(i), + kiHelper.GetKIWave(i + 1), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsKIWaveSwitchedToBearish(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_WAVE), + GetBarTime(symbol, period, i), + kiHelper.GetKIWave(i), + kiHelper.GetKIWave(i + 1), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} + +int HasMAFastSwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsMAFastSwitchedToBullish(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_MA_FAST), + GetBarTime(symbol, period, i), + kiHelper.GetMAFast(i), + kiHelper.GetMAFast(i + 1), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsMAFastSwitchedToBearish(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_MA_FAST), + GetBarTime(symbol, period, i), + kiHelper.GetMAFast(i), + kiHelper.GetMAFast(i + 1), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} + +int HasMASlowSwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsMASlowSwitchedToBullish(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_MA_SLOW), + GetBarTime(symbol, period, i), + kiHelper.GetMASlow(i), + kiHelper.GetMASlow(i + 1), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsMASlowSwitchedToBearish(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_MA_SLOW), + GetBarTime(symbol, period, i), + kiHelper.GetMAFast(i), + kiHelper.GetMAFast(i + 1), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} + +int HasMASuperSlowSwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsMASuperSlowSwitchedToBullish(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_MA_SUPER_SLOW), + GetBarTime(symbol, period, i), + kiHelper.GetMASuperSlow(i), + kiHelper.GetMASuperSlow(i + 1), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsMASuperSlowSwitchedToBearish(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_MA_SUPER_SLOW), + GetBarTime(symbol, period, i), + kiHelper.GetMAFast(i), + kiHelper.GetMAFast(i + 1), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} + +int HasMACrossedSwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsMACrossoverSwitchedToBullish(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_MA_CROSS), + GetBarTime(symbol, period, i), + MathMin(kiHelper.GetMAFast(i), kiHelper.GetMASlow(i)), + MathMin(kiHelper.GetMAFast(i + 1), kiHelper.GetMASlow(i + 1)), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsMACrossoverSwitchedToBearish(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_MA_CROSS), + GetBarTime(symbol, period, i), + MathMin(kiHelper.GetMAFast(i), kiHelper.GetMASlow(i)), + MathMin(kiHelper.GetMAFast(i + 1), kiHelper.GetMASlow(i + 1)), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} + +int HasATRVolatilitySwitch( + XDirectionShift &switches[], + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE // +) +{ + // + int result = 0; + + // + XClean(switches); + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool has = false; + XDirectionShift iShift; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + // Bullish ... + bool hasBullish = kiParser.IsVolatilitySwitchdToHigh(i); + has = hasBullish && isBullish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_ATR), + GetBarTime(symbol, period, i), + kiHelper.GetATR(i), + kiHelper.GetATR(i + 1), + symbol, + period, + X_DIRECTION_BULLISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + + // + // Bearish ... + bool hasBearish = kiParser.IsVolatilitySwitchdToLow(i); + has = hasBearish && isBearish; + if (has) + { + // + iShift.Clean(); + has = iShift.Init( + ToXString(X121_XKI_ATR), + GetBarTime(symbol, period, i), + kiHelper.GetATR(i), + kiHelper.GetATR(i + 1), + symbol, + period, + X_DIRECTION_BEARISH // + ); + if (has) + { + // + AddIfNotExists( + iShift, + switches // + ); + + // + iShift.Clean(); + } + } + } + + // + result = ArraySize(switches); + + // + return result; +} +// #endregion + +// #region Peak and Vale ... +// TODO: Implement Root of Changes when IsPeakOverLast or IsValeUnderLast Happens ... +// #endregion + +// #region Rejecteds ... +bool IsKIFastRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetKIFast(barIndex); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsKISlowRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetKISlow(barIndex); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsKISuperSlowRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetKISuperSlow(barIndex); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsKIUpperRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetKIUpper(barIndex); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsKILowerRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetKILower(barIndex); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsMAFastRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetMAFast(barIndex); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsMASlowRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetMASlow(barIndex); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsMASuperSlowRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetMASuperSlow(barIndex); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsPrevPeakRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetPeak(barIndex + 1); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} + +bool IsPrevValeRejected( + ENUM_X_DIRECTION &dir, + int barIndex = 0, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + bool result = false; + + // + dir = X_DIRECTION_NONE; + if (!IsXValid(forSymbol)) + { + forSymbol = symbol; + } + if (!IsXValid(forPeriod)) + { + forPeriod = period; + } + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + XOHCL bar; + result = + kiParser.IsValid() && + bar.Init(forSymbol, forPeriod, barIndex); + if (!result) + { + return result; + } + + // + double iValue = kiHelper.GetVale(barIndex + 1); + + // + bool isBullish = bar.IsRejected(iValue, X_DIRECTION_BULLISH, false, false); + bool isBearish = bar.IsRejected(iValue, X_DIRECTION_BEARISH, false, false); + + // + dir = + isBullish + ? X_DIRECTION_BULLISH + : isBearish + ? X_DIRECTION_BEARISH + : X_DIRECTION_NONE; + + // + result = HasDirection(dir); + + // + bar.Clean(); + + // + return result; +} +// #endregion + +// #region Counters ... +int CountKIFastRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsKIFastRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountKISlowRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsKISlowRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountKISuperSlowRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsKISuperSlowRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountKIUpperRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsKIUpperRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountKILowerRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsKILowerRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountMAFastRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsMAFastRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountMASlowRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsMASlowRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountMASuperSlowRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsMASuperSlowRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountPrevPeakRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsPrevPeakRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} + +int CountPrevValeRejects( + int barIndex = 0, + int loopback = 10, + ENUM_X_DIRECTION forDir = X_DIRECTION_NONE, + string forSymbol = NULL, + ENUM_TIMEFRAMES forPeriod = NULL // +) +{ + // + int result = 0; + + // + loopback = NormalizeInt(loopback, 2); + barIndex = kiParser.NormalizeBarIndex(barIndex); + + // + bool isBullish = !HasDirection(forDir) || IsXBullish(forDir); + bool isBearish = !HasDirection(forDir) || IsXBearish(forDir); + + // + bool is = false; + bool hasBullish = false; + bool hasBearish = false; + ENUM_X_DIRECTION tmpDir; + for (int i = barIndex; i < barIndex + loopback; i++) + { + // + is = IsPrevValeRejected( + tmpDir, + i, + forSymbol, + forPeriod // + ); + hasBullish = is && IsXBullish(tmpDir); + hasBearish = is && IsXBearish(tmpDir); + + // + if ((isBullish && hasBullish) || + (isBearish && hasBearish)) + { + result++; + } + } + + // + return result; +} +// #endregion +// #endregion \ No newline at end of file diff --git a/Documents/BKP/X121XKI/tmps.bkp.mq5 b/Documents/BKP/X121XKI/tmps.bkp.mq5 index 32167e4c..77ba8384 100644 --- a/Documents/BKP/X121XKI/tmps.bkp.mq5 +++ b/Documents/BKP/X121XKI/tmps.bkp.mq5 @@ -4038,6 +4038,951 @@ bool Strategy1HasSignal( } // #endregion + // #region PV ... + bool IsPeakSameAsLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsSame( + helper.GetPeak(barIndex), + helper.GetPeak(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsPeakOverLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsOver( + helper.GetPeak(barIndex), + helper.GetPeak(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsPeakUnderLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsUnder( + helper.GetPeak(barIndex), + helper.GetPeak(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsValeSameAsLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsSame( + helper.GetVale(barIndex), + helper.GetVale(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsValeOverLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsOver( + helper.GetVale(barIndex), + helper.GetVale(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsValeUnderLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsUnder( + helper.GetVale(barIndex), + helper.GetVale(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + // #endregion + + // #region ATR ... + bool IsATRBreakoutUp( + int barIndex = 0, + ENUM_X_PRICE priceType = X_PRICE_CLOSE // + ) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid() && + IsXValid(priceType); + if (!result) + { + return result; + } + + // + XOHCL bar; + result = bar.Init(symbol, period, barIndex); + if (!result) + { + return result; + } + + // + double price = bar.GetPrice(priceType); + result = price > helper.GetATRRawUpper(barIndex); + bar.Clean(); + + // + return result; + } + + bool IsATRBreakoutDown( + int barIndex = 0, + ENUM_X_PRICE priceType = X_PRICE_CLOSE // + ) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid() && + IsXValid(priceType); + if (!result) + { + return result; + } + + // + XOHCL bar; + result = bar.Init(symbol, period, barIndex); + if (!result) + { + return result; + } + + // + double price = bar.GetPrice(priceType); + result = price < helper.GetATRRawLower(barIndex); + bar.Clean(); + + // + return result; + } + + bool IsATROverLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsOver( + helper.GetATR(barIndex), + helper.GetATR(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsATRUnderLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsUnder( + helper.GetATR(barIndex), + helper.GetATR(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsATRSwitchedOverLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsATROverLast(barIndex, tolerance) && + !IsATROverLast(barIndex + 1, tolerance); + + // + return result; + } + + bool IsATRSwitchedUnderLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsATRUnderLast(barIndex, tolerance) && + !IsATRUnderLast(barIndex + 1, tolerance); + + // + return result; + } + + bool IsATRSmoothedOverLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsOver( + helper.GetATRSmoothed(barIndex), + helper.GetATRSmoothed(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsATRSmoothedUnderLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsUnder( + helper.GetATRSmoothed(barIndex), + helper.GetATRSmoothed(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsATRSmoothedSwitchedOverLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsATRSmoothedOverLast(barIndex, tolerance) && + !IsATRSmoothedOverLast(barIndex + 1, tolerance); + + // + return result; + } + + bool IsATRSmoothedSwitchedUnderLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsATRSmoothedUnderLast(barIndex, tolerance) && + !IsATRSmoothedUnderLast(barIndex + 1, tolerance); + + // + return result; + } + + bool IsVolatilityHigh(int barIndex = 0) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + double atr = helper.GetATR(barIndex); + double atrMa = helper.GetATRSmoothed(barIndex); + result = atr > atrMa; + + // + return result; + } + + bool IsVolatilityLow(int barIndex = 0) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + double atr = helper.GetATR(barIndex); + double atrMa = helper.GetATRSmoothed(barIndex); + result = atr < atrMa; + + // + return result; + } + + bool IsVolatilitySwitchdToHigh(int barIndex = 0) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + double atr = helper.GetATR(barIndex); + double atrPrev = helper.GetATR(barIndex + 1); + double atrMa = helper.GetATRSmoothed(barIndex); + double atrMaPrev = helper.GetATRSmoothed(barIndex + 1); + + // + result = + atr > atrMa && + atrPrev <= atrMaPrev; + + // + return result; + } + + bool IsVolatilitySwitchdToLow(int barIndex = 0) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + double atr = helper.GetATR(barIndex); + double atrPrev = helper.GetATR(barIndex + 1); + double atrMa = helper.GetATRSmoothed(barIndex); + double atrMaPrev = helper.GetATRSmoothed(barIndex + 1); + + // + result = + atr < atrMa && + atrPrev >= atrMaPrev; + + // + return result; + } + // #endregion + + // #region RSI ... + bool IsRSIBullish( + int barIndex = 0, + double threshold = 55, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + result = helper.GetRSI(barIndex) > threshold + (GetPoints(symbol) * tolerance) || + helper.GetRSI(barIndex) > threshold - (GetPoints(symbol) * tolerance); + + // + return result; + } + + bool IsRSISwitchedToBullish( + int barIndex = 0, + double threshold = 55, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + result = + IsRSIBullish(barIndex, threshold, tolerance) && + !IsRSIBullish(barIndex + 1, threshold, tolerance); + + // + return result; + } + + bool IsRSIBearish( + int barIndex = 0, + double threshold = 45, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + result = helper.GetRSI(barIndex) < threshold + (GetPoints(symbol) * tolerance) || + helper.GetRSI(barIndex) < threshold - (GetPoints(symbol) * tolerance); + + // + return result; + } + + bool IsRSISwitchedToBearish( + int barIndex = 0, + double threshold = 45, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + result = + IsRSIBearish(barIndex, threshold, tolerance) && + !IsRSIBearish(barIndex + 1, threshold, tolerance); + + // + return result; + } + + bool IsRSIRising(int barIndex = 0) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + helper.GetRSI(barIndex) > helper.GetRSISmoothed(barIndex); + + // + return result; + } + + bool IsRSISwitchedToRising(int barIndex = 0) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsRSIRising(barIndex) && + !IsRSIRising(barIndex + 1); + + // + return result; + } + + bool IsRSIFalling(int barIndex = 0) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + helper.GetRSI(barIndex) < helper.GetRSISmoothed(barIndex); + + // + return result; + } + + bool IsRSISwitchedToFalling(int barIndex = 0) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsRSIFalling(barIndex) && + !IsRSIFalling(barIndex + 1); + + // + return result; + } + + bool IsRSIOverLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsOver( + helper.GetRSI(barIndex), + helper.GetRSI(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsRSISwitchedOverLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsRSIOverLast(barIndex, tolerance) && + !IsRSIOverLast(barIndex + 1, tolerance); + + // + return result; + } + + bool IsRSIUnderLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsUnder( + helper.GetRSI(barIndex), + helper.GetRSI(barIndex + 1), + GetPoints(symbol) * tolerance // + ); + + // + return result; + } + + bool IsRSISwitchedUnderLast( + int barIndex = 0, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsRSIUnderLast(barIndex, tolerance) && + !IsRSIUnderLast(barIndex + 1, tolerance); + + // + return result; + } + + bool IsRSIOverbought( + int barIndex = 0, + double threshold = 70, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + result = helper.GetRSI(barIndex) > threshold + (GetPoints(symbol) * tolerance) || + helper.GetRSI(barIndex) > threshold - (GetPoints(symbol) * tolerance); + + // + return result; + } + + bool IsRSIOversold( + int barIndex = 0, + double threshold = 30, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + // Normalize ... + barIndex = NormalizeBarIndex(barIndex); + + // + // Validate ... + result = IsValid(); + if (!result) + { + return result; + } + + // + result = helper.GetRSI(barIndex) < threshold + (GetPoints(symbol) * tolerance) || + helper.GetRSI(barIndex) < threshold - (GetPoints(symbol) * tolerance); + + // + return result; + } + + bool IsRSISwitchedToOversold( + int barIndex = 0, + double threshold = 30, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsRSIOversold(barIndex, threshold, tolerance) && + !IsRSIOversold(barIndex + 1, threshold, tolerance); + + // + return result; + } + + bool IsRSISwitchedFromOversold( + int barIndex = 0, + double threshold = 30, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + !IsRSIOversold(barIndex, threshold, tolerance) && + IsRSIOversold(barIndex + 1, threshold, tolerance); + + // + return result; + } + + bool IsRSISwitchedToOverbought( + int barIndex = 0, + double threshold = 70, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + IsRSIOverbought(barIndex, threshold, tolerance) && + !IsRSIOverbought(barIndex + 1, threshold, tolerance); + + // + return result; + } + + bool IsRSISwitchedFromOverbought( + int barIndex = 0, + double threshold = 70, + double tolerance = 2 // + ) + { + // + bool result = false; + + // + barIndex = NormalizeBarIndex(barIndex); + + // + result = + IsValid() && + !IsRSIOverbought(barIndex, threshold, tolerance) && + IsRSIOverbought(barIndex + 1, threshold, tolerance); + + // + return result; + } + // #endregion // #region Composite ... bool IsKIHasTrend( diff --git a/X121XKIEA/Classes/x-saherelm.x121.xki.parser.class.mq5 b/X121XKIEA/Classes/x-saherelm.x121.xki.parser.class.mq5 index 05e973b3..c135a550 100644 --- a/X121XKIEA/Classes/x-saherelm.x121.xki.parser.class.mq5 +++ b/X121XKIEA/Classes/x-saherelm.x121.xki.parser.class.mq5 @@ -114,7 +114,7 @@ class XCX121XKIHelperParser : XCBase // barIndex = NormalizeBarIndex(barIndex); XOHCL result; - result.Init(symbol, period); + result.Init(symbol, period, barIndex); return result; } @@ -171,153 +171,22 @@ class XCX121XKIHelperParser : XCBase DECLARE_CROSSING_COMPARATOR_FUNCTIONS("KI", "Slow", "SuperSlow", helper.GetKISlow, helper.GetKISuperSlow, NormalizeBarIndex, GetPoints); DECLARE_CROSSING_COMPARATOR_FUNCTIONS("MA", "Slow", "SuperSlow", helper.GetMASlow, helper.GetMASuperSlow, NormalizeBarIndex, GetPoints); - // #region PV ... - bool IsPeakSameAsLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; + // + DECLARE_VALUE_COMPARATOR_FUNCTIONS("Peak", helper.GetPeak, NormalizeBarIndex, GetPoints); + DECLARE_VALUE_COMPARATOR_FUNCTIONS("Vale", helper.GetVale, NormalizeBarIndex, GetPoints); - // - barIndex = NormalizeBarIndex(barIndex); + // + DECLARE_VALUE_COMPARATOR_FUNCTIONS("ATR", helper.GetATR, NormalizeBarIndex, GetPoints); + DECLARE_VALUE_COMPARATOR_FUNCTIONS("ATRSmoothed", helper.GetATRSmoothed, NormalizeBarIndex, GetPoints); - // - result = - IsValid() && - IsSame( - helper.GetPeak(barIndex), - helper.GetPeak(barIndex + 1), - GetPoints(symbol) * tolerance // - ); + // + DECLARE_VALUE_COMPARATOR_FUNCTIONS("RSI", helper.GetRSI, NormalizeBarIndex, GetPoints); + DECLARE_VALUE_COMPARATOR_FUNCTIONS("RSISmoothed", helper.GetRSISmoothed, NormalizeBarIndex, GetPoints); - // - return result; - } + // + // + // - bool IsPeakOverLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsOver( - helper.GetPeak(barIndex), - helper.GetPeak(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsPeakUnderLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsUnder( - helper.GetPeak(barIndex), - helper.GetPeak(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsValeSameAsLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsSame( - helper.GetVale(barIndex), - helper.GetVale(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsValeOverLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsOver( - helper.GetVale(barIndex), - helper.GetVale(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsValeUnderLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsUnder( - helper.GetVale(barIndex), - helper.GetVale(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - // #endregion - - // #region ATR ... bool IsATRBreakoutUp( int barIndex = 0, ENUM_X_PRICE priceType = X_PRICE_CLOSE // @@ -394,186 +263,6 @@ class XCX121XKIHelperParser : XCBase return result; } - bool IsATROverLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsOver( - helper.GetATR(barIndex), - helper.GetATR(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsATRUnderLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsUnder( - helper.GetATR(barIndex), - helper.GetATR(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsATRSwitchedOverLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsATROverLast(barIndex, tolerance) && - !IsATROverLast(barIndex + 1, tolerance); - - // - return result; - } - - bool IsATRSwitchedUnderLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsATRUnderLast(barIndex, tolerance) && - !IsATRUnderLast(barIndex + 1, tolerance); - - // - return result; - } - - bool IsATRSmoothedOverLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsOver( - helper.GetATRSmoothed(barIndex), - helper.GetATRSmoothed(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsATRSmoothedUnderLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsUnder( - helper.GetATRSmoothed(barIndex), - helper.GetATRSmoothed(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsATRSmoothedSwitchedOverLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsATRSmoothedOverLast(barIndex, tolerance) && - !IsATRSmoothedOverLast(barIndex + 1, tolerance); - - // - return result; - } - - bool IsATRSmoothedSwitchedUnderLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsATRSmoothedUnderLast(barIndex, tolerance) && - !IsATRSmoothedUnderLast(barIndex + 1, tolerance); - - // - return result; - } - bool IsVolatilityHigh(int barIndex = 0) { // @@ -689,9 +378,7 @@ class XCX121XKIHelperParser : XCBase // return result; } - // #endregion - // #region RSI ... bool IsRSIBullish( int barIndex = 0, double threshold = 55, @@ -714,8 +401,8 @@ class XCX121XKIHelperParser : XCBase } // - result = helper.GetRSI(barIndex) > threshold + (GetPoints(symbol) * tolerance) || - helper.GetRSI(barIndex) > threshold - (GetPoints(symbol) * tolerance); + result = helper.GetRSI(barIndex) > threshold + (GetXPoints(symbol) * tolerance) || + helper.GetRSI(barIndex) > threshold - (GetXPoints(symbol) * tolerance); // return result; @@ -773,8 +460,8 @@ class XCX121XKIHelperParser : XCBase } // - result = helper.GetRSI(barIndex) < threshold + (GetPoints(symbol) * tolerance) || - helper.GetRSI(barIndex) < threshold - (GetPoints(symbol) * tolerance); + result = helper.GetRSI(barIndex) < threshold + (GetXPoints(symbol) * tolerance) || + helper.GetRSI(barIndex) < threshold - (GetXPoints(symbol) * tolerance); // return result; @@ -880,96 +567,6 @@ class XCX121XKIHelperParser : XCBase return result; } - bool IsRSIOverLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsOver( - helper.GetRSI(barIndex), - helper.GetRSI(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsRSISwitchedOverLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsRSIOverLast(barIndex, tolerance) && - !IsRSIOverLast(barIndex + 1, tolerance); - - // - return result; - } - - bool IsRSIUnderLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsUnder( - helper.GetRSI(barIndex), - helper.GetRSI(barIndex + 1), - GetPoints(symbol) * tolerance // - ); - - // - return result; - } - - bool IsRSISwitchedUnderLast( - int barIndex = 0, - double tolerance = 2 // - ) - { - // - bool result = false; - - // - barIndex = NormalizeBarIndex(barIndex); - - // - result = - IsValid() && - IsRSIUnderLast(barIndex, tolerance) && - !IsRSIUnderLast(barIndex + 1, tolerance); - - // - return result; - } - bool IsRSIOverbought( int barIndex = 0, double threshold = 70, @@ -992,8 +589,8 @@ class XCX121XKIHelperParser : XCBase } // - result = helper.GetRSI(barIndex) > threshold + (GetPoints(symbol) * tolerance) || - helper.GetRSI(barIndex) > threshold - (GetPoints(symbol) * tolerance); + result = helper.GetRSI(barIndex) > threshold + (GetXPoints(symbol) * tolerance) || + helper.GetRSI(barIndex) > threshold - (GetXPoints(symbol) * tolerance); // return result; @@ -1021,8 +618,8 @@ class XCX121XKIHelperParser : XCBase } // - result = helper.GetRSI(barIndex) < threshold + (GetPoints(symbol) * tolerance) || - helper.GetRSI(barIndex) < threshold - (GetPoints(symbol) * tolerance); + result = helper.GetRSI(barIndex) < threshold + (GetXPoints(symbol) * tolerance) || + helper.GetRSI(barIndex) < threshold - (GetXPoints(symbol) * tolerance); // return result; @@ -1115,7 +712,6 @@ class XCX121XKIHelperParser : XCBase // return result; } - // #endregion // // Protected ... diff --git a/X121XKIEA/Classes/x-saherelm.x121.xki.x-poi.detector.class.mq5 b/X121XKIEA/Classes/x-saherelm.x121.xki.x-poi.detector.class.mq5 index f115482e..97163aa9 100644 --- a/X121XKIEA/Classes/x-saherelm.x121.xki.x-poi.detector.class.mq5 +++ b/X121XKIEA/Classes/x-saherelm.x121.xki.x-poi.detector.class.mq5 @@ -2233,7 +2233,7 @@ class XCX121XKIPOIDetector : public XCMarketPatternDetector { // // Bullish ... - bool hasBullish = kiParser.IsMACrossoverSwitchedToBullish(i); + bool hasBullish = kiParser.IsMAFastCrossedOverSlow(i); has = hasBullish && isBullish; if (has) { @@ -2263,7 +2263,7 @@ class XCX121XKIPOIDetector : public XCMarketPatternDetector // // Bearish ... - bool hasBearish = kiParser.IsMACrossoverSwitchedToBearish(i); + bool hasBearish = kiParser.IsMAFastCrossedUnderSlow(i); has = hasBearish && isBearish; if (has) {