add XTargetManager Class and use it in XBacktesterEA Class ...

also i have to implement it's usage on XCExpert Class ...
extends XTarget approaches and add support to Distances ...
This commit is contained in:
2025-10-01 17:16:13 +03:30
parent 684d3028c4
commit 2669790493
7 changed files with 1054 additions and 201 deletions
@@ -23,6 +23,7 @@
#include "../Classes/x-saherelm.base.class.mq5"
#include "../Classes/x-saherelm.x-alert.class.mq5"
#include "../Classes/x-saherelm.x-chart.helper.class.mq5"
#include "../Classes/x-saherelm.x-target.manager.class.mq5"
#include "../Classes/x-saherelm.x-trade.class.mq5"
#include "../Classes/x-saherelm.x-volume.class.mq5"
@@ -82,6 +83,9 @@ class XCBackTesterEA : public XCBase
//
XCAlert *eaAlert; // EA Scope Alert Handler ...
XCTrade *eaTrader; // EA Scope Trade Handler ...
XCTargetManager *eaTargetManager; // EA Scope Target Manager ...
//
XCChartHelper *eaChartHelper; // Chart Helper Class ...
//
@@ -273,6 +277,23 @@ class XCBackTesterEA : public XCBase
}
}
//
// Signal Executed Event Handlers ...
count = ArraySize(mOnSignalExecutedEventHandlers);
has = IsValidSize(count);
if (has)
{
//
for (int i = 0; i < count; i++)
{
eaTrader.AddOnSignalExecutedEventHandler(mOnSignalExecutedEventHandlers[i]);
}
}
//
// Init Target Managers ...
eaTargetManager = new XCTargetManager(eaTrader);
//
// Initial GUI ...
result = InitGUI();
@@ -294,6 +315,11 @@ class XCBackTesterEA : public XCBase
*/
void HandleOnDeInit()
{
//
eaTargetManager.Destroy();
delete eaTargetManager;
ZeroMemory(eaTargetManager);
//
delete eaTrader;
ZeroMemory(eaTrader);
@@ -326,7 +352,12 @@ class XCBackTesterEA : public XCBase
*/
void HandleOnTick()
{
//
UpdateGUI();
//
// Managing Targets ...
eaTargetManager.Manage();
}
/**
@@ -395,6 +426,9 @@ class XCBackTesterEA : public XCBase
//
// Update Position Buttons ...
UpdatePositionButtons();
//
eaTargetManager.HandleOnStopLossTriggered(deal);
}
/**
@@ -407,6 +441,9 @@ class XCBackTesterEA : public XCBase
//
// Update Position Buttons ...
UpdatePositionButtons();
//
eaTargetManager.HandleOnTakeProfitTriggered(deal);
}
/**
@@ -425,6 +462,13 @@ class XCBackTesterEA : public XCBase
//
// Update Position Buttons ...
UpdatePositionButtons();
//
eaTargetManager.HandleOnPositionForceClosed(
ticket,
position,
comment //
);
}
/**
@@ -502,6 +546,34 @@ class XCBackTesterEA : public XCBase
{
}
/**
* Handle New Signal Recieved ...
*
* @param signal: XSignal, reference to recieved Signal ...
*/
void HandleOnSignalTriggered(XSignal &signal)
{
//
ENUM_X_SIGNAL_EXECUTION_RESULT result;
bool isExcuted = eaTrader.ExecuteSignal(
signal,
result //
);
if (isExcuted)
{
}
}
/**
* Handle Signal Executed Event ...
*
* @param signal: XSignal, reference to Executed Signal ...
*/
void HandleOnSignalExecuted(XSignal &signal)
{
eaTargetManager.AddExecutedSignal(signal);
}
//
// Props and Setter / Getter (s) ...
@@ -652,6 +724,23 @@ class XCBackTesterEA : public XCBase
);
}
//
// Add New Signal Executed Event Handler ...
void AddOnSignalExecutedEventHandler(TOnSignal handler)
{
//
if (handler == NULL)
{
return;
}
//
Add(
handler,
mOnSignalExecutedEventHandlers //
);
}
//
// Protected ...
protected:
@@ -667,6 +756,7 @@ class XCBackTesterEA : public XCBase
TOnStopLoss mStopLossEventHandlers[];
TOnTakeProfit mTakeProfitEventHandlers[];
TOnForceClose mOnForceCloseEventHandlers[];
TOnSignal mOnSignalExecutedEventHandlers[];
TOnDealsChanged mDealsChangedEventHandlers[];
TOnOrdersChanged mOrdersChangedEventHandlers[];
TOnPartialClose mOnPartialCloseEventHandlers[];
@@ -0,0 +1,620 @@
///////////////////////////////////////////////////////
//
// SaherElm IT Center MQL5 Class Library
// ----------------------------------------------
// Name: XCTargetManager
// Description: provides all Positions Target requirements ...
//
//
// Maintainer:
// ------------
// Hadi Khazaee Asl (hadi_khazaee_asl@yahoo.com)
//
//////////////////////////////////////////////////////
//
// Global Properties ...
#property library
#property copyright "Copyright 2023, SaherElm IT Center"
#property link "https://www.saherelm.ir"
#property version "1.00"
#property strict
//
// Imports ...
#include "../Classes/x-saherelm.base.class.mq5"
#include "../Classes/x-saherelm.x-trade.class.mq5"
//
// Implementation ...
class XCTargetManager : public XCBase
{
//
// Public ...
public:
//
XCTrade *trader;
XSignal signals[];
//
// Constructor ...
XCTargetManager(
XCTrade *_trader //
) : XCBase()
{
//
trader = _trader;
XClean(signals);
}
//
// Deconstructor ...
~XCTargetManager()
{
Destroy();
}
//
void Destroy()
{
//
XClean(signals);
}
//
// Actions ...
/**
* Manage Positions ...
*
* @param barIndex: int, Bar Index ...
*/
void Manage(int barIndex = 0)
{
//
// Normalize ...
barIndex = NormalizeInt(barIndex, 0);
//
// Extract In Profit Positions ...
XPosition positions[];
int count = GetInProfitPositions(positions);
bool has = IsValidIndex(count);
if (!has)
{
return;
}
//
XSignal iSignal;
XTarget iTarget;
int signalIDX = -1;
int targetIDX = -1;
XPosition iPosition;
//
// Loop through Positions ...
for (int i = 0; i < count; i++)
{
//
// Select Positions ...
iPosition = positions[i];
has = FindSignal(
signalIDX,
iPosition.ticket //
);
if (!has)
{
continue;
}
iSignal = signals[signalIDX];
//
// Selecting Target ...
targetIDX = iSignal.appliedTargetIDX;
if (iSignal.isTargetApplied)
{
targetIDX++;
}
//
// Validate Targets Size ...
has = HasChild(iSignal.targets) &&
targetIDX < ArraySize(iSignal.targets);
if (has)
{
//
// Select Target ...
iTarget = iSignal.targets[targetIDX];
//
// Check Can Apply Target and Apply it ...
has = HandleApplyTarget(iTarget, iPosition);
if (has)
{
//
// Update Target IDX ...
iSignal.appliedTargetIDX++;
}
}
//
// Update Signal ...
signals[signalIDX] = iSignal;
//
// Cleanup ...
iSignal.Clean();
iTarget.Clean();
iPosition.Clean();
}
//
// Cleanup Resources ...
iSignal.Clean();
iTarget.Clean();
iPosition.Clean();
}
/**
* Extract in Profit Positions ...
*
* @param positions: XPosition, reference collection to holds result ...
*
* @return ( int )
*/
int GetInProfitPositions(
XPosition &positions[] //
)
{
//
int result = 0;
//
// Prepare ...
XClean(positions);
//
// Validate ...
if (trader == NULL)
{
return result;
}
//
result = trader.GetInProfitPositions(
positions,
NULL, // All Symbols ...
NULL, // All Providers ...
NULL, // All Periods ...
NULL, // All Position Types ...
X_POSITION_SELECT_ALL, // Select Method ...
true, // Filter by Magic ...
true // Force Clean ...
);
if (IsValidSize(result))
{
//
XPosition iPos;
XPosition tmp[];
Copy(
positions,
tmp //
);
XClean(positions);
while (HasChild(tmp))
{
//
iPos = tmp[0];
ArrayRemove(
tmp,
0,
1 //
);
//
int idx = -1;
bool has = FindSignal(
idx,
iPos.ticket //
);
if (has)
{
//
AddRef(
iPos,
positions //
);
}
}
//
XClean(tmp);
iPos.Clean();
//
result = ArraySize(positions);
}
//
return result;
}
/**
* Add Executed Signal ...
*
* @param signal: XSignal, reference to Executed Signal ...
*/
void AddExecutedSignal(XSignal &signal)
{
//
// Validate ...
if (!signal.IsValid() || !signal.IsExecuted())
{
return;
}
//
AddRef(
signal,
signals //
);
}
//
// Trade Event Handlers ...
/**
* Handle Stop Loss Event Triggered ...
*
* @param deal: XDeal instance refrence, provides Triggered Deal info ...
*/
void HandleOnStopLossTriggered(const XDeal &deal)
{
RemoveSignal(deal.positionId);
}
/**
* Handle Take Profit Event Triggered ...
*
* @param deal: XDeal instance refrence, provides Triggered Deal info ...
*/
void HandleOnTakeProfitTriggered(const XDeal &deal)
{
RemoveSignal(deal.positionId);
}
/**
* Handle Position Force Closed Event ...
*
* @param ticket: ulong, triggered Positions ticket ...
* @param position: XPosition instance refrence, Triggered Position ...
* @param comment: string, Comment ...
*/
void HandleOnPositionForceClosed(
const ulong ticket,
const XPosition &position,
const string comment //
)
{
RemoveSignal(ticket);
}
//
// Event Handlers Registration ...
//
void AddOnStopLossEventHandler(TOnStopLoss handler)
{
//
if (handler == NULL)
{
return;
}
//
Add(
handler,
mStopLossEventHandlers
//
);
}
//
void AddOnTakeProfitEventHandler(TOnTakeProfit handler)
{
//
if (handler == NULL)
{
return;
}
//
Add(
handler,
mTakeProfitEventHandlers
//
);
}
//
void AddOnForceClosePositionEventHandler(TOnForceClose handler)
{
//
if (handler == NULL)
{
return;
}
//
Add(
handler,
mOnForceCloseEventHandlers
//
);
}
//
// Protected ...
protected:
//
/**
* Find Specified Signal ...
*
* @param index: int, reference to holds detected index ...
* @param signal: XSignal, reference to Specified Signal ...
*
* @return ( bool )
*/
bool FindSignal(
int &index,
XSignal &signal //
)
{
//
bool result = false;
//
// Prepare ...
index = -1;
//
// Validate ...
result = signal.IsValid() &&
HasChild(signals);
if (!result)
{
return result;
}
//
// Looping Through Signals ...
int count = ArraySize(signals);
for (int i = 0; i < count; i++)
{
//
result = signals[i]
.IsSameAs(signal);
if (result)
{
//
index = i;
break;
}
}
//
result = IsValidIndex(index);
//
return result;
}
/**
* Find Specified Signal ...
*
* @param index: int, reference to holds detected index ...
* @param ticket: ulong, Specified Signal Position ID ...
*
* @return ( bool )
*/
bool FindSignal(
int &index,
ulong ticket //
)
{
//
bool result = false;
//
// Prepare ...
index = -1;
//
// Validate ...
result = NotEmptyZero(ticket) &&
HasChild(signals);
if (!result)
{
return result;
}
//
// Looping Through Signals ...
int count = ArraySize(signals);
for (int i = 0; i < count; i++)
{
//
result = signals[i].IsValid() &&
signals[i].IsExecuted() &&
signals[i].positionId == ticket;
if (result)
{
//
index = i;
break;
}
}
//
result = IsValidIndex(index);
//
return result;
}
/**
* Remove Specified Signal ...
*
* @param ticket: ulong, Specified Ticket ...
*/
void RemoveSignal(ulong ticket)
{
//
bool has = NotEmptyZero(ticket) &&
HasChild(signals);
if (!has)
{
return;
}
//
int idx = -1;
has = FindSignal(
idx,
ticket //
);
if (!has)
{
return;
}
//
ArrayRemove(
signals,
idx,
1 //
);
}
/**
* Check Can Apply Specified Target on Specified Position or not ...
*
* @param target: XTarget, reference to Specified Target for Apply ...
* @param position: XPosition, reference to Specified Position ...
*
* @return ( bool )
*/
bool CanApplyTarget(
XTarget &target,
XPosition &position //
)
{
//
bool result = false;
//
// Validate ...
result =
target.IsValid() &&
position.IsValid();
if (!result)
{
return result;
}
//
// Check Price Reached Targets Value and Distance ...
double targetDistance = (target.actingDistance > 0 ? target.actingDistance : 0) * position.GetPointsValue();
result =
IsLong(position.type)
? position.price >= target.target + targetDistance
: position.price <= target.target - targetDistance;
//
return result;
}
/**
* Apply Specified Target on Specified Position ...
*
* @param target: XTarget, reference to Specified Target for Apply ...
* @param position: XPosition, reference to Specified Position ...
*
* @return ( bool )
*/
bool HandleApplyTarget(
XTarget &target,
XPosition &position //
)
{
//
bool result = false;
//
// Validate ...
result =
target.IsValid() &&
position.IsValid() &&
CanApplyTarget(
target,
position //
);
if (!result)
{
return result;
}
//
// Apply Target ...
string comment = NULL;
//
// Do Risk Free if Provided ...
if (target.doRF)
{
//
comment = "Taregt Manager do RF ...";
result = trader.Modify(
position.ticket,
target.target, // SL ...
position.tp, // TP ...
comment //
);
}
//
// Do Partial Close if Provided ...
if (result && target.volumeMultiplier > 0)
{
//
double volume = NormalizeVolume((position.volume * target.volumeMultiplier), position.symbol);
if (volume != position.volume)
{
//
comment = "Target Manager do Partial Close ...";
result = trader.ClosePartial(
position.ticket,
volume,
comment //
);
}
}
//
return result;
}
//
// Private ...
private:
//
//
// Required Event Handlers ...
TOnStopLoss mStopLossEventHandlers[];
TOnTakeProfit mTakeProfitEventHandlers[];
TOnForceClose mOnForceCloseEventHandlers[];
};
//
+50 -3
View File
@@ -814,6 +814,23 @@ class XCTrade : public XCBase
);
}
//
// Add New Signal Executed Event Handler ...
void AddOnSignalExecutedEventHandler(TOnSignal handler)
{
//
if (handler == NULL)
{
return;
}
//
Add(
handler,
mOnSignalExecutedEventHandlers //
);
}
//
// Functions ...
@@ -1355,11 +1372,10 @@ class XCTrade : public XCBase
mSignal.positionId = ticket;
//
// Handle Store XPositionInfo ...
// Notify Signal Execution ...
if (mSignal.mode == X_ORDER_MODE_MARKET)
{
//
// TODO: Implement this ...
NotifySignalExecuted(mSignal);
}
}
@@ -3568,6 +3584,33 @@ class XCTrade : public XCBase
}
}
//
void NotifySignalExecuted(XSignal &signal)
{
//
bool has = signal.IsValid() &&
signal.IsExecuted();
if (!has)
{
return;
}
//
int count = ArraySize(mOnSignalExecutedEventHandlers);
if (count <= 0)
{
return;
}
//
for (int i = 0; i < count; i++)
{
//
TOnSignal iHandler = mOnSignalExecutedEventHandlers[i];
iHandler(signal);
}
}
//
// Tools ...
@@ -3728,6 +3771,10 @@ class XCTrade : public XCBase
// Trade State Changed Event Handlers ...
TOnTradeStateChanged mTradeStateChangedEventHandlers[];
//
// Signal Executed Event Handlers ...
TOnSignal mOnSignalExecutedEventHandlers[];
//
TOnModify mOnModifyEventHandlers[];
TOnForceClose mOnForceCloseEventHandlers[];
+113
View File
@@ -1274,3 +1274,116 @@ void OnTick()
//
cBar.Clean();
}
//
void AnalyseMarket(int barIndex = 0)
{
//
bool has = false;
//
barIndex = NormalizeInt(barIndex, 0);
//
string symbol = fima1Signaller.symbol;
ENUM_TIMEFRAMES period = fima1Signaller.period;
//
// Retrieve Signal Bar ...
XOHCL bar;
has = bar.Init(
symbol,
period,
barIndex //
);
if (!has)
{
//
bar.Clean();
return;
}
//
// TODO: Remove this and add in OnInit() Method ...
//
// Configuring Detector ...
//
detectorConfig.detectSwingTrend = true;
//
detectorConfig.detectPinned = true;
detectorConfig.detectMomentum = true;
detectorConfig.detectEngulfed = true;
detectorConfig.detectTrueGaped = true;
//
detectorConfig.detectStarPattern = true;
detectorConfig.detectFlagPattern = true;
detectorConfig.detectRisingPattern = true;
detectorConfig.detectPiercingPattern = true;
detectorConfig.detectSignalKeyBarPattern = true;
//
detectorConfig.analyseFIMAPVPivots = true;
detectorConfig.analyseFIMAZigZagPivots = true;
//
// Configure Drawer ...
//
marketStructureDrawerConfig.drawOB = false;
marketStructureDrawerConfig.drawFVG = false;
//
marketStructureDrawerConfig.drawPinned = false;
marketStructureDrawerConfig.drawEngulfed = true;
marketStructureDrawerConfig.drawTrueGaped = false;
marketStructureDrawerConfig.drawMomentum = false;
marketStructureDrawerConfig.drawFlagPattern = false;
marketStructureDrawerConfig.drawStarPattern = false;
marketStructureDrawerConfig.drawRisingPattern = false;
marketStructureDrawerConfig.drawPiercingPattern = false;
marketStructureDrawerConfig.drawSignalKeyBarPattern = true;
//
// Recents ...
marketStructureDrawerConfig.drawRecentPatterns = false;
marketStructureDrawerConfig.drawFakeBreakedZone = false;
marketStructureDrawerConfig.drawRecentlyTestedZones = false;
marketStructureDrawerConfig.drawRecentlyBreakedZones = false;
//
// XPV ...
marketStructureDrawerConfig.drawFIMAPVPivotsAnalysis = true;
marketStructureDrawerConfig.drawFIMAPVPivotsAnalysisZones = true;
marketStructureDrawerConfig.drawFIMAPVPivotsAnalysisTrends = true;
marketStructureDrawerConfig.drawFIMAPVPivotsAnalysisPivots = true;
//
// XSAR ...
marketStructureDrawerConfig.drawFIMASARPivotsAnalysis = false;
marketStructureDrawerConfig.drawFIMASARPivotsAnalysisZones = false;
marketStructureDrawerConfig.drawFIMASARPivotsAnalysisTrends = false;
marketStructureDrawerConfig.drawFIMASARPivotsAnalysisPivots = false;
//
// XZigZag ...
marketStructureDrawerConfig.drawFIMAZigZagPivotsAnalysis = true;
marketStructureDrawerConfig.drawFIMAZigZagPivotsAnalysisZones = true;
marketStructureDrawerConfig.drawFIMAZigZagPivotsAnalysisTrends = false;
marketStructureDrawerConfig.drawFIMAZigZagPivotsAnalysisPivots = false;
//
// Analyse Market on Signalling Bar ...
fima1Signaller.poiDetector.AnalyseMarket(
bar,
marketStructure,
detectorConfig //
);
//
bar.Clean();
}
+12 -180
View File
@@ -228,6 +228,7 @@ int OnInit()
eaExpert.AddOnDealsChangedEventHandler(OnDealsChanged);
eaExpert.AddOnStopLossEventHandler(OnStopLossTriggered);
eaExpert.AddOnOrdersChangedEventHandler(OnOrdersChanged);
eaExpert.AddOnSignalExecutedEventHandler(OnSignalExecuted);
eaExpert.AddOnTakeProfitEventHandler(OnTakeProfitTriggered);
eaExpert.AddOnModifyPositionEventHandler(OnPositionModified);
eaExpert.AddOnPositionsChangedEventHandler(OnPositionsChanged);
@@ -440,10 +441,8 @@ void OnTick()
int barIndex = 1;
//
// Signallers Calling OnTick ...
fima1Signaller.OnTick(barIndex);
//
// AnalyseMarket(barIndex);
}
//
@@ -590,17 +589,6 @@ void DestroyTimer()
*/
void OnSignalTriggered(XSignal &signal)
{
//
// Validate Signal ...
if (!signal.IsValid())
{
return;
}
//
// TODO: Fix this ...
// return;
//
// Draw Signal on Chart ...
XCSignalObject *iSignalObj;
@@ -611,60 +599,17 @@ void OnSignalTriggered(XSignal &signal)
);
//
if (has)
{
//
ENUM_X_SIGNAL_EXECUTION_RESULT result;
eaExpert.eaTrader.ExecuteSignal(
signal,
result //
);
eaExpert.HandleOnSignalTriggered(signal);
}
//
Print("Signal Issued: ", signal.GetObjectID());
}
//
// Try to Execute Signal ...
//
// Draw Signal Vertical Line ...
// //
// CChartObjectVLine *iObj = new CChartObjectVLine();
// //
// string iName = signal.GetObjectID();
// color iColor = IsLong(signal.type) ? clrLime : clrRed;
// //
// bool has = iObj.Create(
// fima2Signaller.poiDrawer.ChartIdentification(),
// iName,
// fima2Signaller.poiDrawer.SubWindowIdentification(),
// signal.time //
// );
// if (has)
// {
// //
// iObj.Width(2);
// iObj.Color(iColor);
// //
// // eaDraws.Add(iObj);
// }
// //
// // Alert Issued Signal ...
// string message = signal.GetMessage();
//
// int signalBarIndex = GetBarIndex(
// signal.symbol,
// signal.period,
// signal.time //
// );
// AnalyseMarket(signalBarIndex);
/**
* Trigger OnSignal Executed Event ...
*
* @param signal: XSignal
*/
void OnSignalExecuted(XSignal &signal)
{
eaExpert.HandleOnSignalExecuted(signal);
}
//
@@ -794,116 +739,3 @@ void OnTradeStateChanged(const XOnTradeHandlerState &state)
}
//
void AnalyseMarket(int barIndex = 0)
{
//
bool has = false;
//
barIndex = NormalizeInt(barIndex, 0);
//
string symbol = fima1Signaller.symbol;
ENUM_TIMEFRAMES period = fima1Signaller.period;
//
// Retrieve Signal Bar ...
XOHCL bar;
has = bar.Init(
symbol,
period,
barIndex //
);
if (!has)
{
//
bar.Clean();
return;
}
//
// TODO: Remove this and add in OnInit() Method ...
//
// Configuring Detector ...
//
detectorConfig.detectSwingTrend = true;
//
detectorConfig.detectPinned = true;
detectorConfig.detectMomentum = true;
detectorConfig.detectEngulfed = true;
detectorConfig.detectTrueGaped = true;
//
detectorConfig.detectStarPattern = true;
detectorConfig.detectFlagPattern = true;
detectorConfig.detectRisingPattern = true;
detectorConfig.detectPiercingPattern = true;
detectorConfig.detectSignalKeyBarPattern = true;
//
detectorConfig.analyseFIMAPVPivots = true;
detectorConfig.analyseFIMAZigZagPivots = true;
//
// Configure Drawer ...
//
marketStructureDrawerConfig.drawOB = false;
marketStructureDrawerConfig.drawFVG = false;
//
marketStructureDrawerConfig.drawPinned = false;
marketStructureDrawerConfig.drawEngulfed = true;
marketStructureDrawerConfig.drawTrueGaped = false;
marketStructureDrawerConfig.drawMomentum = false;
marketStructureDrawerConfig.drawFlagPattern = false;
marketStructureDrawerConfig.drawStarPattern = false;
marketStructureDrawerConfig.drawRisingPattern = false;
marketStructureDrawerConfig.drawPiercingPattern = false;
marketStructureDrawerConfig.drawSignalKeyBarPattern = true;
//
// Recents ...
marketStructureDrawerConfig.drawRecentPatterns = false;
marketStructureDrawerConfig.drawFakeBreakedZone = false;
marketStructureDrawerConfig.drawRecentlyTestedZones = false;
marketStructureDrawerConfig.drawRecentlyBreakedZones = false;
//
// XPV ...
marketStructureDrawerConfig.drawFIMAPVPivotsAnalysis = true;
marketStructureDrawerConfig.drawFIMAPVPivotsAnalysisZones = true;
marketStructureDrawerConfig.drawFIMAPVPivotsAnalysisTrends = true;
marketStructureDrawerConfig.drawFIMAPVPivotsAnalysisPivots = true;
//
// XSAR ...
marketStructureDrawerConfig.drawFIMASARPivotsAnalysis = false;
marketStructureDrawerConfig.drawFIMASARPivotsAnalysisZones = false;
marketStructureDrawerConfig.drawFIMASARPivotsAnalysisTrends = false;
marketStructureDrawerConfig.drawFIMASARPivotsAnalysisPivots = false;
//
// XZigZag ...
marketStructureDrawerConfig.drawFIMAZigZagPivotsAnalysis = true;
marketStructureDrawerConfig.drawFIMAZigZagPivotsAnalysisZones = true;
marketStructureDrawerConfig.drawFIMAZigZagPivotsAnalysisTrends = false;
marketStructureDrawerConfig.drawFIMAZigZagPivotsAnalysisPivots = false;
//
// Analyse Market on Signalling Bar ...
fima1Signaller.poiDetector.AnalyseMarket(
bar,
marketStructure,
detectorConfig //
);
//
bar.Clean();
}
//
+41
View File
@@ -719,6 +719,7 @@ struct XTarget
//
// Props ...
bool doRF; // Do RF on Target
double actingDistance; // Acting Distances
double target; // Target Price for Actions
double volumeMultiplier; // Volume Multiplier for Partial Close
@@ -739,6 +740,7 @@ struct XTarget
//
target = 0;
doRF = false;
actingDistance = 0;
volumeMultiplier = 0;
}
@@ -5688,6 +5690,45 @@ void ApplyTargetsOnSignal(
targets //
);
//
// Compare TP with Targets ...
int idx = IsLong(signal.type)
? GetHighest(targets)
: GetLowest(targets);
has = IsValidIndex(idx);
if (has)
{
//
// Compare TP ...
has = IsLong(signal.type)
? targets[idx].target > signal.tp
: targets[idx].target < signal.tp;
if (has)
{
//
XTarget tpTarget;
tpTarget = targets[idx];
tpTarget.target = signal.tp;
signal.tp = targets[idx].target;
ArrayRemove(
targets,
idx,
1 //
);
AddRef(
tpTarget,
targets //
);
}
//
// Sort Targets ...
ApplySortOnTargets(
sortingDir,
targets //
);
}
//
Copy(
targets,
@@ -804,22 +804,6 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
);
}
//
CArrayObj *zoneObjs;
poiDrawer.DrawBoxes(
supports,
zoneObjs //
);
poiDrawer.DrawBoxes(
resistances,
zoneObjs //
);
poiDrawer.DrawBoxes(
structure.fvgs,
zoneObjs,
false //
);
//
// Check Affected Zone ...
// Select a Support or Resistance ...
@@ -878,6 +862,132 @@ class XCXFIMAStrategy1Signaller : public XCXFIMABaseSignaller
//
// Check Reversal FVGS ...
int idx = -1;
XTarget target;
XBoxZone targetZones[];
int numberOfTargets = 3;
double actingDistance = 20;
double iValue = EMPTY_VALUE;
bool ignoreFirstTarget = true;
ENUM_X_DIRECTION targetsDir = Opposit(dir);
int count = ExtractByDirection(
targetZones,
structure.fvgs,
targetsDir //
);
bool has = IsValidSize(count);
if (has)
{
//
// Calculate Value ...
double points = GetPoints(zone.symbol);
double zoneRange = zone.upper - zone.lower;
iValue = IsXBullish(dir)
? (zone.upper + (zoneRange * defaultSignalR2R))
: (zone.lower + (zoneRange * defaultSignalR2R));
double defaultTarget = iValue;
//
// Looping Back ...
for (int i = 0; i < numberOfTargets; i++)
{
//
// Detect Lowest Above Zone ...
if (IsXBullish(dir))
{
//
idx = GetLowestAbove(iValue, targetZones);
has = IsValidIndex(idx);
if (!has)
{
break;
}
//
iValue = targetZones[idx].lower;
}
//
// Detect Highest below Zone ...
else if (IsXBearish(dir))
{
//
idx = GetHighestBelow(iValue, targetZones);
has = IsValidIndex(idx);
if (!has)
{
break;
}
//
iValue = targetZones[idx].upper;
}
//
// Validate Target Value ...
has = NotEmptyZero(iValue) &&
iValue != defaultTarget;
if (has)
{
//
// Init Target ...
target.Clean();
target.doRF = true;
target.target = iValue;
target.actingDistance = actingDistance;
has = target.IsValid();
if (has)
{
//
// Add Target to Targets ...
AddRef(
target,
targets //
);
}
target.Clean();
}
}
//
// Remove Nearest ...
has = ignoreFirstTarget &&
HasChild(targets);
if (has)
{
//
ArrayRemove(
targets,
0,
1 //
);
}
}
//
// Cleanup Resources ...
target.Clean();
XClean(targetZones);
}
//
// TODO: Remove this ...
if (result)
{
//
CArrayObj *zoneObjs;
poiDrawer.DrawBoxes(
supports,
zoneObjs //
);
poiDrawer.DrawBoxes(
resistances,
zoneObjs //
);
poiDrawer.DrawBoxes(
structure.fvgs,
zoneObjs,
false //
);
}
//