Summary: Gold Horizon EA is a stable MQL4 expert advisor for XAUUSD. It uses dual MA crossover with RSI confirmation, fixed stop loss/take profit, and daily loss limit. Suitable for H1 timeframe.




Gold Horizon EA is designed specifically for gold (XAUUSD) with a focus on stable, long-term operational consistency. The EA employs a dual moving average crossover strategy (fast EMA and slow EMA) to identify trend direction and entries. An RSI filter prevents entering during overbought or oversold extremes that often lead to reversals in gold. Each trade is protected by a fixed stop loss and take profit, and the EA includes a daily equity loss limit and maximum spread control to ensure stable operation even during volatile market conditions.

Recommended Timeframe: H1
Trading Logic:
1. Trend Direction: Fast EMA (12) crossing above Slow EMA (26) indicates uptrend; cross below indicates downtrend.
2. Entry Filter: RSI(14) must be between 30 and 70 to avoid overbought/oversold conditions.
3. Entry Signal: After crossover confirmed, enter on the following bar's open.
4. Risk Control: Fixed SL (350 points), fixed TP (700 points), max 1 trade at a time, daily loss limit 5%, max spread 40 points.

```mql4
//+------------------------------------------------------------------+
//| GoldHorizonEA.mq4 |
//| |
//| |
//+------------------------------------------------------------------+
#property copyright ""
#property link ""
#property version "1.00"
#property strict

//--- input parameters with comments
input double LotSize = 0.01; // Fixed lot size (0.01 lot for gold)
input int FastMAPeriod = 12; // Fast EMA period
input int SlowMAPeriod = 26; // Slow EMA period
input int RSIPeriod = 14; // RSI period for entry filter
input int RSIUpper = 70; // RSI upper threshold (avoid overbought)
input int RSILower = 30; // RSI lower threshold (avoid oversold)
input int StopLossPoints = 350; // Stop loss in points (350 points for gold)
input int TakeProfitPoints = 700; // Take profit in points (2:1 risk-reward)
input int MagicNumber = 202415; // Unique EA identifier
input int MaxSpread = 40; // Maximum allowed spread (in points)
input double DailyLossLimit = 5.0; // Daily loss limit in percentage of balance
input bool UseCloseOnFriday = true; // Close all trades before Friday 21:00

//--- global variables
double dailyStartBalance = 0;
datetime lastBarTime = 0;
bool isFridayCloseExecuted = false;

//+------------------------------------------------------------------+
//| Expert initialization function |
//+------------------------------------------------------------------+
int OnInit()
{
dailyStartBalance = AccountBalance();
lastBarTime = 0;
isFridayCloseExecuted = false;
return(INIT_SUCCEEDED);
}

//+------------------------------------------------------------------+
//| Expert deinitialization function |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
Comment("");
}

//+------------------------------------------------------------------+
//| Expert tick function |
//+------------------------------------------------------------------+
void OnTick()
{
// Daily equity protection
double currentEquity = AccountEquity();
double lossPercent = (dailyStartBalance - currentEquity) / dailyStartBalance * 100;
if(lossPercent >= DailyLossLimit)
{
Comment("Daily loss limit reached. No new trades.");
return;
}

// Friday close before weekend
if(UseCloseOnFriday && !isFridayCloseExecuted)
{
datetime currentTime = TimeCurrent();
if(TimeDayOfWeek(currentTime) == 5 && TimeHour(currentTime) >= 21)
{
CloseAllOrders();
isFridayCloseExecuted = true;
return;
}
if(TimeDayOfWeek(currentTime) != 5)
isFridayCloseExecuted = false;
}

// Spread filter
if(MarketInfo(Symbol(), MODE_SPREAD) > MaxSpread)
{
Comment("Spread too high");
return;
}

// New bar logic (H1)
if(Time[0] == lastBarTime)
return;
lastBarTime = Time[0];

// Check for existing position
if(CountPositions() > 0)
return;

// Calculate indicators on previous completed bar
double fastEMA = iMA(Symbol(), PERIOD_H1, FastMAPeriod, 0, MODE_EMA, PRICE_CLOSE, 1);
double slowEMA = iMA(Symbol(), PERIOD_H1, SlowMAPeriod, 0, MODE_EMA, PRICE_CLOSE, 1);
double fastEMA_prev = iMA(Symbol(), PERIOD_H1, FastMAPeriod, 0, MODE_EMA, PRICE_CLOSE, 2);
double slowEMA_prev = iMA(Symbol(), PERIOD_H1, SlowMAPeriod, 0, MODE_EMA, PRICE_CLOSE, 2);
double rsi = iRSI(Symbol(), PERIOD_H1, RSIPeriod, PRICE_CLOSE, 1);

int cmd = -1;
double sl = 0, tp = 0;

// Bullish crossover: fast EMA crosses above slow EMA, RSI not overbought
if(fastEMA_prev <= slowEMA_prev && fastEMA > slowEMA && rsi < RSIUpper)
{
cmd = OP_BUY;
sl = SymbolInfoDouble(Symbol(), SYMBOL_BID) - StopLossPoints * Point;
tp = SymbolInfoDouble(Symbol(), SYMBOL_BID) + TakeProfitPoints * Point;
}
// Bearish crossover: fast EMA crosses below slow EMA, RSI not oversold
else if(fastEMA_prev >= slowEMA_prev && fastEMA < slowEMA && rsi > RSILower)
{
cmd = OP_SELL;
sl = SymbolInfoDouble(Symbol(), SYMBOL_ASK) + StopLossPoints * Point;
tp = SymbolInfoDouble(Symbol(), SYMBOL_ASK) - TakeProfitPoints * Point;
}

if(cmd != -1)
{
int ticket = OrderSend(Symbol(), cmd, LotSize, (cmd==OP_BUY?Ask:Bid), 3, sl, tp, "Gold Horizon EA", MagicNumber, 0, clrNONE);
if(ticket < 0)
Print("OrderSend failed: ", GetLastError());
}
}

//+------------------------------------------------------------------+
//| Count open positions with this MagicNumber |
//+------------------------------------------------------------------+
int CountPositions()
{
int count = 0;
for(int i = OrdersTotal()-1; i >= 0; i--)
{
if(OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if(OrderSymbol() == Symbol() && OrderMagicNumber() == MagicNumber)
count++;
}
}
return count;
}

//+------------------------------------------------------------------+
//| Close all orders for this symbol and magic |
//+------------------------------------------------------------------+
void CloseAllOrders()
{
for(int i = OrdersTotal()-1; i >= 0; i--)
{
if(OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if(OrderSymbol() == Symbol() && OrderMagicNumber() == MagicNumber)
{
if(OrderType() == OP_BUY)
OrderClose(OrderTicket(), OrderLots(), Bid, 3, clrNONE);
else if(OrderType() == OP_SELL)
OrderClose(OrderTicket(), OrderLots(), Ask, 3, clrNONE);
}
}
}
}
//+------------------------------------------------------------------+
```
Reference: Original MQL4 code for educational purposes.
Disclaimer: Trading Forex and Gold involves high risk. This EA is provided as-is without any guarantee of profit. Test thoroughly on demo before live trading. Past performance does not guarantee future results.