MQL4 สำหรับเทรด Forex

MQL4 เป็นภาษาโปรแกรมสำหรับ MetaTrader 4 ใช้สร้าง Expert Advisors เทรดอัตโนมัติ Custom Indicators วิเคราะห์ตลาด Scripts จัดการ Orders

การเรียน MQL4 ช่วยสร้างระบบเทรดอัตโนมัติ ทดสอบ Strategy ด้วย Backtesting ลดอารมณ์ในการเทรด เพิ่มประสิทธิภาพการเทรด

Expert Advisor พื้นฐาน

//+------------------------------------------------------------------+
//| SimpleMA_EA.mq4 — Moving Average Crossover EA |
//| Expert Advisor สำหรับเทรดด้วย Moving Average Crossover |
//+------------------------------------------------------------------+
#property copyright "SiamCafe Blog"
#property link "https://siamcafe.net"
#property version "1.00"
#property strict

// Input Parameters
input int FastMA_Period = 10; // Fast MA Period
input int SlowMA_Period = 50; // Slow MA Period
input int MA_Method = MODE_SMA; // MA Method (SMA/EMA)
input double LotSize = 0.1; // Lot Size
input int StopLoss = 50; // Stop Loss (pips)
input int TakeProfit = 100; // Take Profit (pips)
input int MagicNumber = 12345; // Magic Number
input int Slippage = 3; // Slippage (pips)

// Global Variables
double fastMA_current, fastMA_previous;
double slowMA_current, slowMA_previous;

//+------------------------------------------------------------------+
//| Expert initialization function |
//+------------------------------------------------------------------+
int OnInit()
{
 Print("SimpleMA EA initialized");
 Print("Fast MA: ", FastMA_Period, " | Slow MA: ", SlowMA_Period);
 return(INIT_SUCCEEDED);
}

//+------------------------------------------------------------------+
//| Expert deinitialization function |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
 Print("SimpleMA EA removed. Reason: ", reason);
}

//+------------------------------------------------------------------+
//| Expert tick function |
//+------------------------------------------------------------------+
void OnTick()
{
 // คำนวณ Moving Averages
 fastMA_current = iMA(NULL, 0, FastMA_Period, 0, MA_Method, PRICE_CLOSE, 0);
 fastMA_previous = iMA(NULL, 0, FastMA_Period, 0, MA_Method, PRICE_CLOSE, 1);
 slowMA_current = iMA(NULL, 0, SlowMA_Period, 0, MA_Method, PRICE_CLOSE, 0);
 slowMA_previous = iMA(NULL, 0, SlowMA_Period, 0, MA_Method, PRICE_CLOSE, 1);

 // ตรวจสอบว่ามี Order อยู่หรือไม่
 if (CountOrders() > 0) return;

 // Buy Signal: Fast MA cross above Slow MA
 if (fastMA_previous < slowMA_previous && fastMA_current > slowMA_current)
 {
 OpenBuy();
 }

 // Sell Signal: Fast MA cross below Slow MA
 if (fastMA_previous > slowMA_previous && fastMA_current < slowMA_current)
 {
 OpenSell();
 }
}

//+------------------------------------------------------------------+
//| Open Buy Order |
//+------------------------------------------------------------------+
void OpenBuy()
{
 double sl = Ask - StopLoss * Point * 10;
 double tp = Ask + TakeProfit * Point * 10;

 int ticket = OrderSend(
 Symbol(), OP_BUY, LotSize, Ask, Slippage,
 sl, tp, "MA Cross Buy", MagicNumber, 0, clrGreen
 );

 if (ticket > 0)
 Print("Buy Order opened: #", ticket, " at ", Ask);
 else
 Print("Buy Order failed: ", GetLastError());
}

//+------------------------------------------------------------------+
//| Open Sell Order |
//+------------------------------------------------------------------+
void OpenSell()
{
 double sl = Bid + StopLoss * Point * 10;
 double tp = Bid - TakeProfit * Point * 10;

 int ticket = OrderSend(
 Symbol(), OP_SELL, LotSize, Bid, Slippage,
 sl, tp, "MA Cross Sell", MagicNumber, 0, clrRed
 );

 if (ticket > 0)
 Print("Sell Order opened: #", ticket, " at ", Bid);
 else
 Print("Sell Order failed: ", GetLastError());
}

//+------------------------------------------------------------------+
//| Count open orders |
//+------------------------------------------------------------------+
int CountOrders()
{
 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;
}

Custom Indicator

//+------------------------------------------------------------------+
//| TrendStrength.mq4 — Custom Trend Strength Indicator |
//| วัดความแรงของ Trend ด้วย ADX + MA Slope |
//+------------------------------------------------------------------+
#property copyright "SiamCafe Blog"
#property indicator_separate_window
#property indicator_minimum 0
#property indicator_maximum 100
#property indicator_buffers 2
#property indicator_color1 clrDodgerBlue
#property indicator_color2 clrOrangeRed
#property indicator_width1 2
#property indicator_width2 2
#property indicator_level1 25
#property indicator_level2 50
#property indicator_level3 75

input int ADX_Period = 14; // ADX Period
input int MA_Period = 20; // MA Period for Slope

double TrendBuffer[];
double SignalBuffer[];

int OnInit()
{
 SetIndexBuffer(0, TrendBuffer);
 SetIndexBuffer(1, SignalBuffer);
 SetIndexLabel(0, "Trend Strength");
 SetIndexLabel(1, "Signal");
 IndicatorShortName("Trend Strength (" +
 IntegerToString(ADX_Period) + "," +
 IntegerToString(MA_Period) + ")");
 return(INIT_SUCCEEDED);
}

int OnCalculate(const int rates_total,
 const int prev_calculated,
 const datetime &time[],
 const double &open[],
 const double &high[],
 const double &low[],
 const double &close[],
 const long &tick_volume[],
 const long &volume[],
 const int &spread[])
{
 int limit = rates_total - prev_calculated;
 if (prev_calculated > 0) limit++;

 for (int i = limit - 1; i >= 0; i--)
 {
 // ADX Value
 double adx = iADX(NULL, 0, ADX_Period, PRICE_CLOSE, MODE_MAIN, i);

 // MA Slope (normalized)
 double ma_now = iMA(NULL, 0, MA_Period, 0, MODE_EMA, PRICE_CLOSE, i);
 double ma_prev = iMA(NULL, 0, MA_Period, 0, MODE_EMA, PRICE_CLOSE, i + 5);
 double slope = MathAbs(ma_now - ma_prev) / Point / 10;
 slope = MathMin(slope, 50); // Cap at 50

 // Trend Strength = ADX * 0.6 + Slope * 0.4
 TrendBuffer[i] = adx * 0.6 + slope * 0.8;
 TrendBuffer[i] = MathMin(TrendBuffer[i], 100);

 // Signal Line (smoothed)
 if (i + 3 < rates_total)
 SignalBuffer[i] = (TrendBuffer[i] + TrendBuffer[i+1] + TrendBuffer[i+2]) / 3;
 }

 return(rates_total);
}
// การใช้งาน:
// Trend Strength > 50 = Strong Trend
// Trend Strength > 75 = Very Strong Trend
// Trend Strength < 25 = Weak/No Trend (Ranging)

Risk Management EA

//+------------------------------------------------------------------+
//| RiskManager.mq4 — Risk Management Functions |
//+------------------------------------------------------------------+
#property strict

input double RiskPercent = 2.0; // Risk % per trade
input double MaxDrawdownPct = 20.0; // Max Drawdown %
input int MaxOpenOrders = 3; // Max concurrent orders

//+------------------------------------------------------------------+
//| Calculate Lot Size based on Risk % |
//+------------------------------------------------------------------+
double CalculateLotSize(double stopLossPips)
{
 double accountBalance = AccountBalance();
 double riskAmount = accountBalance * (RiskPercent / 100.0);

 // Pip value
 double tickValue = MarketInfo(Symbol(), MODE_TICKVALUE);
 double tickSize = MarketInfo(Symbol(), MODE_TICKSIZE);
 double pipValue = tickValue / tickSize * Point * 10;

 if (pipValue == 0 || stopLossPips == 0) return 0.01;

 double lotSize = riskAmount / (stopLossPips * pipValue);

 // Normalize
 double minLot = MarketInfo(Symbol(), MODE_MINLOT);
 double maxLot = MarketInfo(Symbol(), MODE_MAXLOT);
 double lotStep = MarketInfo(Symbol(), MODE_LOTSTEP);

 lotSize = MathFloor(lotSize / lotStep) * lotStep;
 lotSize = MathMax(lotSize, minLot);
 lotSize = MathMin(lotSize, maxLot);

 return NormalizeDouble(lotSize, 2);
}

//+------------------------------------------------------------------+
//| Check if trading is allowed |
//+------------------------------------------------------------------+
bool CanTrade()
{
 // Check max orders
 if (CountOrders() >= MaxOpenOrders)
 {
 Print("Max orders reached: ", MaxOpenOrders);
 return false;
 }

 // Check drawdown
 double drawdown = 0;
 if (AccountBalance() > 0)
 drawdown = (AccountBalance() - AccountEquity()) / AccountBalance() * 100;

 if (drawdown > MaxDrawdownPct)
 {
 Print("Max drawdown exceeded: ", drawdown, "%");
 return false;
 }

 // Check spread
 double spread = MarketInfo(Symbol(), MODE_SPREAD);
 if (spread > 30) // More than 3 pips
 {
 Print("Spread too high: ", spread);
 return false;
 }

 return true;
}

//+------------------------------------------------------------------+
//| Trailing Stop |
//+------------------------------------------------------------------+
void TrailingStop(int trailingPips)
{
 double trailDistance = trailingPips * Point * 10;

 for (int i = OrdersTotal() - 1; i >= 0; i--)
 {
 if (!OrderSelect(i, SELECT_BY_POS)) continue;
 if (OrderSymbol() != Symbol()) continue;

 if (OrderType() == OP_BUY)
 {
 double newSL = Bid - trailDistance;
 if (newSL > OrderStopLoss() && newSL > OrderOpenPrice())
 {
 OrderModify(OrderTicket(), OrderOpenPrice(),
 newSL, OrderTakeProfit(), 0, clrGreen);
 }
 }
 else if (OrderType() == OP_SELL)
 {
 double newSL = Ask + trailDistance;
 if (newSL < OrderStopLoss() && newSL < OrderOpenPrice())
 {
 OrderModify(OrderTicket(), OrderOpenPrice(),
 newSL, OrderTakeProfit(), 0, clrRed);
 }
 }
 }
}

// Risk Management Summary:
// 1. Position Sizing ตาม Risk % (2% default)
// 2. Max Drawdown Limit (20% default)
// 3. Max Open Orders (3 default)
// 4. Spread Filter (ไม่เทรดเมื่อ Spread สูง)
// 5. Trailing Stop (ล็อคกำไร)

เคล็ดลับ MQL4

  • Strategy Tester: ทดสอบ EA ด้วย Strategy Tester ก่อนใช้จริงเสมอ
  • Risk Management: ใช้ Risk 1-2% ต่อ Trade ตั้ง Max Drawdown Limit
  • Magic Number: ใช้ Magic Number แยก Orders ของแต่ละ EA
  • Error Handling: ตรวจสอบ GetLastError() หลัง OrderSend/OrderModify
  • Optimization: อย่า Over-optimize ทดสอบกับหลาย Pairs และ Timeframes
  • Demo First: ทดสอบบน Demo Account อย่างน้อย 3 เดือนก่อนใช้เงินจริง

MQL4 คืออะไร

MetaQuotes Language 4 ภาษาโปรแกรมสำหรับ Expert Advisors Custom Indicators Scripts บน MetaTrader 4 สร้างระบบเทรดอัตโนมัติ วิเคราะห์ตลาด Forex คล้ายภาษา C