//+------------------------------------------------------------------+
//|                                            MacdPatternTrader.mq4 |
//|                                                     FORTRADER.RU |
//|                                              http://FORTRADER.RU |
//+------------------------------------------------------------------+
/*
 
Looking for an interpreter for the English version of the magazine on partnership.

//добавлено ограничение на одну сделку в одном направлении
//исправлена ошибка приводившая к не правильному открытию по сигналу
//добавлен параметр maxbarABpoint задающий количество баров между точками для генерации сигнала на вход, всегда должен быть 1 или больше. 

Страница обсуждения советника, последние новости и обновления:
http://fortrader.ru/services/eaVersion/single?id=8

Download last EA version:
http://fortrader.ru/services/eaVersion/single?id=8


*/
#property copyright "FORTRADER.RU"
#property link "http://FORTRADER.RU"

extern int stoplossbars = 6; // count bars for find minimum/maximum for enter stoploss
extern int takeprofitbars = 20;
extern int stoploss_deviation = 10;
extern int fastema = 5;
extern int slowema = 13;
extern double maxur = 0.0045;
extern double maxur1=0.0030;
extern double minur = -0.0045;
extern double minur1=-0.0030;
extern int maxbarABpoint = 1;

extern string x = "Настройки MA:";
extern int perema1 = 7;
extern int perema2 = 21;
extern int persma3 = 98;
extern int perema4 = 365;

extern double Lots = 0.1;

int buy, sell;
int nummodb, nummods;
int flaglot;
int start() {

    AOPattern();
    ActivePosManager();

    return (0);
}
int aop_maxur, aop_minur, aop_oksell, aop_okbuy, numberbar, numberbarsell, s_otstup,s,bars_bup,stops,stops1,bs,sstops,sstops1;
double max1,max2,max3,min1,min2,min3;

void AOPattern() {

    if (Digits == 5 || Digits == 3) {
        s_otstup = stoploss_deviation * 10;
    }


    //загружаем индикаторы
    double macdcurr = iMACD(NULL, 0, fastema, slowema, 1, PRICE_CLOSE, MODE_MAIN, 1);
    double macdlast = iMACD(NULL, 0,  fastema, slowema, 1, PRICE_CLOSE, MODE_MAIN, 2);
    double macdlast3 = iMACD(NULL, 0,  fastema, slowema, 1, PRICE_CLOSE, MODE_MAIN, 3);
    
   //Нашли первый заход за 45 и дали отмашку искать максимум
   if(macdcurr>maxur){s=1;bars_bup=bars_bup+1;}
   
   //ищем цену первого бугорка выше 45, этот максимум должен быть максимальный который был за 45 и цена еще невыходила до уровня ниже 45
   if(s==1 && macdcurr<macdlast && macdlast>macdlast3 && macdlast>max1 && stops==0){max1=macdlast;}
   
   //если был заход за 45 вниз останавливаем и переходим к поиску второго бугорка
   if(max1>0 &&macdcurr<maxur){stops=1;}
   
   //а если зашли за минимум то снова ищем первый максимум
   if(macdcurr<maxur1 ){stops=0;max1=0;s=0;}
   
    //ищем второй максимум который выше чем первый
    if(stops==1 && macdcurr>maxur && macdcurr<macdlast && macdlast>macdlast3 && macdlast>max1 && macdlast>max2 && stops1==0){max2=macdlast;Print("max2 "+max2);} 
    
    //если был заход за 45 вниз останавливаем и переходим к поиску третьего бугорка
    if(max2>0 &&macdcurr<maxur){stops1=1;}
    
    //а вдруг если зашли за минимум то снова ищем второй максимум
    if(macdcurr<maxur1 ){stops1=0;max2=0;}
    
    //ищем трейти максимум ниже второго  
   if(stops1==1 && macdcurr>maxur1&& macdlast>maxur1&& macdlast3>maxur1&&  macdcurr<macdlast && macdlast>macdlast3 && macdlast<max2  && aop_oksell==0 ){max3=macdlast;Print("max1 "+max1);Print("max2 "+max2);Print("max3"+max3);aop_oksell=1;} 
   
   

    if ( aop_oksell==1) {
   stops=0;max1=0; s=0;max2=0;max3=0;stops1=0;
        OrderSend(Symbol(), OP_SELL, Lots, Bid, 3, StopLoss(0), TakeProfit(0), "FORTRADER.RU", 16385, 0, Red);
        aop_oksell = 0;
        aop_maxur = 0;
        nummods = 0;
        flaglot = 0;
    }

    //Нашли первый заход за 45 и дали отмашку искать максимум
   if(macdcurr<minur){bs=1;}
    
   //ищем цену первого бугорка выше 45, этот максимум должен быть максимальный который был за 45 и цена еще невыходила до уровня ниже 45
   if(bs==1 && macdcurr>macdlast && macdlast<macdlast3 && macdlast<min1 && sstops==0){min1=macdlast;}
   
   //если был заход за 45 вниз останавливаем и переходим к поиску второго бугорка
   if(min1<0 &&macdcurr>minur){sstops=1;bs=0;}
   
   //а вдруг если зашли за минимум то снова ищем первый максимум
   if(macdcurr>minur1 ){sstops=0;min1=0;bs=0;}
      
   //ищем второй максимум выше 45
    if(sstops==1 && macdcurr<minur&& macdcurr>macdlast && macdlast<macdlast3 && macdlast<min1 && macdlast<min2 && sstops1==0){min2=macdlast;} 
    
    //45 вниз останавливаем и переходим к поиску третьего бугорка
    if(min2!=0 &&macdcurr>minur){sstops1=1;sstops=0;}
   
   //а вдруг если зашли за минимум то снова ищем второй максимум
   if(macdcurr>minur1 ){sstops1=0;min2=0;}
   
   ///ищем трейти максимум выше 45
   if(sstops1==1 && macdcurr<minur1&& macdlast<minur1&& macdlast3<minur1&&  macdcurr>macdlast && macdlast<macdlast3 && macdlast>min2 && aop_okbuy==0 ){min3=macdlast;Print("min1"+min1);Print("mi2"+min2);Print("mi3"+min3);aop_okbuy=1;sstops1=0;} 

    if (aop_okbuy == 1) {
       min1=0; bs=0;min2=0;min3=0;
       sstops=0;sstops1=0;

        OrderSend(Symbol(), OP_BUY, Lots, Ask, 3, StopLoss(1), TakeProfit(1), "FORTRADER.RU", 16385, 0, Red);
        aop_okbuy = 0;
        aop_minur = 0;
        nummodb = 0;
        flaglot = 0;
    }

}

//проверяет есть ли стоп ордера
int Chpos(int type) {
    int i;
    for (i = 1; i <= OrdersTotal(); i++) {
        if (OrderSelect(i - 1, SELECT_BY_POS) == true) {
            if (OrderType() == OP_BUY && OrderSymbol() == Symbol() && type == 1) {
                return (1);
            }
            if (OrderType() == OP_SELL && OrderSymbol() == Symbol() && type == 0) {
                return (1);
            }
        }
    }
    return (0);
}

double StopLoss(int type) {
    double stoploss;
    if (type == 0) {
        stoploss = High[iHighest(NULL, 0, MODE_HIGH, stoplossbars, 1)] + s_otstup * Point;
        return (stoploss);
    }
    if (type == 1) {
        stoploss = Low[iLowest(NULL, 0, MODE_LOW, stoplossbars, 1)] - s_otstup * Point;
        return (stoploss);
    }
return 0;
}

double TakeProfit(int type) {
    int t = 0, stop = 0;
    double takeprofit;

    if (type == 0) {
        while (stop == 0) {
            takeprofit = Low[iLowest(NULL, 0, MODE_LOW, takeprofitbars, t)];
            if (takeprofit > Low[iLowest(NULL, 0, MODE_LOW, takeprofitbars, t + takeprofitbars)]) {
                takeprofit = Low[iLowest(NULL, 0, MODE_LOW, takeprofitbars, t + takeprofitbars)];
                t = t + takeprofitbars;
            } else {
                stop = 1;
                return (takeprofit);
            }
        }
    }

    if (type == 1) {
        while (stop == 0) {
            takeprofit = High[iHighest(NULL, 0, MODE_HIGH, takeprofitbars, t)];
            if (takeprofit < High[iHighest(NULL, 0, MODE_HIGH, takeprofitbars, t + takeprofitbars)]) {
                takeprofit = High[iHighest(NULL, 0, MODE_HIGH, takeprofitbars, t + takeprofitbars)];
                t = t + takeprofitbars;
            } else {
                stop = 1;
                return (takeprofit);
            }
        }
    }
return 0;
}

void ActivePosManager() {
    double ema1 = iMA(NULL, 0, perema1, 0, MODE_EMA, PRICE_CLOSE, 1);
    double ema2 = iMA(NULL, 0, perema2, 0, MODE_EMA, PRICE_CLOSE, 1);
    double sma1 = iMA(NULL, 0, persma3, 0, MODE_SMA, PRICE_CLOSE, 1);
    double ema3 = iMA(NULL, 0, perema4, 0, MODE_EMA, PRICE_CLOSE, 1);

    for (int i = 0; i < OrdersTotal(); i++) {
        OrderSelect(i, SELECT_BY_POS, MODE_TRADES);
        if (OrderType() == OP_BUY && OrderProfit() > 5 && Close[1] > ema2 && nummodb == 0) {
            OrderClose(OrderTicket(), NormalizeDouble(OrderLots() / 3, 2), Bid, 3, Violet);
            nummodb++;
        }

        if (OrderType() == OP_BUY && OrderProfit() > 5 && High[1] > (sma1 + ema3) / 2 && nummodb == 1) {
            OrderClose(OrderTicket(), NormalizeDouble(OrderLots() / 2, 2), Bid, 3, Violet);
            nummodb++;
        }

        if (OrderType() == OP_SELL && OrderProfit() > 5 && Close[1] < ema2 && nummods == 0) {
            OrderClose(OrderTicket(), NormalizeDouble(OrderLots() / 3, 2), Ask, 3, Violet);
            nummods++;
        }

        if (OrderType() == OP_SELL && OrderProfit() > 5 && Low[1] < (sma1 + ema3) / 2 && nummods == 1) {
            OrderClose(OrderTicket(), NormalizeDouble(OrderLots() / 2, 2), Ask, 3, Violet);
            nummods++;
        }
    }

}