Files
ironsan2kk-pixel 6450d1efc6 Fix download links
2026-06-08 10:36:15 +02:00

222 lines
13 KiB
Plaintext

// ★★★ EA_SingleLogic_LongOnly ★★★
//---------------------------------------------
// (1) Input parameters
//---------------------------------------------
// --- Parameters for Magic_A
input double SARStep = 0.001; // SAR acceleration factor increment
input double SARMaxStep = 0.2; // Maximum SAR acceleration factor
input double TPPips = 90; // Take Profit in pips
input double SLPips = 70; // Stop Loss in pips
// --- Other settings
input double MaxSpreadPips = 3.0; // Maximum allowed spread (pips)
input int SlippagePips = 3; // Allowed slippage (pips)
input double LotSize = 0.1; // Fixed lot size
input int MaxOpenBuyPositions = 1; // Maximum number of open BUY positions
//---------------------------------------------
// (2) Magic number
//---------------------------------------------
input int Magic_A = 12345;
//---------------------------------------------
// (3) Internal state variables
//---------------------------------------------
datetime prevTime_A = 0;
//---------------------------------------------
// (4) ENUM: Exit / Entry signals
//---------------------------------------------
enum SignalType
{
NO_SIGNAL = 0,
BUY_ENTRY,
BUY_EXIT
};
//---------------------------------------------
// (6) New bar detection
//---------------------------------------------
bool IsNewBar(int timeframe, datetime &lastBarTime)
{
datetime currentBar = iTime(Symbol(), timeframe, 0);
if (currentBar != lastBarTime)
{
lastBarTime = currentBar;
return true;
}
return false;
}
//---------------------------------------------
// (7) Pip size calculation
//---------------------------------------------
double Pip()
{
return (Digits == 5 || Digits == 3) ? Point * 10 : Point;
}
//---------------------------------------------
// Convert pips to points (for slippage)
int PipToPoint(double pips)
{
return (int)MathRound(pips * Pip() / Point);
}
//---------------------------------------------
// (11) Count open BUY orders for this EA
//---------------------------------------------
int CountOrdersByTypeThisEA(int type)
{
int count = 0;
for (int i = OrdersTotal() - 1; i >= 0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderSymbol() == Symbol() &&
OrderMagicNumber() == Magic_A &&
OrderType() == type)
{
count++;
}
}
}
return count;
}
//---------------------------------------------
// (12) Check if a new BUY order can be placed
//---------------------------------------------
bool CanPlaceNewBuy()
{
return CountOrdersByTypeThisEA(OP_BUY) < MaxOpenBuyPositions;
}
//---------------------------------------------
// (14) Exit signal logic
//---------------------------------------------
SignalType ExitSignalA()
{
double SAR0 = iSAR(_Symbol, 0, SARStep, SARMaxStep, 0);
double SAR1 = iSAR(_Symbol, 0, SARStep, SARMaxStep, 1);
double SAR2 = iSAR(_Symbol, 0, SARStep, SARMaxStep, 2);
if ((Low[1] > SAR1 && Close[0] <= SAR0) ||
(High[2] < SAR2 && High[1] < SAR1 && High[0] < SAR0))
return BUY_EXIT;
return NO_SIGNAL;
}
//---------------------------------------------
// (15) Entry signal logic
//---------------------------------------------
SignalType EntrySignalA()
{
double SAR1 = iSAR(_Symbol, 0, SARStep, SARMaxStep, 1);
double SAR2 = iSAR(_Symbol, 0, SARStep, SARMaxStep, 2);
double SAR3 = iSAR(_Symbol, 0, SARStep, SARMaxStep, 3);
if ((High[2] < SAR2 && Close[1] >= SAR1) ||
(Low[3] > SAR3 && Low[2] > SAR2 && Low[1] > SAR1))
return BUY_ENTRY;
return NO_SIGNAL;
}
//---------------------------------------------
// (21) Exit processing (BUY only)
//---------------------------------------------
void HandleExitA(SignalType sig)
{
if (sig != BUY_EXIT) return;
double closePrice = Bid;
for (int i = OrdersTotal() - 1; i >= 0; i--)
{
if (OrderSelect(i, SELECT_BY_POS, MODE_TRADES))
{
if (OrderMagicNumber() == Magic_A &&
OrderSymbol() == _Symbol &&
OrderType() == OP_BUY)
{
int ticket = OrderTicket();
double lots = OrderLots();
bool result = OrderClose(
ticket,
lots,
closePrice,
PipToPoint(SlippagePips),
clrOrange
);
if (!result)
PrintFormat("❌ OrderClose failed. Ticket=%d Error=%d", ticket, GetLastError());
else
PrintFormat("✅ Order closed successfully. Ticket=%d", ticket);
}
}
}
}
//---------------------------------------------
// (22) Entry processing (BUY only)
//---------------------------------------------
void HandleEntryA(SignalType sig)
{
if (sig != BUY_ENTRY) return;
// Spread check
double spreadPips = (Ask - Bid) / Pip();
if (spreadPips > MaxSpreadPips)
{
PrintFormat("❌ Spread too high (%.1f pips). Entry skipped.", spreadPips);
return;
}
if (!CanPlaceNewBuy()) return;
double price = Ask;
double sl = NormalizeDouble(price - SLPips * Pip(), Digits);
double tp = NormalizeDouble(price + TPPips * Pip(), Digits);
int slippagePoints = PipToPoint(SlippagePips);
int ticket = OrderSend(
_Symbol,
OP_BUY,
LotSize,
price,
slippagePoints,
sl,
tp,
"Magic_A Entry",
Magic_A,
0,
clrOrange
);
if (ticket > 0)
PrintFormat("✅ Magic_A BUY order placed. Ticket=%d", ticket);
else
PrintFormat("❌ Magic_A OrderSend failed. Error=%d", GetLastError());
}
//---------------------------------------------
// (27) Main OnTick processing
//---------------------------------------------
void OnTick()
{
// EXIT: evaluated on every tick and executed immediately if conditions are met
SignalType exitSig = ExitSignalA();
HandleExitA(exitSig);
// ENTRY: evaluated only on a new bar
if (IsNewBar(PERIOD_CURRENT, prevTime_A))
{
SignalType entrySig = EntrySignalA();
HandleEntryA(entrySig);
}
}
// --- END ---