This commit is contained in:
2024-06-26 18:04:28 +03:30
parent 2e365b2bc2
commit f048bd3d37
4 changed files with 814 additions and 165 deletions
+303 -135
View File
@@ -298,7 +298,29 @@ struct XTradeInfo
}
//
string ToString()
string GetSignalFileName()
{
//
string result = NULL;
//
result =
//
symbol + "\\" +
ToString(type) + "\\" +
provider + "_" +
ToFormatString(time)
//
;
//
return result;
}
//
string ToString(
bool onlySignals = false //
)
{
//
string result = NULL;
@@ -346,7 +368,9 @@ struct XTradeInfo
//
result =
//
ToString("Ticket", ticket) +
(onlySignals
? ""
: ToString("Ticket", ticket)) +
ToString("Symbol", symbol) +
ToString("Period", period) +
ToString("Entry", entry) +
@@ -354,14 +378,16 @@ struct XTradeInfo
ToString("Type", ToString(type)) +
ToString("Time", time) +
ToString("Pushers", pushers) +
"-------------" + "\n" +
ToString("Volume", volume) +
ToString("Profit", profit) +
ToString("Commission", commission) +
ToString("Swap", swap) +
ToString("End Time", endTime) +
ToString("Age", age) +
ToString("Message", message) +
(onlySignals
? ""
: "-------------" + "\n" +
ToString("Volume", volume) +
ToString("Profit", profit) +
ToString("Commission", commission) +
ToString("Swap", swap) +
ToString("End Time", endTime) +
ToString("Age", age) +
ToString("Message", message)) +
"-------------" + "\n" +
"Conditions" + "\n" +
"-------------" + "\n" +
@@ -932,6 +958,37 @@ public:
return result;
}
//
bool SaveSignal(XTradeInfo &item)
{
//
bool result = false;
//
string content = item.ToString();
result = IsValid(content);
if (!result)
{
return result;
}
//
int mHandler = GetSignalFileHandlerForWrite(item);
result = mHandler != INVALID_HANDLE;
if (!result)
{
return result;
}
//
FileWrite(mHandler, content);
FileFlush(mHandler);
FileClose(mHandler);
//
return result;
}
//
// Protected ...
protected:
@@ -964,7 +1021,32 @@ private:
//
result =
//
mPath + "\\" + fileName + ".x121.log"
mPath + "\\" + "Trades" + "\\" + fileName + ".x121.log"
//
;
//
return result;
}
//
string GetSignalFilePath(XTradeInfo &item)
{
//
string fileName = item.GetSignalFileName();
//
return GetSignalFilePath(fileName);
}
string GetSignalFilePath(string fileName)
{
//
string result = "";
//
result =
//
mPath + "\\" + "Signals" + "\\" + fileName + ".x121.log"
//
;
@@ -1015,6 +1097,50 @@ private:
//
return result;
}
//
int GetSignalFileHandlerForRead(XTradeInfo &item)
{
//
int result = INVALID_HANDLE;
//
string filePath = GetSignalFilePath(item);
if (!IsValid(filePath))
{
return result;
}
//
result = FileOpen(
filePath,
FILE_READ | FILE_TXT //
);
//
return result;
}
int GetSignalFileHandlerForWrite(XTradeInfo &item)
{
//
int result = INVALID_HANDLE;
//
string filePath = GetSignalFilePath(item);
if (!IsValid(filePath))
{
return result;
}
//
result = FileOpen(
filePath,
FILE_READ | FILE_WRITE | FILE_TXT //
);
//
return result;
}
};
//
@@ -1063,6 +1189,65 @@ public:
mSave = value;
}
//
bool GetSaveSignalsOnly()
{
return mSaveSignalsOnly;
}
//
void SetSaveSignalsOnly(bool value)
{
mSaveSignalsOnly = value;
}
//
// Hedging ...
//
double MinProfitPerTrade()
{
return mMinProfitPerTrade;
}
//
void MinProfitPerTrade(double value)
{
//
if (value < 0)
{
value = 0;
}
//
mMinProfitPerTrade = value;
}
//
double MinProfitPerVolumeFactor()
{
return mMinProfitPerVolumeFactor;
}
//
void MinProfitPerVolumeFactor(double value)
{
//
if (value < 0)
{
value = 0;
}
//
if (value > 0 && value < 0.01)
{
value = 0.01;
}
//
mMinProfitPerVolumeFactor = value;
}
//
// Trailling Stop ...
@@ -1684,6 +1869,12 @@ public:
info,
data //
);
//
if (GetSaveSignalsOnly())
{
collector.SaveSignal(info);
}
}
//
@@ -2162,7 +2353,13 @@ protected:
XTradeInfoCollector *collector;
//
bool mSave; // Save Results ...
bool mSave; // Save Results ...
bool mSaveSignalsOnly; // Save Only Signals and COnditions
//
// Hedging ...
double mMinProfitPerTrade; // Minimum Required Profit for Hedging
double mMinProfitPerVolumeFactor; // Minimum Required Profit for Hedging Per Volume
//
// Trailling ...
@@ -3497,6 +3694,18 @@ public:
mTradeHandler.SetSave(value);
}
//
bool SaveSignalsOnly()
{
return mTradeHandler.GetSaveSignalsOnly();
}
//
void SaveSignalsOnly(bool value)
{
mTradeHandler.SetSaveSignalsOnly(value);
}
//
double MinFreeMargingForOpenTrades()
{
@@ -3516,6 +3725,37 @@ public:
mMinFreeMargingForOpenTrades = value;
}
//
// Hedging ...
//
double MinProfitPerTrade()
{
return mTradeHandler.MinProfitPerTrade();
}
//
void MinProfitPerTrade(double value)
{
//
MinRequiredProfitPerTrade(value);
mTradeHandler.MinProfitPerTrade(value);
}
//
double MinProfitPerVolumeFactor()
{
return mTradeHandler.MinProfitPerVolumeFactor();
}
//
void MinProfitPerVolumeFactor(double value)
{
//
MinRequiredProfitPerVolumeFactor(value);
mTradeHandler.MinProfitPerVolumeFactor(value);
}
//
// Overrides ...
@@ -4384,7 +4624,7 @@ public:
bool HandleStateManagement(XSignal &signals[]) override
{
//
const bool result = false;
bool result = false;
//
// Do all State Management here ...
@@ -4395,7 +4635,11 @@ public:
// Youngest Age of Positions longest as enough
// Make State of Signalling to Force State for Recieving
// Signal and Clear their Tp and SL for allowing hedges ...
EQMHandleForceState();
EQMHandleForceState(signals);
if (mForce)
{
result = true;
}
//
DoHedge();
@@ -4582,6 +4826,9 @@ protected:
//
Alert(message);
//
EQMHandleForceState(signals);
//
return;
}
@@ -4843,6 +5090,7 @@ private:
//
SaveResults(false);
SaveSignalsOnly(true);
}
//
@@ -4990,7 +5238,8 @@ private:
XSignal supports[];
int supportsCount = mTradeHandler.DoProtect(
supports,
mSetups);
mSetups //
);
//
if (IsValidSize(supportsCount))
@@ -5038,146 +5287,65 @@ private:
//
// Handle Force State Management ...
void EQMHandleForceState()
bool mForce;
void EQMHandleForceState(XSignal &forceSignals[])
{
//
// Validate Force Marigin ...
double marigin = mTrader.mAccount.GetMargin();
double minFreeMarigin = MinFreeMargingForOpenTrades();
double forceMargin = 3 * minFreeMarigin; // TODO: Make It Configurable
//
// Retrieving Positions ...
XPosition positions[];
int positionsCount = mTrader.GetPositions(positions);
if (!IsValidSize(positionsCount) || positionsCount <= 4)
if (!IsValidSize(positionsCount))
{
return;
}
//
double minRequiredProfitPerTrade = MinRequiredProfitPerTrade();
double minRequiredProfitPerVolumeFactor = MinRequiredProfitPerVolumeFactor();
XPosition oldest;
int oldestAge = GetOldest(
oldest,
positions //
);
//
mForce = marigin >= forceMargin && oldestAge >= 288;
if (!mForce)
{
return;
}
//
double minProfitPerTrade = MinProfitPerTrade();
double minProfitPerVolumeFactor = MinProfitPerVolumeFactor();
//
double profit = SpecifiedCalculatePositionsProfit(positions);
double requiredProfit = SpecifiedCalculateRequiredProfitForHedge(
positions,
minRequiredProfitPerTrade,
minRequiredProfitPerVolumeFactor //
minProfitPerTrade,
minProfitPerVolumeFactor //
);
//
bool canClose =
profit > 0 &&
(profit == requiredProfit ||
profit >= requiredProfit / 2);
if (canClose) {
DoEQMForceClose();
XSymbolPositions symbolPositions[];
int symbolPositionsCount = ExtractSymbolPositions(
positions,
symbolPositions,
minProfitPerTrade,
minProfitPerVolumeFactor //
);
if (!IsValidSize(symbolPositionsCount))
{
return;
}
return;
// //
// XPosition positions[];
// int positionsCount = mTrader.GetPositions(positions);
// if (!IsValidSize(positionsCount))
// {
// //
// EQMClearAllForceStates();
// //
// return;
// }
// //
// // Search For Force State Per Each Setup ...
// //
// int forceCount = 0;
// int setupsCount = CountSetups();
// if (IsValidSize(setupsCount))
// {
// //
// int maxAllowed = MaxAllowedTrades();
// bool perDirection = UseMaxAllowedPerDirection();
// //
// for (int i = 0; i < setupsCount; i++)
// {
// //
// string iSymbol = mSetups[i].GetSymbol();
// ENUM_TIMEFRAMES iPeriod = mSetups[i].GetPeriod();
// //
// XPosition iPositions[];
// int iPositionsCount = mTrader.GetPositions(
// iPositions,
// iSymbol,
// NULL, // All Providers ...
// NULL, // All Periods ...
// NULL, // All Types ...
// true // Filter By Magic ...
// );
// if (!IsValidSize(iPositionsCount))
// {
// continue;
// }
// //
// // Counting Positions ...
// int longs;
// double longProfits;
// double longVolumes;
// //
// int shorts;
// double shortProfits;
// double shortVolumes;
// //
// CountPositions(
// iPositions,
// //
// longs,
// longProfits,
// longVolumes,
// //
// shorts,
// shortProfits,
// shortVolumes //
// );
// //
// bool isMaxReached =
// maxAllowed <= 0
// ? false
// : !perDirection
// ? longs + shorts >= maxAllowed
// : longs >= maxAllowed && shorts >= maxAllowed;
// double volumeSummary = longVolumes + shortVolumes;
// double profitsSummary = longProfits + shortProfits;
// //
// bool isIInForce =
// //
// maxAllowed <= 0
// ? profitsSummary < 0 &&
// longVolumes == shortVolumes
// : isMaxReached &&
// profitsSummary < 0 &&
// longVolumes == shortVolumes
// //
// ;
// if (isIInForce)
// {
// //
// forceCount++;
// mSetups[i].ForceState(true);
// }
// }
// }
// //
// bool isForce = forceCount >= 1;
// if (!isForce)
// {
// return;
// }
//
Log("symbolPositionsCount: " + ToString(symbolPositionsCount));
}
//