mql5/Experts/Advisors/Modules/TradeManager.mqh

1316 lines
46 KiB
MQL5
Raw Permalink Normal View History

//+------------------------------------------------------------------+
//| TradeManager.mqh v2.2 |
2025-08-08 20:32:34 +01:00
//| Optimized Trade Management Module |
//| Fixed: Compatibility with ERMT 6.8 |
//+------------------------------------------------------------------+
#ifndef TRADE_MANAGER_MQH
#define TRADE_MANAGER_MQH
#include <Object.mqh>
#include <Trade/Trade.mqh>
#include <Arrays/ArrayObj.mqh>
#include "DataTypes.mqh"
#include "Utilities.mqh"
#include "RiskManager.mqh"
#include "TechnicalAnalysis.mqh"
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
#include "ExternalTradeManager.mqh"
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
//| Trade Manager Class |
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
class CTradeManager : public CObject
{
private:
// Dependencies
CUtilities* m_utils;
CRiskManager* m_risk;
CTechnicalAnalysis* m_tech;
CExternalTradeManager* m_external;
// Trade execution
CTrade m_trade;
// Settings
int m_magic_number;
string m_comment;
double m_slippage;
ENUM_POSITION_SIZING m_sizing_method;
double m_fixed_lot_size;
double m_atr_multiplier_sl;
double m_atr_multiplier_tp;
// Trailing stop settings
ENUM_TRAILING_METHOD m_trailing_method;
double m_trail_start;
double m_trail_step;
double m_trail_distance;
bool m_breakeven_enabled;
double m_breakeven_trigger;
double m_breakeven_offset;
// Trade tracking - using arrays of structures
TradeInfo m_managed_trades[];
int m_trade_count;
// Performance tracking
PerformanceMetrics m_performance;
double m_peak_balance;
datetime m_last_update;
// Trade history
TradeInfo m_history[];
int m_history_count;
// Helper methods
bool UpdateTradeInfo(int index);
void RecordTrade(const TradeInfo &trade);
void UpdatePerformanceMetrics();
bool ExecuteMarketOrder(MqlTradeRequest &request, MqlTradeResult &result);
double CalculateStopLoss(ENUM_ORDER_TYPE type, double entry, double atr);
double CalculateTakeProfit(ENUM_ORDER_TYPE type, double entry, double sl);
int FindTradeIndex(ulong ticket);
public:
// Constructor/Destructor
CTradeManager();
~CTradeManager();
// Initialization
bool Initialize(CUtilities* utils, CRiskManager* risk,
CTechnicalAnalysis* tech,
CExternalTradeManager* external,
int magic);
// Configuration
void SetSizingMethod(ENUM_POSITION_SIZING method) { m_sizing_method = method; }
void SetFixedLotSize(double size) { m_fixed_lot_size = size; }
void SetATRMultipliers(double sl_mult, double tp_mult);
void SetTrailingMethod(ENUM_TRAILING_METHOD method) { m_trailing_method = method; }
void SetTrailingParams(double start, double step, double distance);
void SetBreakevenEnabled(bool enabled) { m_breakeven_enabled = enabled; }
void SetBreakevenParams(double trigger, double offset);
void SetSlippage(double slippage) { m_slippage = slippage; }
void SetComment(string comment) { m_comment = comment; }
// Trade execution
ulong OpenTrade(MqlTradeRequest &request);
bool CloseTrade(ulong ticket, string reason = "");
bool PartialClose(ulong ticket, double volume, string reason = "");
bool ModifyTrade(ulong ticket, double sl, double tp);
// Position management
bool ApplyTrailingStop(ulong ticket);
bool CheckBreakeven(ulong ticket);
bool MoveToBreakeven(ulong ticket);
bool ScaleOut(ulong ticket, double percent, string reason);
bool ScaleIn(ulong ticket, double additional_lots);
// Trade information
int GetManagedTrades(TradeInfo &trades[]);
int GetOpenTradeCount() const { return m_trade_count; }
bool GetTradeInfo(ulong ticket, TradeInfo &trade);
double GetTotalExposure();
double GetTotalProfit();
// Performance metrics
void GetPerformanceMetrics(PerformanceMetrics &metrics);
double GetWinRate() const { return m_performance.win_rate; }
double GetProfitFactor() const { return m_performance.profit_factor; }
double GetAverageWin() const { return m_performance.average_win; }
double GetAverageLoss() const { return m_performance.average_loss; }
double GetMaxDrawdown() const { return m_performance.max_drawdown; }
// Trade monitoring
void UpdateAllTrades();
void CheckStopLevels();
void CheckTakeProfitLevels();
// Utility
void CleanupHistory();
void ExportHistory(string filename);
void ResetPerformance();
};
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
//| Constructor |
//+------------------------------------------------------------------+
CTradeManager::CTradeManager()
{
m_utils = NULL;
m_risk = NULL;
m_tech = NULL;
m_external = NULL;
m_magic_number = 0;
m_comment = "";
m_slippage = 3;
m_sizing_method = SIZING_FIXED_PERCENT;
m_fixed_lot_size = 0.1;
m_atr_multiplier_sl = 2.0;
m_atr_multiplier_tp = 3.0;
m_trailing_method = TRAIL_NONE;
m_trail_start = 30;
m_trail_step = 10;
m_trail_distance = 20;
m_breakeven_enabled = false;
m_breakeven_trigger = 20;
m_breakeven_offset = 2;
m_trade_count = 0;
ArrayResize(m_managed_trades, 10);
m_history_count = 0;
ArrayResize(m_history, 100);
m_peak_balance = 0;
m_last_update = 0;
// Initialize performance metrics
ZeroMemory(m_performance);
}
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
//| Destructor |
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
CTradeManager::~CTradeManager()
{
ArrayFree(m_managed_trades);
ArrayFree(m_history);
}
//+------------------------------------------------------------------+
//| Initialize |
//+------------------------------------------------------------------+
bool CTradeManager::Initialize(CUtilities* utils, CRiskManager* risk,
CTechnicalAnalysis* tech,
CExternalTradeManager* external, int magic)
{
if(utils == NULL || risk == NULL || tech == NULL) return false;
m_utils = utils;
m_risk = risk;
m_tech = tech;
m_external = external;
m_magic_number = magic;
// Set trade parameters
m_trade.SetExpertMagicNumber(m_magic_number);
m_trade.SetDeviationInPoints((ulong)m_slippage);
m_trade.SetTypeFilling(ORDER_FILLING_RETURN);
m_trade.SetAsyncMode(false);
// Initialize performance tracking
m_peak_balance = AccountInfoDouble(ACCOUNT_BALANCE);
m_last_update = TimeCurrent();
// Load existing positions
UpdateAllTrades();
m_utils.Log("Trade Manager initialized successfully", LOG_INFO);
m_utils.Log(StringFormat("Managing positions with magic: %d", m_magic_number), LOG_INFO);
return true;
}
//+------------------------------------------------------------------+
//| Set ATR Multipliers |
//+------------------------------------------------------------------+
void CTradeManager::SetATRMultipliers(double sl_mult, double tp_mult)
{
m_atr_multiplier_sl = sl_mult;
m_atr_multiplier_tp = tp_mult;
m_utils.Log(StringFormat("ATR multipliers set: SL=%.1f, TP=%.1f",
sl_mult, tp_mult), LOG_DEBUG);
}
//+------------------------------------------------------------------+
//| Set Trailing Parameters |
//+------------------------------------------------------------------+
void CTradeManager::SetTrailingParams(double start, double step, double distance)
{
m_trail_start = start;
m_trail_step = step;
m_trail_distance = distance;
m_utils.Log(StringFormat("Trailing params: Start=%.0f, Step=%.0f, Distance=%.0f",
start, step, distance), LOG_DEBUG);
}
//+------------------------------------------------------------------+
//| Set Breakeven Parameters |
//+------------------------------------------------------------------+
void CTradeManager::SetBreakevenParams(double trigger, double offset)
{
m_breakeven_trigger = trigger;
m_breakeven_offset = offset;
}
//+------------------------------------------------------------------+
//| Open Trade |
//+------------------------------------------------------------------+
ulong CTradeManager::OpenTrade(MqlTradeRequest &request)
{
MqlTradeResult result;
MqlTradeCheckResult check_result;
ZeroMemory(result);
ZeroMemory(check_result);
// Ensure proper filling type
request.type_filling = ORDER_FILLING_RETURN;
request.deviation = (ulong)m_slippage;
// Set magic and comment if not already set
if(request.magic == 0) request.magic = m_magic_number;
if(request.comment == "") request.comment = m_comment;
// Validate stops
if(!m_trade.OrderCheck(request, check_result))
{
m_utils.Log(StringFormat("Order check failed: %s", check_result.comment), LOG_ERROR);
return 0;
}
// Execute order
if(!ExecuteMarketOrder(request, result))
{
return 0;
}
// Create trade info record
if(result.order > 0)
{
// Wait for position to appear
Sleep(100);
// Find the position
for(int i = 0; i < PositionsTotal(); i++)
{
ulong ticket = PositionGetTicket(i);
if(PositionGetInteger(POSITION_MAGIC) == m_magic_number &&
PositionGetInteger(POSITION_IDENTIFIER) == result.order)
{
// Create new trade record
if(m_trade_count >= ArraySize(m_managed_trades))
{
ArrayResize(m_managed_trades, m_trade_count + 10);
}
TradeInfo trade;
trade.ticket = ticket;
trade.symbol = request.symbol;
trade.type = request.type;
trade.volume = request.volume;
trade.entry_price = result.price;
trade.current_price = result.price;
trade.sl = request.sl;
trade.tp = request.tp;
trade.open_time = TimeCurrent();
trade.last_update = TimeCurrent();
trade.status = TRADE_STATUS_ACTIVE;
trade.comment = request.comment;
trade.magic = m_magic_number;
trade.is_external = false;
trade.management_mode = MODE_FULL_CONTROL;
trade.profit = 0;
trade.swap = 0;
trade.commission = 0;
trade.close_requested = false;
trade.close_reason = "";
trade.partial_close_volume = 0;
trade.partial_close_reason = "";
// Calculate risk
double stop_distance = MathAbs(result.price - request.sl);
trade.risk_amount = m_risk.CalculateTradeRisk(request.volume,
stop_distance,
request.symbol);
trade.risk_percent = (trade.risk_amount / AccountInfoDouble(ACCOUNT_BALANCE)) * 100;
trade.current_rr = 0;
m_managed_trades[m_trade_count] = trade;
m_trade_count++;
m_utils.LogTrade(trade);
return ticket;
}
}
}
return result.order;
}
//+------------------------------------------------------------------+
//| Execute Market Order |
//+------------------------------------------------------------------+
bool CTradeManager::ExecuteMarketOrder(MqlTradeRequest &request, MqlTradeResult &result)
{
// Try to execute order
if(!m_trade.OrderSend(request, result))
{
m_utils.Log(StringFormat("OrderSend failed: %d - %s",
m_trade.ResultRetcode(),
m_trade.ResultComment()), LOG_ERROR);
return false;
}
// Check result
if(result.retcode != TRADE_RETCODE_DONE)
{
m_utils.Log(StringFormat("Order failed: Retcode %d - %s",
result.retcode, result.comment), LOG_ERROR);
return false;
}
m_utils.Log(StringFormat("Order executed: #%d at %.5f",
result.order, result.price), LOG_INFO);
return true;
}
//+------------------------------------------------------------------+
//| Find Trade Index |
//+------------------------------------------------------------------+
int CTradeManager::FindTradeIndex(ulong ticket)
{
for(int i = 0; i < m_trade_count; i++)
{
if(m_managed_trades[i].ticket == ticket)
return i;
}
return -1;
}
//+------------------------------------------------------------------+
//| Close Trade |
//+------------------------------------------------------------------+
bool CTradeManager::CloseTrade(ulong ticket, string reason)
{
if(!PositionSelectByTicket(ticket))
{
m_utils.Log(StringFormat("Position %d not found", ticket), LOG_WARNING);
return false;
}
// Close position
if(!m_trade.PositionClose(ticket, (ulong)m_slippage))
{
m_utils.Log(StringFormat("Failed to close position %d: %s",
ticket, m_trade.ResultComment()), LOG_ERROR);
return false;
}
// Update trade record
int index = FindTradeIndex(ticket);
if(index >= 0)
{
m_managed_trades[index].status = TRADE_STATUS_CLOSED;
m_managed_trades[index].close_reason = reason;
m_managed_trades[index].last_update = TimeCurrent();
// Record in history
RecordTrade(m_managed_trades[index]);
// Remove from active trades by shifting array
for(int j = index; j < m_trade_count - 1; j++)
{
m_managed_trades[j] = m_managed_trades[j + 1];
}
m_trade_count--;
}
m_utils.Log(StringFormat("Position %d closed: %s", ticket, reason), LOG_INFO);
// Update performance
UpdatePerformanceMetrics();
return true;
}
//+------------------------------------------------------------------+
//| Partial Close |
//+------------------------------------------------------------------+
bool CTradeManager::PartialClose(ulong ticket, double volume, string reason)
{
if(!PositionSelectByTicket(ticket))
{
m_utils.Log(StringFormat("Position %d not found", ticket), LOG_WARNING);
return false;
}
double current_volume = PositionGetDouble(POSITION_VOLUME);
if(volume >= current_volume)
{
// Close entire position
return CloseTrade(ticket, reason);
}
// Partial close
if(!m_trade.PositionClosePartial(ticket, volume, (ulong)m_slippage))
{
m_utils.Log(StringFormat("Failed to partial close %d: %s",
ticket, m_trade.ResultComment()), LOG_ERROR);
return false;
}
// Update trade record
int index = FindTradeIndex(ticket);
if(index >= 0)
{
m_managed_trades[index].volume = current_volume - volume;
m_managed_trades[index].partial_close_volume = 0;
m_managed_trades[index].partial_close_reason = "";
m_managed_trades[index].last_update = TimeCurrent();
}
m_utils.Log(StringFormat("Partial close %d: %.2f lots (%s)",
ticket, volume, reason), LOG_INFO);
return true;
}
//+------------------------------------------------------------------+
//| Modify Trade |
//+------------------------------------------------------------------+
bool CTradeManager::ModifyTrade(ulong ticket, double sl, double tp)
{
if(!PositionSelectByTicket(ticket))
{
m_utils.Log(StringFormat("Position %d not found", ticket), LOG_WARNING);
return false;
}
// Validate stops
string symbol = PositionGetString(POSITION_SYMBOL);
ENUM_ORDER_TYPE type = (ENUM_ORDER_TYPE)PositionGetInteger(POSITION_TYPE);
double current_price = PositionGetDouble(POSITION_PRICE_CURRENT);
double point = SymbolInfoDouble(symbol, SYMBOL_POINT);
int stops_level = (int)SymbolInfoInteger(symbol, SYMBOL_TRADE_STOPS_LEVEL);
double min_stop = stops_level * point;
// Validate stop loss
if(sl > 0)
{
if(type == ORDER_TYPE_BUY)
{
if(sl > current_price - min_stop)
{
sl = current_price - min_stop;
}
}
else
{
if(sl < current_price + min_stop)
{
sl = current_price + min_stop;
}
}
}
// Validate take profit
if(tp > 0)
{
if(type == ORDER_TYPE_BUY)
{
if(tp < current_price + min_stop)
{
tp = current_price + min_stop;
}
}
else
{
if(tp > current_price - min_stop)
{
tp = current_price - min_stop;
}
}
}
// Modify position
if(!m_trade.PositionModify(ticket, sl, tp))
{
m_utils.Log(StringFormat("Failed to modify position %d: %s",
ticket, m_trade.ResultComment()), LOG_ERROR);
return false;
}
// Update trade record
int index = FindTradeIndex(ticket);
if(index >= 0)
{
m_managed_trades[index].sl = sl;
m_managed_trades[index].tp = tp;
m_managed_trades[index].last_update = TimeCurrent();
// Recalculate risk
double stop_distance = MathAbs(m_managed_trades[index].entry_price - sl);
m_managed_trades[index].risk_amount = m_risk.CalculateTradeRisk(
m_managed_trades[index].volume, stop_distance, symbol);
m_managed_trades[index].risk_percent =
(m_managed_trades[index].risk_amount / AccountInfoDouble(ACCOUNT_BALANCE)) * 100;
}
m_utils.Log(StringFormat("Position %d modified: SL=%.5f, TP=%.5f",
ticket, sl, tp), LOG_DEBUG);
return true;
}
//+------------------------------------------------------------------+
//| Apply Trailing Stop |
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
bool CTradeManager::ApplyTrailingStop(ulong ticket)
2025-08-22 17:46:10 +01:00
{
if(m_trailing_method == TRAIL_NONE) return false;
if(!PositionSelectByTicket(ticket))
return false;
string symbol = PositionGetString(POSITION_SYMBOL);
ENUM_ORDER_TYPE type = (ENUM_ORDER_TYPE)PositionGetInteger(POSITION_TYPE);
double current_price = PositionGetDouble(POSITION_PRICE_CURRENT);
double current_sl = PositionGetDouble(POSITION_SL);
double entry_price = PositionGetDouble(POSITION_PRICE_OPEN);
double point = SymbolInfoDouble(symbol, SYMBOL_POINT);
double new_sl = 0;
switch(m_trailing_method)
{
case TRAIL_FIXED_POINTS:
{
double trail_distance = m_trail_distance * point;
if(type == ORDER_TYPE_BUY)
{
new_sl = current_price - trail_distance;
if(current_sl == 0 || new_sl > current_sl)
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
else
{
new_sl = current_price + trail_distance;
if(current_sl == 0 || new_sl < current_sl)
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
}
break;
2025-08-22 17:46:10 +01:00
case TRAIL_PERCENT:
{
double trail_distance = current_price * m_trail_distance / 100;
if(type == ORDER_TYPE_BUY)
{
new_sl = current_price - trail_distance;
if(current_sl == 0 || new_sl > current_sl)
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
else
{
new_sl = current_price + trail_distance;
if(current_sl == 0 || new_sl < current_sl)
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
}
break;
case TRAIL_ATR:
{
double atr = m_tech.GetATR();
double trail_distance = atr * (m_trail_distance / 10); // Normalize
if(type == ORDER_TYPE_BUY)
{
new_sl = current_price - trail_distance;
if(current_sl == 0 || new_sl > current_sl)
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
else
{
new_sl = current_price + trail_distance;
if(current_sl == 0 || new_sl < current_sl)
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
}
break;
case TRAIL_PARABOLIC_SAR:
{
int sar_handle = iSAR(symbol, PERIOD_CURRENT, 0.02, 0.2);
if(sar_handle != INVALID_HANDLE)
{
double sar_buffer[1];
if(CopyBuffer(sar_handle, 0, 0, 1, sar_buffer) > 0)
{
new_sl = sar_buffer[0];
IndicatorRelease(sar_handle);
if(type == ORDER_TYPE_BUY && (current_sl == 0 || new_sl > current_sl))
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
else if(type == ORDER_TYPE_SELL && (current_sl == 0 || new_sl < current_sl))
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
else
{
IndicatorRelease(sar_handle);
}
}
}
break;
case TRAIL_MOVING_AVERAGE:
{
double ma = m_tech.GetMA();
if(type == ORDER_TYPE_BUY && (current_sl == 0 || ma > current_sl))
{
return ModifyTrade(ticket, ma, PositionGetDouble(POSITION_TP));
}
else if(type == ORDER_TYPE_SELL && (current_sl == 0 || ma < current_sl))
{
return ModifyTrade(ticket, ma, PositionGetDouble(POSITION_TP));
}
}
break;
case TRAIL_STEPPED:
{
double profit_points = (current_price - entry_price) / point;
if(type == ORDER_TYPE_SELL)
profit_points = (entry_price - current_price) / point;
if(profit_points >= m_trail_start)
{
int steps = (int)(profit_points / m_trail_step);
double new_trail = steps * m_trail_step * point;
if(type == ORDER_TYPE_BUY)
{
new_sl = entry_price + new_trail - m_trail_distance * point;
if(current_sl == 0 || new_sl > current_sl)
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
else
{
new_sl = entry_price - new_trail + m_trail_distance * point;
if(current_sl == 0 || new_sl < current_sl)
{
return ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
}
}
break;
}
return false;
2025-08-22 17:46:10 +01:00
}
//+------------------------------------------------------------------+
//| Check Breakeven |
//+------------------------------------------------------------------+
bool CTradeManager::CheckBreakeven(ulong ticket)
{
if(!m_breakeven_enabled) return false;
if(!PositionSelectByTicket(ticket))
return false;
double entry_price = PositionGetDouble(POSITION_PRICE_OPEN);
double current_price = PositionGetDouble(POSITION_PRICE_CURRENT);
double current_sl = PositionGetDouble(POSITION_SL);
ENUM_ORDER_TYPE type = (ENUM_ORDER_TYPE)PositionGetInteger(POSITION_TYPE);
string symbol = PositionGetString(POSITION_SYMBOL);
double point = SymbolInfoDouble(symbol, SYMBOL_POINT);
double profit_points = 0;
if(type == ORDER_TYPE_BUY)
{
profit_points = (current_price - entry_price) / point;
if(profit_points >= m_breakeven_trigger)
{
double new_sl = entry_price + m_breakeven_offset * point;
if(current_sl < new_sl)
{
return MoveToBreakeven(ticket);
}
}
}
else
{
profit_points = (entry_price - current_price) / point;
if(profit_points >= m_breakeven_trigger)
{
double new_sl = entry_price - m_breakeven_offset * point;
2025-08-08 20:32:34 +01:00
if(current_sl == 0 || current_sl > new_sl)
{
return MoveToBreakeven(ticket);
}
}
}
return false;
}
//+------------------------------------------------------------------+
//| Move to Breakeven |
//+------------------------------------------------------------------+
bool CTradeManager::MoveToBreakeven(ulong ticket)
{
if(!PositionSelectByTicket(ticket))
return false;
double entry_price = PositionGetDouble(POSITION_PRICE_OPEN);
ENUM_ORDER_TYPE type = (ENUM_ORDER_TYPE)PositionGetInteger(POSITION_TYPE);
string symbol = PositionGetString(POSITION_SYMBOL);
double point = SymbolInfoDouble(symbol, SYMBOL_POINT);
double new_sl = 0;
if(type == ORDER_TYPE_BUY)
{
new_sl = entry_price + m_breakeven_offset * point;
}
else
{
new_sl = entry_price - m_breakeven_offset * point;
}
bool result = ModifyTrade(ticket, new_sl, PositionGetDouble(POSITION_TP));
if(result)
{
m_utils.Log(StringFormat("Position %d moved to breakeven at %.5f",
ticket, new_sl), LOG_INFO);
}
return result;
}
//+------------------------------------------------------------------+
//| Get Managed Trades |
//+------------------------------------------------------------------+
int CTradeManager::GetManagedTrades(TradeInfo &trades[])
{
UpdateAllTrades();
ArrayResize(trades, m_trade_count);
for(int i = 0; i < m_trade_count; i++)
{
trades[i] = m_managed_trades[i];
}
return m_trade_count;
}
//+------------------------------------------------------------------+
//| Update All Trades |
//+------------------------------------------------------------------+
void CTradeManager::UpdateAllTrades()
{
// Update existing trades
for(int i = m_trade_count - 1; i >= 0; i--)
{
if(!UpdateTradeInfo(i))
{
// Trade closed
RecordTrade(m_managed_trades[i]);
// Shift array
for(int j = i; j < m_trade_count - 1; j++)
{
m_managed_trades[j] = m_managed_trades[j + 1];
}
m_trade_count--;
}
}
// Check for new positions
for(int i = 0; i < PositionsTotal(); i++)
{
ulong ticket = PositionGetTicket(i);
if(ticket == 0) continue;
if(PositionGetInteger(POSITION_MAGIC) != m_magic_number)
continue;
// Check if already tracked
if(FindTradeIndex(ticket) >= 0) continue;
// Add new trade
if(m_trade_count >= ArraySize(m_managed_trades))
{
ArrayResize(m_managed_trades, m_trade_count + 10);
}
TradeInfo trade;
trade.ticket = ticket;
trade.symbol = PositionGetString(POSITION_SYMBOL);
trade.type = (ENUM_ORDER_TYPE)PositionGetInteger(POSITION_TYPE);
trade.volume = PositionGetDouble(POSITION_VOLUME);
trade.entry_price = PositionGetDouble(POSITION_PRICE_OPEN);
trade.current_price = PositionGetDouble(POSITION_PRICE_CURRENT);
trade.sl = PositionGetDouble(POSITION_SL);
trade.tp = PositionGetDouble(POSITION_TP);
trade.profit = PositionGetDouble(POSITION_PROFIT);
trade.swap = PositionGetDouble(POSITION_SWAP);
trade.commission = 0; // Not available directly
trade.open_time = (datetime)PositionGetInteger(POSITION_TIME);
trade.last_update = TimeCurrent();
trade.status = TRADE_STATUS_ACTIVE;
trade.comment = PositionGetString(POSITION_COMMENT);
trade.magic = m_magic_number;
trade.is_external = false;
trade.management_mode = MODE_FULL_CONTROL;
trade.close_requested = false;
trade.close_reason = "";
trade.partial_close_volume = 0;
trade.partial_close_reason = "";
trade.risk_amount = 0;
trade.risk_percent = 0;
trade.current_rr = 0;
m_managed_trades[m_trade_count] = trade;
m_trade_count++;
m_utils.Log(StringFormat("New position detected: %d", ticket), LOG_INFO);
}
2025-08-08 20:32:34 +01:00
}
//+------------------------------------------------------------------+
//| Update Trade Info |
2025-08-08 20:32:34 +01:00
//+------------------------------------------------------------------+
bool CTradeManager::UpdateTradeInfo(int index)
2025-08-08 20:32:34 +01:00
{
if(index < 0 || index >= m_trade_count) return false;
ulong ticket = m_managed_trades[index].ticket;
if(!PositionSelectByTicket(ticket))
{
// Position closed
m_managed_trades[index].status = TRADE_STATUS_CLOSED;
m_managed_trades[index].last_update = TimeCurrent();
return false;
}
// Update current values
m_managed_trades[index].current_price = PositionGetDouble(POSITION_PRICE_CURRENT);
m_managed_trades[index].profit = PositionGetDouble(POSITION_PROFIT);
m_managed_trades[index].swap = PositionGetDouble(POSITION_SWAP);
m_managed_trades[index].sl = PositionGetDouble(POSITION_SL);
m_managed_trades[index].tp = PositionGetDouble(POSITION_TP);
m_managed_trades[index].volume = PositionGetDouble(POSITION_VOLUME);
m_managed_trades[index].last_update = TimeCurrent();
// Update risk metrics
if(m_managed_trades[index].sl > 0)
{
double stop_distance = MathAbs(m_managed_trades[index].entry_price -
m_managed_trades[index].sl);
m_managed_trades[index].risk_amount = m_risk.CalculateTradeRisk(
m_managed_trades[index].volume, stop_distance, m_managed_trades[index].symbol);
m_managed_trades[index].risk_percent =
(m_managed_trades[index].risk_amount / AccountInfoDouble(ACCOUNT_BALANCE)) * 100;
if(m_managed_trades[index].tp > 0)
{
m_managed_trades[index].current_rr = m_utils.CalculateRiskReward(
m_managed_trades[index].entry_price,
m_managed_trades[index].sl,
m_managed_trades[index].tp,
m_managed_trades[index].type);
}
}
return true;
2025-08-08 20:32:34 +01:00
}
//+------------------------------------------------------------------+
//| Record Trade in History |
2025-08-08 20:32:34 +01:00
//+------------------------------------------------------------------+
void CTradeManager::RecordTrade(const TradeInfo &trade)
2025-08-08 20:32:34 +01:00
{
if(m_history_count >= ArraySize(m_history))
{
ArrayResize(m_history, m_history_count + 100);
}
m_history[m_history_count] = trade;
m_history_count++;
// Update performance metrics
UpdatePerformanceMetrics();
}
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
//| Update Performance Metrics |
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
void CTradeManager::UpdatePerformanceMetrics()
2025-08-22 17:46:10 +01:00
{
// Reset metrics
ZeroMemory(m_performance);
double total_wins = 0;
double total_losses = 0;
int win_count = 0;
int loss_count = 0;
// Analyze history
for(int i = 0; i < m_history_count; i++)
{
m_performance.total_trades++;
if(m_history[i].profit > 0)
{
m_performance.winning_trades++;
total_wins += m_history[i].profit;
win_count++;
}
else if(m_history[i].profit < 0)
{
m_performance.losing_trades++;
total_losses += MathAbs(m_history[i].profit);
loss_count++;
}
m_performance.total_profit += m_history[i].profit;
}
// Calculate metrics
if(m_performance.total_trades > 0)
{
m_performance.win_rate = (double)m_performance.winning_trades /
m_performance.total_trades * 100;
}
if(win_count > 0)
{
m_performance.average_win = total_wins / win_count;
}
if(loss_count > 0)
{
m_performance.average_loss = total_losses / loss_count;
}
if(total_losses > 0)
{
m_performance.profit_factor = total_wins / total_losses;
}
// Calculate drawdown
double current_balance = AccountInfoDouble(ACCOUNT_BALANCE);
if(current_balance > m_peak_balance)
{
m_peak_balance = current_balance;
}
m_performance.current_drawdown = ((m_peak_balance - current_balance) / m_peak_balance) * 100;
m_performance.max_drawdown = MathMax(m_performance.max_drawdown,
m_performance.current_drawdown);
// Expected value
if(m_performance.total_trades > 0)
{
m_performance.expected_value = m_performance.total_profit /
m_performance.total_trades;
}
// Sharpe ratio (simplified)
if(m_performance.average_loss > 0)
{
double avg_return = m_performance.expected_value;
double std_dev = MathSqrt(MathPow(m_performance.average_win - avg_return, 2) *
m_performance.win_rate / 100 +
MathPow(m_performance.average_loss + avg_return, 2) *
(1 - m_performance.win_rate / 100));
if(std_dev > 0)
{
m_performance.sharpe_ratio = avg_return / std_dev;
}
}
// Recovery factor
if(m_performance.max_drawdown > 0)
{
m_performance.recovery_factor = m_performance.total_profit /
m_performance.max_drawdown;
}
m_performance.last_update = TimeCurrent();
// Update risk manager with performance data
m_risk.UpdatePerformanceMetrics(m_performance.win_rate,
m_performance.average_win,
m_performance.average_loss);
2025-08-22 17:46:10 +01:00
}
//+------------------------------------------------------------------+
//| Get Performance Metrics |
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
void CTradeManager::GetPerformanceMetrics(PerformanceMetrics &metrics)
2025-08-22 17:46:10 +01:00
{
UpdatePerformanceMetrics();
metrics = m_performance;
2025-08-22 17:46:10 +01:00
}
//+------------------------------------------------------------------+
//| Get Total Exposure |
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
double CTradeManager::GetTotalExposure()
2025-08-22 17:46:10 +01:00
{
double total = 0;
for(int i = 0; i < m_trade_count; i++)
{
total += m_managed_trades[i].volume;
}
return total;
2025-08-22 17:46:10 +01:00
}
//+------------------------------------------------------------------+
//| Get Total Profit |
//+------------------------------------------------------------------+
double CTradeManager::GetTotalProfit()
{
double total = 0;
for(int i = 0; i < m_trade_count; i++)
{
total += m_managed_trades[i].profit;
}
return total;
}
//+------------------------------------------------------------------+
//| Get Trade Info |
//+------------------------------------------------------------------+
bool CTradeManager::GetTradeInfo(ulong ticket, TradeInfo &trade)
{
int index = FindTradeIndex(ticket);
if(index >= 0)
{
trade = m_managed_trades[index];
return true;
}
return false;
}
//+------------------------------------------------------------------+
//| Cleanup History |
//+------------------------------------------------------------------+
void CTradeManager::CleanupHistory()
{
// Keep only last 1000 trades in memory
if(m_history_count > 1000)
{
int to_remove = m_history_count - 1000;
// Shift remaining records
for(int i = 0; i < 1000; i++)
{
m_history[i] = m_history[i + to_remove];
}
m_history_count = 1000;
m_utils.Log("Trade history cleaned up", LOG_DEBUG);
}
}
//+------------------------------------------------------------------+
//| Export History |
//+------------------------------------------------------------------+
void CTradeManager::ExportHistory(string filename)
{
if(filename == "")
{
filename = StringFormat("TradeHistory_%s.csv",
TimeToString(TimeCurrent(), TIME_DATE));
}
TradeInfo history_array[];
ArrayResize(history_array, m_history_count);
for(int i = 0; i < m_history_count; i++)
{
history_array[i] = m_history[i];
}
m_utils.SaveTradeHistory(history_array, m_history_count);
}
//+------------------------------------------------------------------+
//| Reset Performance |
//+------------------------------------------------------------------+
void CTradeManager::ResetPerformance()
{
ZeroMemory(m_performance);
m_peak_balance = AccountInfoDouble(ACCOUNT_BALANCE);
m_last_update = TimeCurrent();
// Clear history
m_history_count = 0;
m_utils.Log("Performance metrics reset", LOG_INFO);
2025-08-08 20:32:34 +01:00
}
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
//| Calculate Stop Loss |
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
double CTradeManager::CalculateStopLoss(ENUM_ORDER_TYPE type, double entry, double atr)
2025-08-22 17:46:10 +01:00
{
double sl = 0;
double stop_distance = atr * m_atr_multiplier_sl;
if(type == ORDER_TYPE_BUY)
{
sl = entry - stop_distance;
}
else
{
sl = entry + stop_distance;
}
return m_utils.NormalizePrice(sl, _Symbol);
2025-08-22 17:46:10 +01:00
}
//+------------------------------------------------------------------+
//| Calculate Take Profit |
2025-08-22 17:46:10 +01:00
//+------------------------------------------------------------------+
double CTradeManager::CalculateTakeProfit(ENUM_ORDER_TYPE type, double entry, double sl)
2025-08-22 17:46:10 +01:00
{
if(sl == 0) return 0;
double risk = MathAbs(entry - sl);
double reward = risk * m_atr_multiplier_tp / m_atr_multiplier_sl;
double tp = 0;
if(type == ORDER_TYPE_BUY)
{
tp = entry + reward;
}
else
{
tp = entry - reward;
}
return m_utils.NormalizePrice(tp, _Symbol);
2025-08-22 17:46:10 +01:00
}
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
//+------------------------------------------------------------------+
//| Scale Out Position |
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
//+------------------------------------------------------------------+
bool CTradeManager::ScaleOut(ulong ticket, double percent, string reason)
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
{
if(!PositionSelectByTicket(ticket))
return false;
double current_volume = PositionGetDouble(POSITION_VOLUME);
double close_volume = current_volume * percent / 100;
return PartialClose(ticket, close_volume, reason);
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
}
//+------------------------------------------------------------------+
//| Scale In Position |
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
//+------------------------------------------------------------------+
bool CTradeManager::ScaleIn(ulong ticket, double additional_lots)
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
{
if(!PositionSelectByTicket(ticket))
return false;
// Create new position in same direction
MqlTradeRequest request = {};
request.symbol = PositionGetString(POSITION_SYMBOL);
request.type = (ENUM_ORDER_TYPE)PositionGetInteger(POSITION_TYPE);
request.volume = additional_lots;
request.magic = m_magic_number;
request.comment = "Scale In";
// Use same stops as original
request.sl = PositionGetDouble(POSITION_SL);
request.tp = PositionGetDouble(POSITION_TP);
ulong new_ticket = OpenTrade(request);
if(new_ticket > 0)
{
m_utils.Log(StringFormat("Scaled in position %d with %.2f lots",
ticket, additional_lots), LOG_INFO);
return true;
}
return false;
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
}
//+------------------------------------------------------------------+
//| Check Stop Levels |
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
//+------------------------------------------------------------------+
void CTradeManager::CheckStopLevels()
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
{
for(int i = 0; i < m_trade_count; i++)
{
// Check if stop loss needs adjustment
if(m_managed_trades[i].sl == 0)
{
// Apply default stop
double atr = m_tech.GetATR();
double sl = CalculateStopLoss(m_managed_trades[i].type,
m_managed_trades[i].entry_price, atr);
ModifyTrade(m_managed_trades[i].ticket, sl, m_managed_trades[i].tp);
}
}
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
}
//+------------------------------------------------------------------+
//| Check Take Profit Levels |
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
//+------------------------------------------------------------------+
void CTradeManager::CheckTakeProfitLevels()
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
{
for(int i = 0; i < m_trade_count; i++)
{
// Check if take profit needs adjustment
if(m_managed_trades[i].tp == 0 && m_managed_trades[i].sl != 0)
{
// Apply default TP based on SL
double tp = CalculateTakeProfit(m_managed_trades[i].type,
m_managed_trades[i].entry_price,
m_managed_trades[i].sl);
ModifyTrade(m_managed_trades[i].ticket, m_managed_trades[i].sl, tp);
}
}
Module Integration Summary for External Trade Management Overview To fully integrate the enhanced external trade management system, updates are required to 5 out of 7 existing modules. The updates maintain backward compatibility while adding new functionality for external trade handling. Module Update Requirements 🟢 No Updates Required (2 modules) TechnicalAnalysis.mqh - Already provides necessary calculations EntrySystem.mqh - Only handles EA's own entry signals 🟡 Minor Updates (2 modules) DataTypes.mqh - Add external trade structures and fields Utilities.mqh - Enhanced logging for external trades 🟠 Moderate Updates (3 modules) RiskManager.mqh - Enhanced risk enforcement methods TradeManager.mqh - Improved stop management for externals Dashboard.mqh - Display external trade information Integration Steps Phase 1: Data Structures (DataTypes.mqh) Add ENUM_EXTERNAL_STATUS enumeration Extend ManagedTrade structure with external-specific fields Add ExternalTradeStats structure for metrics Update DashboardConfig with show_external flag Key additions: external_status - Track state of external trade source_name - Identify where trade came from stops_modified - Track if we modified the trade original_sl/tp - Store original values for comparison Phase 2: Risk Management (RiskManager.mqh) Add EnforceRiskRulesEnhanced() method Implement GetExternalExposure() for risk aggregation Add UpdateExternalStats() for tracking Enhance ValidateAndAdjustRiskExternal() method Key features: Separate risk calculation for external trades Cache mechanism for performance Statistical tracking of external positions Smart risk adjustment without closing trades Phase 3: Trade Management (TradeManager.mqh) Add ApplyDefaultStopsEnhanced() with better logic Implement OverrideExternalStops() with smart override Create ManageExternalTrade() with different rules Add ApplyBreakevenExternal() with wider triggers Key features: Smart stop override (only improve, never worsen) Different management rules for external trades Respect minimum broker distances Track modification success/failure rates Phase 4: User Interface (Dashboard.mqh) Add CreateExternalSection() for display area Implement UpdateExternalSection() for real-time updates Add SetCustomText() for flexible display Create ShowExternalTrades() toggle method Key features: Real-time external trade count and risk Color-coded risk warnings List of active external positions Modification statistics display Phase 5: Logging (Utilities.mqh) Add LogExternalTrade() for detailed event logging Create separate CSV log for external trades Enhance GenerateReportEnhanced() with external section Add IdentifyTradeSource() for magic number interpretation Key features: Separate CSV log for external trade events Detailed tracking of all modifications Source identification from magic numbers Enhanced reporting with external statistics
2025-08-27 14:21:02 +01:00
}
2025-08-22 17:46:10 +01:00
#endif // TRADE_MANAGER_MQH