Plus i have prepared versions for MT5 traders plus IC traders as well.
Transitioning from MQL4 to MQL5 requires a significant architectural shift. While MQL4 is highly procedural and treats everything as an "order," MQL5 is an object-oriented language that strictly separates Orders (requests to the broker), Deals (historical executions), and Positions (your current open exposure).
Since you are running this on IC Markets (IC Trader), the environment will almost certainly feature 5-digit fractional pricing and raw spreads.
To handle the complex MqlTradeRequest structures cleanly, this MT5 version utilizes the standard MQL5 #include <Trade\Trade.mqh> library. This wraps the execution logic into a robust, object-oriented CTrade class, handling slippage, re-quotes, and server routing natively.
MQL5 Source Code: Liquidity Sweep Auto-Scalper (MT5)
Code: Select all
//+------------------------------------------------------------------+
//| Liquidity_Sweep_Scalper_EA.mq5 |
//| Automated Execution with Dynamic Trailing Stop |
//| Optimized for MetaTrader 5 (IC Markets) |
//+------------------------------------------------------------------+
#property copyright "Automated Zone Scalper EA MT5"
#property version "1.20"
#include <Trade\Trade.mqh>
// Initialize the Trade Object
CTrade trade;
// --- Trading Parameters ---
input double InpLotSize = 0.10; // Fixed Lot Size
input int InpStopLossPips = 5; // Initial Stop Loss (Pips)
input int InpTakeProfitPips = 10; // Take Profit (Pips)
input int InpMaxSlippage = 3; // Max Slippage (Pips)
input ulong InpMagicNumber = 999111; // EA Identifier (ulong in MT5)
// --- Trailing Stop Parameters ---
input bool InpUseTrailingStop = true; // Enable Trailing Stop
input int InpTrailingStopPips = 4; // Distance behind price (Pips)
input int InpTrailingStepPips = 1; // Minimum move before adjusting (Pips)
// --- Zone Parameters ---
input int InpLookbackBars = 40; // Lookback Period (Bars)
input int InpZoneWidthPips = 2; // Zone Depth (Pips)
input color InpSweepHighColor = clrLightCoral;
input color InpSweepLowColor = clrLightGreen;
//+------------------------------------------------------------------+
int OnInit()
{
if(InpStopLossPips <= 0 || InpTakeProfitPips <= 0)
{
Print("Invalid SL/TP configuration.");
return(INIT_PARAMETERS_INCORRECT);
}
// Configure the CTrade object
trade.SetExpertMagicNumber(InpMagicNumber);
trade.SetDeviationInPoints(InpMaxSlippage * ((_Digits == 3 || _Digits == 5) ? 10 : 1));
return(INIT_SUCCEEDED);
}
void OnDeinit(const int reason)
{
ObjectsDeleteAll(0, "LiqPool_");
}
void OnTick()
{
// 1. Data Retrieval (MQL5 requires copying timeseries data to arrays)
double High[], Low[], Close[];
datetime Time[];
// Set arrays to behave like MQL4 (Index 0 = Current Bar)
ArraySetAsSeries(High, true);
ArraySetAsSeries(Low, true);
ArraySetAsSeries(Close, true);
ArraySetAsSeries(Time, true);
if(CopyHigh(_Symbol, _Period, 0, InpLookbackBars, High) < InpLookbackBars) return;
if(CopyLow(_Symbol, _Period, 0, InpLookbackBars, Low) < InpLookbackBars) return;
if(CopyClose(_Symbol, _Period, 0, 1, Close) < 1) return;
if(CopyTime(_Symbol, _Period, 0, InpLookbackBars, Time) < InpLookbackBars) return;
// 2. Calculate Pricing Variables
double point = SymbolInfoDouble(_Symbol, SYMBOL_POINT);
double pip_size = (_Digits == 3 || _Digits == 5) ? 10.0 * point : point;
// 3. Manage Open Positions (Trailing Stop)
if(InpUseTrailingStop)
{
ManageTrailingStops(pip_size);
}
// 4. State Management: Prevent multiple entries
if(HasOpenPositions(InpMagicNumber)) return;
// 5. Identify Market Structure Extremes
int highest_idx = ArrayMaximum(High, 0, InpLookbackBars);
int lowest_idx = ArrayMinimum(Low, 0, InpLookbackBars);
double swing_high = High[highest_idx];
double swing_low = Low[lowest_idx];
double zone_height = InpZoneWidthPips * pip_size;
double sell_zone_bottom = swing_high - zone_height;
double buy_zone_top = swing_low + zone_height;
// 6. Render GUI
DrawZone("LiqPool_High", Time[highest_idx], swing_high, TimeCurrent() + PeriodSeconds()*10, sell_zone_bottom, InpSweepHighColor);
DrawZone("LiqPool_Low", Time[lowest_idx], swing_low, TimeCurrent() + PeriodSeconds()*10, buy_zone_top, InpSweepLowColor);
// 7. Execution Logic
double ask = SymbolInfoDouble(_Symbol, SYMBOL_ASK);
double bid = SymbolInfoDouble(_Symbol, SYMBOL_BID);
// SELL Condition
if(Close[0] >= sell_zone_bottom && Close[0] <= swing_high)
{
double sl = NormalizeDouble(bid + (InpStopLossPips * pip_size), _Digits);
double tp = NormalizeDouble(bid - (InpTakeProfitPips * pip_size), _Digits);
trade.Sell(InpLotSize, _Symbol, bid, sl, tp, "Liq Sweep Sell");
}
// BUY Condition
else if(Close[0] <= buy_zone_top && Close[0] >= swing_low)
{
double sl = NormalizeDouble(ask - (InpStopLossPips * pip_size), _Digits);
double tp = NormalizeDouble(ask + (InpTakeProfitPips * pip_size), _Digits);
trade.Buy(InpLotSize, _Symbol, ask, sl, tp, "Liq Sweep Buy");
}
}
//+------------------------------------------------------------------+
//| Subroutine: Manage Dynamic Trailing Stops (MT5 Positions) |
//+------------------------------------------------------------------+
void ManageTrailingStops(double pip_size)
{
double trailing_dist = InpTrailingStopPips * pip_size;
double trailing_step = InpTrailingStepPips * pip_size;
for(int i = PositionsTotal() - 1; i >= 0; i--)
{
ulong ticket = PositionGetTicket(i); // Selects the position
if(PositionGetString(POSITION_SYMBOL) == _Symbol && PositionGetInteger(POSITION_MAGIC) == InpMagicNumber)
{
double current_sl = PositionGetDouble(POSITION_SL);
double open_price = PositionGetDouble(POSITION_PRICE_OPEN);
// Manage BUY Position
if(PositionGetInteger(POSITION_TYPE) == POSITION_TYPE_BUY)
{
double current_bid = SymbolInfoDouble(_Symbol, SYMBOL_BID);
double new_sl = NormalizeDouble(current_bid - trailing_dist, _Digits);
if(current_bid - open_price > trailing_dist)
{
if(current_sl < new_sl - trailing_step || current_sl == 0)
{
trade.PositionModify(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
}
// Manage SELL Position
else if(PositionGetInteger(POSITION_TYPE) == POSITION_TYPE_SELL)
{
double current_ask = SymbolInfoDouble(_Symbol, SYMBOL_ASK);
double new_sl = NormalizeDouble(current_ask + trailing_dist, _Digits);
if(open_price - current_ask > trailing_dist)
{
if(current_sl > new_sl + trailing_step || current_sl == 0)
{
trade.PositionModify(ticket, new_sl, PositionGetDouble(POSITION_TP));
}
}
}
}
}
}
//+------------------------------------------------------------------+
//| Helper: Check if EA has open positions |
//+------------------------------------------------------------------+
bool HasOpenPositions(ulong magic_num)
{
for(int i = PositionsTotal() - 1; i >= 0; i--)
{
if(PositionGetSymbol(i) == _Symbol)
{
if(PositionGetInteger(POSITION_MAGIC) == magic_num) return true;
}
}
return false;
}
//+------------------------------------------------------------------+
//| Helper: Manage GUI objects |
//+------------------------------------------------------------------+
void DrawZone(string obj_name, datetime t1, double p1, datetime t2, double p2, color clr)
{
if(ObjectFind(0, obj_name) < 0)
{
ObjectCreate(0, obj_name, OBJ_RECTANGLE, 0, t1, p1, t2, p2);
ObjectSetInteger(0, obj_name, OBJPROP_COLOR, clr);
ObjectSetInteger(0, obj_name, OBJPROP_BACK, true);
ObjectSetInteger(0, obj_name, OBJPROP_FILL, true);
ObjectSetInteger(0, obj_name, OBJPROP_HIDDEN, true);
}
else
{
ObjectSetInteger(0, obj_name, OBJPROP_TIME1, t1);
ObjectSetDouble(0, obj_name, OBJPROP_PRICE1, p1);
ObjectSetInteger(0, obj_name, OBJPROP_TIME2, t2);
ObjectSetDouble(0, obj_name, OBJPROP_PRICE2, p2);
}
}
//+------------------------------------------------------------------+
Key Changes for MT5 Architecture#include <Trade\Trade.mqh>: This removes the need for manual OrderSend structures and error logging, replacing them with trade.Buy(), trade.Sell(), and trade.PositionModify().Time Series Arrays: MT5 does not provide direct global access to High[], Low[], or Close[]. We instantiate local arrays on every tick and use CopyHigh, CopyLow, etc., to populate them. ArraySetAsSeries(..., true) is critical here; without it, index 0 would be the oldest bar on the chart, not the newest.Positions vs. Orders: The iteration loops inside HasOpenPositions and ManageTrailingStops have been rewritten to use PositionsTotal() and PositionGetTicket().Variable Typing: Variables like InpMagicNumber and ticket are updated to ulong (Unsigned Long), which is MT5's standard for ticket IDs and Magic Numbers.1.Open MetaEditor 5:Press F4 in your MT5 terminal to open the IDE.2.Create Expert Advisor:Select "New" -> "Expert Advisor (template)", name it Liquidity_Sweep_Scalper_MT5, and click Finish.3.Compile Code:Paste the provided C++ code and press F7 to compile.4.Enable Algo Trading:In your MT5 terminal, ensure the "Algo Trading" button on the top toolbar is pressed (it should turn green), then drag the EA onto your chart.