Skip to content

Instantly share code, notes, and snippets.

@b1rdex
Created Feb 6, 2014
Embed
What would you like to do?
#property copyright ""
#property link ""
#property description "moving averages"
#define MAGICMA 123123123
input double MaximumRisk = 0.02; // maximum risk (% of depo)
input bool willYouTradeBuyHands = false; // if true, I'll check every opened order for creator (possible slowing?)
// MA periods
input int MAPeriod1 = 12;
input int MAPeriod2 = 24;
input int MAPeriod3 = 48;
input int MAPeriod4 = 144;
int MAMethod = MODE_EMA;
input int MAgap = 50; // (MAmax - MAmin) distance in points where we start to think to buy/sell
input int stopLoss = 50;
input bool useTakeProfit = false; // true → take profit, false → trailing stop loss
input int takeProfit = 100;
int TrailingStop = stopLoss; // if we don't use take profit, we use trailing stop loss with walue of stopLoss
input int openOrderStrategy = 1; // strategy to open orders
input double openOrderCoef = 3;
double getLotSize()
{
double lot = NormalizeDouble(AccountFreeMargin()*MaximumRisk/1000.0,1);
return MathMax(0.1, lot);
}
void getMAs(double &mas[], int backShift)
{
mas[0] = iMA(NULL, 0, MAPeriod1, 0, MAMethod, PRICE_CLOSE, backShift);
mas[1] = iMA(NULL, 0, MAPeriod2, 0, MAMethod, PRICE_CLOSE, backShift);
mas[2] = iMA(NULL, 0, MAPeriod3, 0, MAMethod, PRICE_CLOSE, backShift);
mas[3] = iMA(NULL, 0, MAPeriod4, 0, MAMethod, PRICE_CLOSE, backShift);
}
double getMAgap(int backShift)
{
double mas[3];
getMAs(mas, backShift);
double highest = mas[ArrayMaximum(mas)];
double lowest = mas[ArrayMinimum(mas)];
return highest - lowest;
}
void CheckForOpen()
{
int currentMAgap = getMAgap(1);
if (currentMAgap <= MAgap*Point && getOpenOrderSwitchBasedDecision()) {
if (isItSellConditions()) { // sell conditions
double sellStopLoss = Ask + stopLoss*Point;
double sellTakeProfit = useTakeProfit ? (Bid - takeProfit*Point) : 0;
OrderSend(Symbol(), OP_SELL, getLotSize(), Bid, 3, sellStopLoss, sellTakeProfit, "", MAGICMA, 0, Red);
return;
} else { // buy conditions
double buyStopLoss = Bid - stopLoss*Point;
double buyTakeProfit = useTakeProfit ? (Ask + takeProfit*Point) : 0;
OrderSend(Symbol(), OP_BUY, getLotSize(), Ask, 3, buyStopLoss, buyTakeProfit, "", MAGICMA, 0, Blue);
return;
}
}
}
bool isItSellConditions()
{
return Open[1] > Close[1]; // FIXME: we need more complex way to decide should we short or long
}
bool getOpenOrderSwitchBasedDecision()
{
switch (openOrderStrategy) {
case 1:
return MathAbs(Open[1] - Close[1]) >= openOrderCoef*MAgap*Point; // previous bar is bigger than MAgap*coef
case 2:
return (getMAgap(3) > getMAgap(2) && getMAgap(2) > getMAgap(1)) // moving averages gap is closing or opening for last 3 bars
|| (getMAgap(3) < getMAgap(2) && getMAgap(2) < getMAgap(1));
break;
case 3:
return (MathAbs(Open[1] - Close[1]) >= openOrderCoef*MAgap*Point) && (getMAgap(2) > getMAgap(1)
|| (getMAgap(2) < getMAgap(1)));
default:
return false;
}
}
void moveStopLosses() // simple trailing stop algorithm
{
for (int cnt=0, total = OrdersTotal(); cnt < total; cnt++) {
OrderSelect(cnt, SELECT_BY_POS, MODE_TRADES);
if (OrderType() <= OP_SELL && OrderSymbol() == Symbol()) {
if (OrderType()==OP_BUY) { // it's long
if (Bid - OrderOpenPrice() > Point*TrailingStop) {
if (OrderStopLoss() < Bid - Point*TrailingStop) {
OrderModify(OrderTicket(), OrderOpenPrice(), Bid-Point*TrailingStop, OrderTakeProfit(), 0, Green);
return;
}
}
} else { // it's short
if (OrderOpenPrice() - Ask > Point*TrailingStop) {
if ((OrderStopLoss()>(Ask + Point*TrailingStop)) || (OrderStopLoss()==0)) {
OrderModify(OrderTicket(), OrderOpenPrice(), Ask+Point*TrailingStop, OrderTakeProfit(), 0, Red);
return;
}
}
}
}
}
}
void OnTick()
{
if (Bars<100 || IsTradeAllowed() == false) {
Alert("Not enough bars data or I can't trade");
return;
}
if (Volume[0]>1) return; // act only on new bars
moveStopLosses();
CheckForOpen();
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment