Create a new Expert Advisor in MetaEditor 4. MQL4 handles timeseries arrays (Close[]) and order execution (OrderSend) differently, so the math indexing and execution logic are adjusted.
Code: Select all
//+------------------------------------------------------------------+
//| ALMA_Pro_MT4.mq4 |
//+------------------------------------------------------------------+
#property strict
// --- Inputs ---
input int InpAlmaLength = 9; // ALMA Window Size
input double InpAlmaOffset = 0.85; // ALMA Offset
input double InpAlmaSigma = 6.0; // ALMA Sigma
input int InpMacdFast = 12; // MACD Fast
input int InpMacdSlow = 26; // MACD Slow
input int InpMacdSignal = 9; // MACD Signal
input int InpAtrPeriod = 14; // ATR Period
input double InpSlAtrMult = 1.5; // SL ATR Multiplier
input double InpRrRatio = 2.0; // Risk/Reward Ratio
input double InpLotSize = 0.1; // Fixed Lot Size
input int InpMagic = 123456; // Magic Number
void OnTick() {
static datetime lastBar = 0;
if(Time[0] == lastBar) return; // Execute strictly on bar close
if(OrdersTotal() > 0) return; // Prevent overlapping trades
// Calculate ALMA for the last two closed bars
double alma1 = CalculateALMA(1, InpAlmaLength, InpAlmaOffset, InpAlmaSigma);
double alma2 = CalculateALMA(2, InpAlmaLength, InpAlmaOffset, InpAlmaSigma);
double close1 = Close[1];
double close2 = Close[2];
// Fetch MACD and ATR data
double macdMain = iMACD(Symbol(), 0, InpMacdFast, InpMacdSlow, InpMacdSignal, PRICE_CLOSE, MODE_MAIN, 1);
double macdSig = iMACD(Symbol(), 0, InpMacdFast, InpMacdSlow, InpMacdSignal, PRICE_CLOSE, MODE_SIGNAL, 1);
double hist1 = macdMain - macdSig; // MACD Histogram
double atr = iATR(Symbol(), 0, InpAtrPeriod, 1);
// Entry Conditions
bool longCross = (close1 > alma1 && close2 <= alma2);
bool shortCross = (close1 < alma1 && close2 >= alma2);
if(longCross && hist1 > 0) {
double sl = NormalizeDouble(close1 - (atr * InpSlAtrMult), Digits);
double tp = NormalizeDouble(close1 + ((close1 - sl) * InpRrRatio), Digits);
int ticket = OrderSend(Symbol(), OP_BUY, InpLotSize, Ask, 3, sl, tp, "ALMA Long", InpMagic, 0, clrGreen);
if(ticket > 0) lastBar = Time[0];
}
else if(shortCross && hist1 < 0) {
double sl = NormalizeDouble(close1 + (atr * InpSlAtrMult), Digits);
double tp = NormalizeDouble(close1 - ((sl - close1) * InpRrRatio), Digits);
int ticket = OrderSend(Symbol(), OP_SELL, InpLotSize, Bid, 3, sl, tp, "ALMA Short", InpMagic, 0, clrRed);
if(ticket > 0) lastBar = Time[0];
}
}
// Custom Gaussian Distribution ALMA Calculation
double CalculateALMA(int shift, int length, double offset, double sigma) {
double m = offset * (length - 1);
double s = length / sigma;
double wSum = 0.0, res = 0.0;
for(int i = 0; i < length; i++) {
double w = MathExp(-(MathPow(i - m, 2)) / (2 * s * s));
// Map i=0 to the oldest bar, and i=(length-1) to the newest bar in the window
res += Close[shift + (length - 1 - i)] * w;
wSum += w;
}
return wSum > 0 ? res / wSum : 0.0;
}