add supports for Symbol Restrictions ...

This commit is contained in:
2025-05-09 03:43:56 +03:30
parent c7f14e90a1
commit 87c6321dcb
2 changed files with 506 additions and 72 deletions
+24 -31
View File
@@ -53,17 +53,19 @@ input double eaConstantBalance = 0.0; // Constant Ba
//
// Management ...
input group "Management";
input bool eaAllowTrade = true; // Allow Trade on Signals
input bool eaAllowLongs = true; // Allow Long Trades
input bool eaAllowShorts = true; // Allow Short Trades
input int eaMaxAllowedTradesPerDay = 3; // Max Allowed Trades per Day
input int eaMaxAllowedSLsPerDay = 2; // Max Allowed SL(s) per Day
input string eaSessionStartTime = ""; // Trade Start Time
input string eaSessionEndTime = ""; // Trade End Time
input int eaMaxAllowedPositions = 5; // Max Allowed Same Time Trades
input double eaMaxAllowedSpread = 25; // Max Allowed Spread For Trade
input double eaMaxAllowedDrawdownFactor = 0.3; // Max Allowed DrawDown for Trade
input string eaCloseAllOpenTradesAt = ""; // Close All Open Trades per Day At Specified Time
input bool eaAllowTrade = true; // Allow Trade on Signals
input bool eaAllowLongs = true; // Allow Long Trades
input bool eaAllowShorts = true; // Allow Short Trades
input ENUM_XCAEA_TRADE_RESTRICTION_PERIOD eaRestrictionsPeriod = XCAEA_TRADE_RESTRICATION_DAILY; // Trade Restrictions Period
input int eaMaxAllowedTPs = 2; // Max Allowed TP(s) per Day
input int eaMaxAllowedSLs = 2; // Max Allowed SL(s) per Day
input int eaMaxAllowedTrades = 3; // Max Allowed Trades per Day
input string eaSessionStartTime = ""; // Trade Start Time
input string eaSessionEndTime = ""; // Trade End Time
input int eaMaxAllowedPositions = 5; // Max Allowed Same Time Trades
input double eaMaxAllowedSpread = 25; // Max Allowed Spread For Trade
input double eaMaxAllowedDrawdownFactor = 0.3; // Max Allowed DrawDown for Trade
input string eaCloseAllOpenTradesAt = ""; // Close All Open Trades per Day At Specified Time
//
// Alert ...
@@ -662,13 +664,13 @@ void InitRequirements()
);
//
//
//
//
// eaMaxAllowedTradesPerDay
// eaMaxAllowedSLsPerDay
// eaSessionStartTime
// eaSessionEndTime
// Setting Trade Restrictions ...
eaTradeManager.SetTradeRestrictions(
eaRestrictionsPeriod,
eaMaxAllowedTPs,
eaMaxAllowedSLs,
eaMaxAllowedTrades //
);
//
// EA Signaller ...
@@ -711,23 +713,14 @@ void HandleTimeReport()
//
// Daily Report ....
bool isNewDay = eaTimeTracker.IsNewDay();
if (isNewDay)
if (eaReportNewDays &&
eaTimeTracker.IsNewDay())
{
//
// Handle New Day on Trade Manager ...
eaTradeManager.HandleNewDay();
string msg = "New Day ...";
//
// Reporting New Day if Reuired ...
if (eaReportNewDays)
{
//
string msg = "New Day ...";
//
eaAlert.Alert(msg);
}
eaAlert.Alert(msg);
}
//
+482 -41
View File
@@ -30,6 +30,29 @@
//
// Definitions ...
//
enum ENUM_XCAEA_TRADE_RESTRICTION_PERIOD
{
XCAEA_TRADE_RESTRICATION_NONE, // None
XCAEA_TRADE_RESTRICATION_HOURLY, // Per Hour
XCAEA_TRADE_RESTRICATION_DAILY, // Per Day
XCAEA_TRADE_RESTRICATION_WEEKLY, // Per Week
XCAEA_TRADE_RESTRICATION_MONTHLY, // Per Month
};
//
string ToString(ENUM_XCAEA_TRADE_RESTRICTION_PERIOD value)
{
//
string result = NULL;
//
result = EnumToString(value);
//
return result;
}
//
enum ENUM_XCAEA_TRADE_FINALIZATION
{
@@ -52,6 +75,95 @@ string ToString(ENUM_XCAEA_TRADE_FINALIZATION value)
return result;
}
//
struct XCAEASymbolInfo
{
//
string symbol;
//
int longs;
int shorts;
//
int trades;
//
int losses;
int profits;
//
int managedSLs;
int managedTPs;
int managedTrades;
//
// Constructor ...
XCAEASymbolInfo()
{
Clean();
}
//
// Tools ...
//
// Cleanup ...
void Clean()
{
//
symbol = NULL;
//
longs = 0;
shorts = 0;
//
trades = 0;
//
losses = 0;
profits = 0;
//
managedSLs = 0;
managedTPs = 0;
managedTrades = 0;
//
ZeroMemory(this);
}
//
// Validate ...
bool IsValid()
{
//
bool result = false;
//
result = IsValid(symbol);
//
return result;
}
//
bool IsSameAs(XCAEASymbolInfo &item)
{
//
bool result = false;
//
result = IsValid() &&
item.IsValid() &&
symbol == item.symbol;
//
return result;
}
};
//
struct XCAEATrade
{
@@ -305,6 +417,7 @@ class XCXCAEATradeManager : public XCBaseAlert
XCTrade *trader;
bool drawSignal;
XCPOIDrawer *drawer;
XTimeTracker timeTracker;
XCXCAEADataCollector *collector;
//
@@ -324,6 +437,12 @@ class XCXCAEATradeManager : public XCBaseAlert
allowLongs = true;
allowShorts = true;
//
maxAllowedTPs = 0;
maxAllowedSLs = 0;
maxAllowedTrades = 0;
restrictionsPeriod = XCAEA_TRADE_RESTRICATION_NONE;
//
reportTrades = true;
reportSignals = true;
@@ -352,6 +471,9 @@ class XCXCAEATradeManager : public XCBaseAlert
//
Clean(trades);
//
timeTracker.Clean();
//
ZeroMemory(trader);
ZeroMemory(drawer);
@@ -419,6 +541,27 @@ class XCXCAEATradeManager : public XCBaseAlert
allowShorts = _allowShorts;
}
//
void SetTradeRestrictions(
ENUM_XCAEA_TRADE_RESTRICTION_PERIOD _period,
int _maxAllowedTPs,
int _maxAllowedSLs,
int _maxAllowedTrades //
)
{
//
// Normalizing Args ...
_maxAllowedTPs = NormalizeInt(_maxAllowedTPs, 0);
_maxAllowedSLs = NormalizeInt(_maxAllowedSLs, 0);
_maxAllowedTrades = NormalizeInt(_maxAllowedTrades, 0);
//
restrictionsPeriod = _period;
maxAllowedTPs = _maxAllowedTPs;
maxAllowedSLs = _maxAllowedSLs;
maxAllowedTrades = _maxAllowedTrades;
}
//
// Tools ...
@@ -428,6 +571,11 @@ class XCXCAEATradeManager : public XCBaseAlert
void Manage()
{
//
// Handle Restrictions ...
HandleRestrictions();
//
// Check Contains Trades for Managing ...
bool has = HasChild(trades);
if (!has)
{
@@ -435,6 +583,7 @@ class XCXCAEATradeManager : public XCBaseAlert
}
//
// Update Required Infos of Trades ...
int count = ArraySize(trades);
for (int i = 0; i < count; i++)
{
@@ -464,7 +613,7 @@ class XCXCAEATradeManager : public XCBaseAlert
}
//
// After Update All Trades we can Do Protection ...
// Do Trade Protection ...
Protect();
}
@@ -823,13 +972,56 @@ class XCXCAEATradeManager : public XCBaseAlert
return result;
}
//
// Check Symbol Info Exists or not ...
int symbolIDX = -1;
bool isSymbolExists = FindSymbolIndex(
symbolIDX,
signal.symbol //
);
//
// TODO: Complete this ...
// Implementing Trade Session Validating ...
//
// TODO: Complete this ...
// Implementing Trade Permissions Based on SL(s) Count ...
bool hasRestrictions = restrictionsPeriod != XCAEA_TRADE_RESTRICATION_NONE;
if (hasRestrictions)
{
//
// Only Can Check Restrictions when
// Symbol Info Exists ...
if (isSymbolExists)
{
//
bool isTPAllowed = maxAllowedTPs == 0
? true
: symbols[symbolIDX].managedTPs < maxAllowedTPs;
bool isSLAllowed = maxAllowedSLs == 0
? true
: symbols[symbolIDX].managedSLs < maxAllowedSLs;
bool isTradeAllowed = maxAllowedTrades == 0
? true
: symbols[symbolIDX].managedTrades < maxAllowedTrades;
//
result = isTPAllowed &&
isSLAllowed &&
isTradeAllowed;
}
//
// Report Error ...
if (!result)
{
//
executionResult = X_SIGNAL_EXECUTION_FAILED_MAX_REACHED;
//
return result;
}
}
//
return result;
@@ -914,6 +1106,7 @@ class XCXCAEATradeManager : public XCBaseAlert
if (result)
{
//
// Draw Signal ...
if (drawSignal)
{
//
@@ -933,6 +1126,30 @@ class XCXCAEATradeManager : public XCBaseAlert
}
//
// Create Symbol Info Struct ...
XCAEASymbolInfo iSymbolInfo;
//
iSymbolInfo.trades = 1;
iSymbolInfo.managedTrades = 1;
iSymbolInfo.symbol = signal.symbol;
//
bool isLong = IsLong(signal.type);
if (isLong)
{
iSymbolInfo.longs = 1;
}
else
{
iSymbolInfo.shorts = 1;
}
//
AddOrUpdateSymbolInfo(iSymbolInfo);
//
// Create Trade Struct ...
XCAEATrade iTrade;
//
@@ -984,10 +1201,6 @@ class XCXCAEATradeManager : public XCBaseAlert
trades[idx].finalizedAt = TimeCurrent();
trades[idx].finalize = XCAEA_TRADE_FINAL_TP;
//
tpCount++;
managedTPCount++;
//
// Save Trade ...
Save(trades[idx]);
@@ -997,6 +1210,20 @@ class XCXCAEATradeManager : public XCBaseAlert
string prefix = "TP: " + ToString(trades[idx].profit);
HandleReportBalance(prefix);
//
// Handle Symbol Info ...
//
XCAEASymbolInfo iSymbolInfo;
//
iSymbolInfo.profits = 1;
iSymbolInfo.managedTPs = 1;
iSymbolInfo.symbol = trades[idx].signal.symbol;
//
AddOrUpdateSymbolInfo(iSymbolInfo);
//
RemoveTrade(idx);
}
@@ -1027,10 +1254,6 @@ class XCXCAEATradeManager : public XCBaseAlert
trades[idx].finalizedAt = TimeCurrent();
trades[idx].finalize = XCAEA_TRADE_FINAL_SL;
//
slCount++;
managedSLCount++;
//
// Save Trade ...
Save(trades[idx]);
@@ -1040,6 +1263,33 @@ class XCXCAEATradeManager : public XCBaseAlert
string prefix = "SL: " + ToString(trades[idx].profit);
HandleReportBalance(prefix);
//
// Handle Symbol Info ...
//
bool isInProfit = trades[idx].profit > 0;
//
XCAEASymbolInfo iSymbolInfo;
//
if (isInProfit)
{
//
iSymbolInfo.profits = 1;
iSymbolInfo.managedTPs = 1;
}
else
{
//
iSymbolInfo.losses = 1;
iSymbolInfo.managedSLs = 1;
}
iSymbolInfo.symbol = trades[idx].signal.symbol;
//
AddOrUpdateSymbolInfo(iSymbolInfo);
//
RemoveTrade(idx);
}
@@ -1076,20 +1326,6 @@ class XCXCAEATradeManager : public XCBaseAlert
? XCAEA_TRADE_FINAL_CLOSE_IN_PROFIT
: XCAEA_TRADE_FINAL_CLOSE_IN_LOSE;
//
if (isInProfit)
{
//
tpCount++;
managedTPCount++;
}
else
{
//
slCount++;
managedSLCount++;
}
//
// Save Trade ...
Save(trades[idx]);
@@ -1104,6 +1340,30 @@ class XCXCAEATradeManager : public XCBaseAlert
ToString(trades[idx].profit);
HandleReportBalance(prefix);
//
// Handle Symbol Info ...
//
XCAEASymbolInfo iSymbolInfo;
//
if (isInProfit)
{
//
iSymbolInfo.profits = 1;
iSymbolInfo.managedTPs = 1;
}
else
{
//
iSymbolInfo.losses = 1;
iSymbolInfo.managedSLs = 1;
}
iSymbolInfo.symbol = trades[idx].signal.symbol;
//
AddOrUpdateSymbolInfo(iSymbolInfo);
//
RemoveTrade(idx);
}
@@ -1114,15 +1374,6 @@ class XCXCAEATradeManager : public XCBaseAlert
{
}
/**
* Handle New Day ...
*/
void HandleNewDay()
{
//
// Clean Managed SL(s) and TP(s) and Positions ...
}
/**
* Find Executed Trade by Providing Position Ticket ...
*
@@ -1381,6 +1632,197 @@ class XCXCAEATradeManager : public XCBaseAlert
return result;
}
//
// Symbol Info ...
//
bool FindSymbolIndex(
int &index,
XCAEASymbolInfo &item //
)
{
//
bool result = false;
//
index = -1;
//
result = item.IsValid();
if (!result)
{
return result;
}
//
result = HasChild(symbols);
if (!result)
{
return result;
}
//
index = FindIndex(
item,
symbols //
);
//
result = IsValidIndex(index);
//
return result;
}
//
bool FindSymbolIndex(
int &index,
string symbol //
)
{
//
bool result = false;
//
index = -1;
//
result = IsValid(symbol) &&
HasChild(symbols);
if (!result)
{
return result;
}
//
int count = ArraySize(symbols);
for (int i = 0; i < count; i++)
{
//
result = symbols[i].symbol == symbol;
if (result)
{
//
index = i;
break;
}
}
//
result = IsValidIndex(index);
//
return result;
}
//
void AddOrUpdateSymbolInfo(XCAEASymbolInfo &item)
{
//
bool has = item.IsValid();
if (!has)
{
return;
}
//
int index = -1;
bool isExists = FindSymbolIndex(
index,
item //
);
if (!isExists)
{
//
AddRef(
item,
symbols //
);
}
else
{
//
symbols[index].longs += item.longs;
symbols[index].shorts += item.shorts;
symbols[index].trades += item.trades;
symbols[index].losses += item.losses;
symbols[index].profits += item.profits;
symbols[index].managedSLs += item.managedSLs;
symbols[index].managedTPs += item.managedTPs;
symbols[index].managedTrades += item.managedTrades;
}
}
//
void ResetSymbolsRestrictions()
{
//
bool has = HasChild(symbols);
if (has)
{
//
string prefix = "Protector: ";
//
int count = ArraySize(symbols);
for (int i = 0; i < count; i++)
{
//
symbols[i].managedSLs = 0;
symbols[i].managedTPs = 0;
symbols[i].managedTrades = 0;
}
//
string message = prefix + "Reset Symbols Restrictions";
HandleReportProtector(message);
}
}
//
void HandleRestrictions()
{
//
bool isNewDay = timeTracker.IsNewDay();
bool isNewHour = timeTracker.IsNewHour();
bool isNewWeek = timeTracker.IsNewWeek();
bool isNewMonth = timeTracker.IsNewMonth();
//
bool canResetRestrictions =
(
//
// Hourly ...
(isNewHour &&
restrictionsPeriod == XCAEA_TRADE_RESTRICATION_HOURLY)
//
||
//
// Daily ...
(isNewDay &&
restrictionsPeriod == XCAEA_TRADE_RESTRICATION_DAILY)
//
||
//
// Weekly ...
(isNewWeek &&
restrictionsPeriod == XCAEA_TRADE_RESTRICATION_WEEKLY)
//
||
//
// Monthly ...
(isNewMonth &&
restrictionsPeriod == XCAEA_TRADE_RESTRICATION_MONTHLY)
//
)
//
;
if (canResetRestrictions)
{
ResetSymbolsRestrictions();
}
}
//
// Private ...
private:
@@ -1392,17 +1834,15 @@ class XCXCAEATradeManager : public XCBaseAlert
bool allowLongs;
bool allowShorts;
//
int maxAllowedTPs;
int maxAllowedSLs;
int maxAllowedTrades;
ENUM_XCAEA_TRADE_RESTRICTION_PERIOD restrictionsPeriod;
//
bool mSaveTrades;
//
int slCount;
int tpCount;
//
int managedSLCount;
int managedTPCount;
//
bool reportTrades;
bool reportSignals;
@@ -1414,6 +1854,7 @@ class XCXCAEATradeManager : public XCBaseAlert
//
XCAEATrade trades[];
XCAEASymbolInfo symbols[];
};
//