This commit is contained in:
2025-10-30 18:41:45 +03:30
parent 574c79afcc
commit 7ed6fb61bd
5 changed files with 956 additions and 94 deletions
+692 -94
View File
@@ -2227,6 +2227,450 @@ class XCMarketPatternDetector : public XCBase
return result;
}
//
// Complex ...
/**
* Check Double Pinned Bar ...
*
* @param bar: XOHCL, reference to Specified Bar ...
* @param dir: ENUM_X_DIRECTION, reference to holds Pattern Direction ...
* @param shadowApprovedMultiplier: double, Shadow Size Approve Multiplier ...
* @param minimumPinBarRangeMultiplier: doubble, Range Size Approve Multiplier in Point ...
* @param forceDirection: bool, Apply Force Bar Type ...
* @param loopback: int, Max Allowed Detecting Loopback lenght ...
*
* @return ( bool )
*/
bool IsDoublePinned(
XOHCL &bar,
ENUM_X_DIRECTION &dir,
double shadowApprovedMultiplier = 3,
double minimumPinBarRangeMultiplier = 4,
bool forceDirection = false,
int loopback = 5 //
)
{
//
bool result = false;
//
// Prepare ...
CleanDirection(dir);
//
// Normalize ...
loopback = NormalizeInt(loopback, 1);
shadowApprovedMultiplier = NormalizeDouble(shadowApprovedMultiplier, 2, 5);
minimumPinBarRangeMultiplier = NormalizeDouble(minimumPinBarRangeMultiplier, 2, 100);
//
// Validate ...
result = bar.IsValid();
if (!result)
{
return result;
}
//
// Do ...
//
// Current Bar Must be a Pinned Bar ...
result = IsPinnedBar(
bar,
dir,
shadowApprovedMultiplier,
minimumPinBarRangeMultiplier,
forceDirection //
);
if (!result)
{
//
CleanDirection(dir);
//
return result;
}
//
XOHCL iBar;
ENUM_X_DIRECTION iDir;
int start = bar.Index() + 1;
int end = start + loopback;
for (int i = start; i < end; i++)
{
//
iBar.Clean();
result = bar.BarAt(i, iBar);
result = result && IsPinnedBar(
iBar,
iDir,
shadowApprovedMultiplier,
minimumPinBarRangeMultiplier,
forceDirection //
);
result = result &&
iDir == dir;
if (result)
{
break;
}
}
//
// Cleanup ...
if (!result)
{
CleanDirection(dir);
}
iBar.Clean();
CleanDirection(iDir);
//
return result;
}
/**
* Check Double Engulfed Bar ...
*
* @param bar: XOHCL, reference to Specified Bar ...
* @param dir: ENUM_X_DIRECTION, reference to holds Pattern Direction ...
* @param loopback: int, Max Allowed Detecting Loopback lenght ...
*
* @return ( bool )
*/
bool IsDoubleEngulfed(
XOHCL &bar,
ENUM_X_DIRECTION &dir,
int loopback = 5 //
)
{
//
bool result = false;
//
// Prepare ...
CleanDirection(dir);
//
// Normalize ...
loopback = NormalizeInt(loopback, 1);
//
// Validate ...
result = bar.IsValid();
if (!result)
{
return result;
}
//
// Do ...
//
// Current Bar Must be a Pinned Bar ...
result = IsEngulfedBar(
bar,
dir //
);
if (!result)
{
//
CleanDirection(dir);
//
return result;
}
//
XOHCL iBar;
ENUM_X_DIRECTION iDir;
int start = bar.Index() + 1;
int end = start + loopback;
for (int i = start; i < end; i++)
{
//
iBar.Clean();
result = bar.BarAt(i, iBar);
result = result && IsEngulfedBar(
iBar,
iDir //
);
result = result &&
iDir == dir;
if (result)
{
break;
}
}
//
// Cleanup ...
if (!result)
{
CleanDirection(dir);
}
iBar.Clean();
CleanDirection(iDir);
//
return result;
}
/**
* Check Double Momentum Bar ...
*
* @param bar: XOHCL, reference to Specified Bar ...
* @param dir: ENUM_X_DIRECTION, reference to holds Pattern Direction ...
* @param requiredBars: int, bar range for approve Momentum ...
* @param approvedMultiplier: double, a Multipler for approve Momentum ...
* @param loopback: int, Max Allowed Detecting Loopback lenght ...
*
* @return ( bool )
*/
bool IsDoubleMomentum(
XOHCL &bar,
ENUM_X_DIRECTION &dir,
int requiredBars = 3,
double approvedMultiplier = 2,
int loopback = 5 //
)
{
//
bool result = false;
//
// Prepare ...
CleanDirection(dir);
//
// Normalize ...
loopback = NormalizeInt(loopback, 1);
requiredBars = NormalizeInt(requiredBars, 3, 10);
approvedMultiplier = NormalizeDouble(approvedMultiplier, 2, 5);
//
// Validate ...
result = bar.IsValid();
if (!result)
{
return result;
}
//
// Do ...
//
// Current Bar Must be a Pinned Bar ...
result = IsMomentumBar(
bar,
dir,
requiredBars,
approvedMultiplier //
);
if (!result)
{
//
CleanDirection(dir);
//
return result;
}
//
XOHCL iBar;
ENUM_X_DIRECTION iDir;
int start = bar.Index() + 1;
int end = start + loopback;
for (int i = start; i < end; i++)
{
//
iBar.Clean();
result = bar.BarAt(i, iBar);
result = result && IsMomentumBar(
iBar,
iDir,
requiredBars,
approvedMultiplier //
);
result = result &&
iDir == dir;
if (result)
{
break;
}
}
//
// Cleanup ...
if (!result)
{
CleanDirection(dir);
}
iBar.Clean();
CleanDirection(iDir);
//
return result;
}
/**
* Check Has Double Patterns ...
*
* @param bar: XOHCL, reference to Specified Bar ...
* @param dir: ENUM_X_DIRECTION, reference to holds Specified Patterns ...
* @param barPatterns: XPatternAnalysis, reference to Provides Bar's Pattern Analysis ...
* @param pBarPatterns: XPatternAnalysis, reference to Provides Previous Bar's Pattern Analysis ...
* @param allowedPatterns: ENUM_X_BAR_PATTERN, collection to Provide Allowed Bar Patterns for Detection ...
* @param config: XPatternAnalysisConfig, Provides Patterns Detection Config ...
* @param loopback: int, Max Allowed Loopback for Detection ...
* @param forDir: ENUM_X_DIRECTION, Specified Patterns Detection Direction ...
*
* @return ( bool )
*/
bool HasDoublePatterns(
XOHCL &bar,
ENUM_X_DIRECTION &dir,
XPatternAnalysis &barPatterns,
XPatternAnalysis &pBarPatterns,
ENUM_X_BAR_PATTERN &allowedPatterns[],
XPatternAnalysisConfig &config,
int loopback = 5,
ENUM_X_DIRECTION forDir = X_DIRECTION_NONE //
)
{
//
bool result = false;
//
// Prepare ...
barPatterns.Clean();
CleanDirection(dir);
pBarPatterns.Clean();
XPatternAnalysisConfig iConfig = config;
//
// Normalize ...
loopback = NormalizeInt(loopback, 2);
//
// Validate ...
result = bar.IsValid() &&
HasChild(allowedPatterns);
if (!result)
{
return result;
}
//
// Prepare Config ...
iConfig.CleanPatterns();
if (HasChild(allowedPatterns))
{
//
for (int i = 0; i < ArraySize(allowedPatterns); i++)
{
iConfig.AddPattern(allowedPatterns[i]);
}
}
//
// Detect Bar Patterns ...
result = AnalyseBarPatterns(bar, barPatterns, config);
if (!result)
{
//
CleanDirection(dir);
barPatterns.Clean();
pBarPatterns.Clean();
//
return result;
}
//
// Check Direction ...
int bullishCount = barPatterns.Count(X_DIRECTION_BULLISH);
int bearishCount = barPatterns.Count(X_DIRECTION_BEARISH);
dir =
bullishCount > bearishCount
? X_DIRECTION_BULLISH
: bearishCount > bullishCount
? X_DIRECTION_BEARISH
: X_DIRECTION_NONE;
result = HasDirection(dir);
//
// Check for Dir ...
if (HasDirection(forDir))
{
//
result =
result &&
dir == forDir;
}
//
// Looping Back ...
if (result)
{
//
XOHCL iBar;
ENUM_X_DIRECTION iDir;
int start = bar.Index() + 1;
int end = start + loopback;
for (int i = start; i < end; i++)
{
//
iBar.Clean();
pBarPatterns.Clean();
result = bar.BarAt(i, iBar);
result = result &&
AnalyseBarPatterns(iBar, pBarPatterns, iConfig);
if (!result)
{
continue;
}
//
bullishCount = pBarPatterns.Count(X_DIRECTION_BULLISH);
bearishCount = pBarPatterns.Count(X_DIRECTION_BEARISH);
iDir =
bullishCount > bearishCount
? X_DIRECTION_BULLISH
: bearishCount > bullishCount
? X_DIRECTION_BEARISH
: X_DIRECTION_NONE;
result = HasDirection(iDir);
result = result &&
dir == iDir;
if (result)
{
break;
}
}
//
iBar.Clean();
CleanDirection(iDir);
}
//
// Cleanup ...
if (!result)
{
//
CleanDirection(dir);
barPatterns.Clean();
pBarPatterns.Clean();
}
iConfig.Clean();
//
return result;
}
//
// Trending ...
@@ -3492,6 +3936,17 @@ class XCMarketPatternDetector : public XCBase
return result;
}
/**
* Collect Required Order Blocks ...
*
* @param bar: XOHCL, reference to Specified Bar ...
* @param dest: XBoxZone, collection reference to holds detected zones ...
* @param zonesLoopback: int, zones detection loopback ...
* @param maxRequiredZone: int, number of required zones ...
* @param loopback: int, max allowed loopback lenght for zone Detection ...
*
* @return ( int )
*/
int CollectOBs(
XOHCL &bar,
XBoxZone &dest[],
@@ -3569,6 +4024,17 @@ class XCMarketPatternDetector : public XCBase
return result;
}
/**
* Collect Required Fair Value Gaps ...
*
* @param bar: XOHCL, reference to Specified Bar ...
* @param dest: XBoxZone, collection reference to holds detected zones ...
* @param zonesLoopback: int, zones detection loopback ...
* @param maxRequiredZone: int, number of required zones ...
* @param loopback: int, max allowed loopback lenght for zone Detection ...
*
* @return ( int )
*/
int CollectFVGs(
XOHCL &bar,
XBoxZone &dest[],
@@ -3646,6 +4112,18 @@ class XCMarketPatternDetector : public XCBase
return result;
}
/**
* Collect Required Support and Resistance Zones ...
*
* @param bar: XOHCL, reference to Specified Bar ...
* @param dest: XBoxZone, collection reference to holds detected zones ...
* @param zonesLoopback: int, zones detection loopback ...
* @param zonesValidationLength: int, zones validation length ...
* @param maxRequiredZone: int, number of required zones ...
* @param loopback: int, max allowed loopback lenght for zone Detection ...
*
* @return ( int )
*/
int CollectZones(
XOHCL &bar,
XBoxZone &dest[],
@@ -3753,6 +4231,220 @@ class XCMarketPatternDetector : public XCBase
return result;
}
/**
* Detect and Collect Required Zones ...
*
* @param bar: XOHCL, reference to Specified Bar ...
* @param zones: XBoxZone, collection reference to holds detected zones ...
* @param validateZones: bool, Specified to Detect only Valid Zones ...
* @param containsOBs: bool, Flag to use Order Block Zones ...
* @param containsFVGs: bool, Flag to use Fair Value Gap Zones ...
* @param containsSupports: bool, Flag to use Support Zones ...
* @param containsResistancess: bool, Flag to use Resistance Zones ...
* @param forDir: ENUM_X_DIRECTION, Specified Zones Direction for Detecting ...
* @param sortby: ENUM_X_SORT_BY, Specified Zones Sorting Factor ...
* @param sortDir: ENUM_X_DIRECTION, Specified Zones Sorting Direction ...
* @param zonesLoopback: int, loop back for Zones Detection ...
* @param zonesValidationLength: int, zones Validation Length ...
* @param count: int, number of required Zones ...
* @param loopback: int, max allowed looping back lenght for detection ...
*
* @return ( int )
*/
int DetectZones(
XOHCL &bar,
XBoxZone &zones[],
bool validateZones = true,
bool removeUsedZones = true,
bool containsOBs = true,
bool containsFVGs = true,
bool containsSupports = true,
bool containsResistancess = true,
ENUM_X_DIRECTION forDir = X_DIRECTION_NONE,
ENUM_X_SORT_BY sortBy = X_SORT_BY_DATE,
ENUM_X_DIRECTION sortDir = X_DIRECTION_BEARISH,
int zonesLoopback = 5,
int zonesValidationLength = 5,
int count = 0,
int loopback = 500 //
)
{
//
int result = 0;
//
// Prepare ...
XClean(zones);
//
// Normalize ...
count = NormalizeInt(count, 0);
loopback = NormalizeInt(loopback, 50);
zonesLoopback = NormalizeInt(zonesLoopback, 2);
zonesValidationLength = NormalizeInt(zonesValidationLength, 3);
//
// Validate ...
bool has = bar.IsValid() &&
IsXValid(sortDir) &&
IsXValid(sortBy) &&
(containsOBs || containsFVGs || containsSupports || containsResistancess);
if (!has)
{
return result;
}
//
XOHCL iBar;
XOHCL tmpBar;
XPivot tmpPivot;
XBoxZone tmpZone;
ENUM_X_DIRECTION tmpDir;
int idx = bar.Index();
while (idx < bar.Index() + loopback)
{
//
idx++;
//
iBar.Clean();
tmpBar.Clean();
tmpZone.Clean();
tmpPivot.Clean();
//
has = bar.BarAt(idx, iBar);
if (!has)
{
continue;
}
//
// Collecting Zones ...
//
// Support ...
if (containsSupports)
{
//
if (!HasDirection(forDir) || IsXBullish(forDir))
{
//
has = HasSupport(iBar, tmpBar, zonesValidationLength, zonesLoopback);
if (has)
{
//
has = ToBox(tmpBar, tmpZone, X_DIRECTION_BULLISH, X_BAR_PATTERN_SUPPORT);
if (has)
{
AddIfNotExists(tmpZone, zones);
}
}
}
}
//
// Resistance ...
if (containsResistancess)
{
//
if (!HasDirection(forDir) || IsXBearish(forDir))
{
//
has = HasResistance(iBar, tmpBar, zonesValidationLength, zonesLoopback);
if (has)
{
//
has = ToBox(tmpBar, tmpZone, X_DIRECTION_BEARISH, X_BAR_PATTERN_RESISTANCE);
if (has)
{
AddIfNotExists(tmpZone, zones);
}
}
}
}
//
// Order Block ...
if (containsOBs)
{
//
has = HasOB(iBar, tmpDir, tmpZone, zonesLoopback);
if (has && (!HasDirection(forDir) || tmpDir == forDir))
{
AddIfNotExists(tmpZone, zones);
}
}
//
// Fair Value Gaps ...
if (containsFVGs)
{
//
has = HasFVG(iBar, tmpDir, tmpZone, zonesLoopback);
if (has && (!HasDirection(forDir) || tmpDir == forDir))
{
AddIfNotExists(tmpZone, zones);
}
}
}
//
// Validate Zones Exists ...
result = ArraySize(zones);
has = IsValidSize(result);
if (!has)
{
return result;
}
//
// Update Zones Time ...
UpdateToTime(zones, bar.time);
//
// Validate Zones ...
if (validateZones)
{
//
// Apply Zones Validation Here ...
RemoveBreakedZones(zones, true);
}
//
// Remove Filled Zones ...
if (removeUsedZones)
{
//
// Remove all Filled Zones ...
RemoveFilledZones(zones);
}
//
// Apply Sorting ...
Sort(zones, sortBy, sortDir);
//
// Validate Zones Count ...
if (count > 0)
{
CleanupArray(zones, count);
}
//
result = ArraySize(zones);
//
// Cleanup ...
iBar.Clean();
tmpBar.Clean();
tmpZone.Clean();
tmpPivot.Clean();
//
return result;
}
/**
* Filter Zones ...
*
@@ -3842,100 +4534,6 @@ class XCMarketPatternDetector : public XCBase
return result;
}
//
// Trigger Bar ...
bool IsTriggerBar(
XOHCL &bar,
ENUM_X_DIRECTION forDir,
ENUM_TIMEFRAMES forPeriod = PERIOD_M1 //
)
{
//
// Trigger Bars Detected in Specified Perido ...
//
bool result = false;
//
// Validate ...
result = bar.IsValid() &&
IsXValid(forPeriod) &&
HasDirection(forDir);
if (!result)
{
return result;
}
//
// Do ...
//
// Initialized Specified Bar in Specified Time Frame ...
XOHCL periodBar;
int index = GetBarIndex(
bar.symbol,
forPeriod,
TimeCurrent() //
);
result = periodBar.Init(bar.symbol, forPeriod, index);
if (!result)
{
return result;
}
//
// Detect Pattern ...
XPatternAnalysisConfig iConfig;
iConfig.Default();
iConfig.CleanPatterns();
iConfig.AddPattern(X_BAR_PATTERN_LOW);
iConfig.AddPattern(X_BAR_PATTERN_HIGH);
iConfig.AddPattern(X_BAR_PATTERN_PINNED);
iConfig.AddPattern(X_BAR_PATTERN_ENGULFED);
iConfig.AddPattern(X_BAR_PATTERN_SIGNALKEY);
//
XPatternAnalysis periodBarAnalysis;
result = AnalyseBarPatterns(periodBar, periodBarAnalysis, iConfig);
//
bool isBullish =
result &&
IsXBullish(forDir) &&
(
//
periodBarAnalysis.HasPattern(X_BAR_PATTERN_PINNED, X_DIRECTION_BULLISH) ||
periodBarAnalysis.HasPattern(X_BAR_PATTERN_ENGULFED, X_DIRECTION_BULLISH) ||
periodBarAnalysis.HasPattern(X_BAR_PATTERN_SIGNALKEY, X_DIRECTION_BULLISH)
//
);
//
bool isBearish =
result &&
IsXBearish(forDir) &&
(
//
periodBarAnalysis.HasPattern(X_BAR_PATTERN_PINNED, X_DIRECTION_BEARISH) ||
periodBarAnalysis.HasPattern(X_BAR_PATTERN_ENGULFED, X_DIRECTION_BEARISH) ||
periodBarAnalysis.HasPattern(X_BAR_PATTERN_SIGNALKEY, X_DIRECTION_BEARISH)
//
);
//
// Summarize Result ...
result = isBullish || isBearish;
//
// Cleanup ...
iConfig.Clean();
periodBar.Clean();
periodBarAnalysis.Clean();
//
return result;
}
//
// Protected ...
protected:
@@ -5108,6 +5108,116 @@ int RemoveBreakedZones(
return result;
}
/**
* Remove Filled Zones ...
*
* @param source: XBoxZone, collection reference to Provide Data Source ...
* @param zoneRangeFilledFactor: double, Filling Factor ...
*
* @return ( int )
*/
int RemoveFilledZones(
XBoxZone &source[],
double zoneRangeFilledFactor = 0.8 //
)
{
//
int result = 0;
//
// Validate ...
bool has = HasChild(source);
if (!has)
{
return result;
}
//
XBoxZone iTMP;
XBoxZone tmp[];
Copy(source, tmp);
XClean(source);
while (HasChild(tmp))
{
//
iTMP.Clean();
iTMP = tmp[0];
ArrayRemove(tmp, 0, 1);
//
has = IsFilled(iTMP, zoneRangeFilledFactor);
if (!has)
{
AddIfNotExists(iTMP, source);
}
}
//
result = ArraySize(source);
//
return result;
}
/**
* Check a Zone is Filled or Not ...
*
* @param zone: XBoxZone, reference to Specified Zone ...
* @param zoneRangeFilledFactor: double, Filling Factor ...
*
* @return ( bool )
*/
bool IsFilled(
XBoxZone &zone,
double zoneRangeFilledFactor = 0.8 //
)
{
//
bool result = false;
//
// Validate ...
result = zone.IsValid() &&
zoneRangeFilledFactor > 0 &&
zoneRangeFilledFactor < 1;
if (!result)
{
//
result = true;
return result;
}
//
XOHCL iBar;
int toIDX = zone.ToIndex();
int fromIDX = zone.FromIndex();
double zoneRangeFactor = zone.GetRange() / 100;
double useValue = zone.lower + (zoneRangeFactor * zoneRangeFilledFactor);
for (int i = toIDX; i < fromIDX; i++)
{
//
// Initialize Indexed Bar ...
iBar.Clean();
result = iBar.Init(zone.symbol, zone.period, i);
result =
result &&
(zone.IsBullish()
? iBar.GetPrice(X_PRICE_LOW) <= useValue
: iBar.GetPrice(X_PRICE_HIGH) >= useValue);
if (result)
{
break;
}
}
//
// Cleanup ...
iBar.Clean();
//
return result;
}
/**
* Check Specified Zone is Breaked by Specified Bar or not ...
*
+34
View File
@@ -318,6 +318,40 @@ int GetAllBarPatters(ENUM_X_BAR_PATTERN &dest[])
return ArraySize(dest);
}
/**
* Fill Required Candlestick Patters ...
*
* @param dest: ENUM_X_BAR_PATTERN, collection reference to Fill ...
*
* @return ( int )
*/
int GetCandlestickPatterns(ENUM_X_BAR_PATTERN &dest[])
{
//
int result = 0;
//
// Prepare ...
XClean(dest);
//
Add(X_BAR_PATTERN_STAR, dest);
Add(X_BAR_PATTERN_FLAG, dest);
Add(X_BAR_PATTERN_PINNED, dest);
Add(X_BAR_PATTERN_RISING, dest);
Add(X_BAR_PATTERN_MOMENTUM, dest);
Add(X_BAR_PATTERN_ENGULFED, dest);
Add(X_BAR_PATTERN_PIERCING, dest);
Add(X_BAR_PATTERN_SIGNALKEY, dest);
Add(X_BAR_PATTERN_TRUE_GAPED, dest);
//
result = ArraySize(dest);
//
return result;
}
//
// Structures ...
@@ -1925,11 +1925,13 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
XOHCL tmpBar;
XPivot tmpPivot;
XBoxZone atrBox;
XBoxZone zones[];
XBoxZone tmpZone;
XBoxZone scPVZone;
XBoxZone mcPVZone;
XBoxZone lcPVZone;
XBoxZone hcPVZone;
XBoxZone tmpZones[];
XBoxZone pinBarZone;
XBoxZone supports[];
XBoxZone resistances[];
@@ -2151,6 +2153,65 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
}
}
//
// Collecting Zones ...
//
int collectedZonesCount = poiDetector.DetectZones(
bar,
zones,
true, // Validated Zones ...
false, // Remove Used Zones ...
false, // Contains Order Blocks ...
true, // Contains Fair Value Gaps ...
true, // Contains Supports ...
true, // Contains Resistances ...
X_DIRECTION_NONE, // For Dir (Contains All Direction Zones) ...
X_SORT_BY_DATE, // Sort By ...
X_DIRECTION_BEARISH, // Sort Dir ...
3, // Zones Loopback ...
3, // Zones Validation Length ...
0, // Count (All Zones) ...
100 // Loop back for Detection ...
);
bool hasCollectedZones = IsValidSize(collectedZonesCount) &&
collectedZonesCount > 1;
int affectedZonesCount = 0;
bool hasAffectedZone = false;
int collectedZonesBullishCount = 0;
int collectedZonesBearishCount = 0;
bool hasBullishAffectedZone = false;
bool hasBearishAffectedZone = false;
bool hasBullishCollectedZones = false;
bool hasBearishCollectedZones = false;
if (hasCollectedZones)
{
//
// Bullish ...
XClean(tmpZones);
collectedZonesBullishCount = ExtractByDirection(tmpZones, zones, X_DIRECTION_BULLISH);
hasBullishCollectedZones = IsValidSize(collectedZonesBullishCount);
//
// Bearish ...
XClean(tmpZones);
collectedZonesBearishCount = ExtractByDirection(tmpZones, zones, X_DIRECTION_BEARISH);
hasBearishCollectedZones = IsValidSize(collectedZonesBearishCount);
//
// Extract Affected Zones ...
XClean(tmpZones);
int affectedZonesCount = ExtractAffectedZones(p2Bar, zones, tmpZones);
int idx = GetYoungest(tmpZones);
if (IsValidIndex(idx))
{
affectedZone = tmpZones[idx];
}
hasAffectedZone = affectedZone.IsValid();
hasBullishAffectedZone = hasAffectedZone && affectedZone.IsBullish();
hasBearishAffectedZone = hasAffectedZone && affectedZone.IsBearish();
}
//
// Reading Cycle PVS ...
bool hasSCPV = poiDetector.GetSCZone(pBar, scPVZone);
@@ -2230,10 +2291,32 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
bool isP2BarPinnedBearish = isP2BarIsPinBar && IsXBearish(tmpDir);
//
// Checking ATR Box ...
bool hasATRBox = fimaParser.GetATRBox(
atrBox,
bar.Index() //
);
bool hasATRBoxBullish = hasATRBox && atrBox.IsBullish();
bool hasATRBoxBearish = hasATRBox && atrBox.IsBearish();
//
// Checking Double Patterns ...
ENUM_X_DIRECTION iDBDir;
XPatternAnalysis iPatterns;
XPatternAnalysis iPPatterns;
ENUM_X_BAR_PATTERN doublePatterns[];
GetCandlestickPatterns(doublePatterns);
bool hasDoublePatterns = poiDetector.HasDoublePatterns(
pBar,
iDBDir,
iPatterns,
iPPatterns,
doublePatterns,
iPatternsConfig,
5 //
);
bool hasBullishDoublePatterns = hasDoublePatterns && IsXBullish(iDBDir);
bool hasBearishDoublePatterns = hasDoublePatterns && IsXBearish(iDBDir);
//
isBullish =
@@ -2241,10 +2324,14 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
hasSupport &&
hasResistance &&
isCyclesBullish &&
hasATRBoxBullish &&
isCyclePVBullish &&
isP2BarPinnedBullish &&
hasBullishAffectedZone &&
isPBarHasBullishPatterns &&
hasBullishCollectedZones &&
isP2BarHasBullishPatterns &&
collectedZonesBullishCount > collectedZonesBearishCount &&
true
//
;
@@ -2255,10 +2342,14 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
hasSupport &&
hasResistance &&
isCyclesBearish &&
hasATRBoxBearish &&
isCyclePVBearish &&
isP2BarPinnedBearish &&
hasBearishAffectedZone &&
isPBarHasBearishPatterns &&
hasBearishCollectedZones &&
isP2BarHasBearishPatterns &&
collectedZonesBearishCount > collectedZonesBullishCount &&
true
//
;
@@ -2314,9 +2405,11 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
//
poiDrawer.DrawZone(pinBarZone, iConfig);
poiDrawer.DrawZone(affectedZone, iConfig);
poiDrawer.DrawTrendLine(pinBarZoneTrend, iConfig);
//
// poiDrawer.DrawZones(zones, iConfig);
poiDrawer.DrawZones(supports, iConfig);
poiDrawer.DrawZones(resistances, iConfig);
@@ -2326,6 +2419,14 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
poiDrawer.DrawZone(atrBox, iConfig);
}
//
if (hasDoublePatterns)
{
//
poiDrawer.DrawPatternAnalysis(iPatterns, iPatternsConfig);
poiDrawer.DrawPatternAnalysis(iPPatterns, iPatternsConfig);
}
//
iConfig.Clean();
iPatternsConfig.Clean();
@@ -2358,9 +2459,11 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
pBar.Clean();
p2Bar.Clean();
p3Bar.Clean();
XClean(zones);
tmpBar.Clean();
tmpZone.Clean();
XClean(supports);
XClean(tmpZones);
scPVZone.Clean();
mcPVZone.Clean();
lcPVZone.Clean();
@@ -488,6 +488,14 @@ class XCXFIMAPOIDetector : public XCMarketPatternDetector
return result;
}
/**
* Detect XPV Zone ...
*
* @param zone: XBoxZone, reference to Holds detected Zone ...
* @param barIndex: int, Specified Bar Index ...
*
* @return ( bool )
*/
bool DetectXPVZone(
XBoxZone &zone,
int barIndex = 0 //
@@ -1600,6 +1608,15 @@ class XCXFIMAPOIDetector : public XCMarketPatternDetector
return result;
}
/**
* Collect Specified ZOnes Boundary Min / Max Values ...
*
* @param uppers: XPivot, collection reference to holds Peaks of Zone's Boundary ...
* @param lowers: XPivot, collection reference to holds Vales of Zone's Boundary ...
* @param zone: XBoxZone, reference to Provide Specified Zone for Boundary Detection ...
*
* @return ( int )
*/
int CollectZonesBoundary(
XPivot &uppers[],
XPivot &lowers[],