//+------------------------------------------------------------------+
//|                                         Equity Graph Go Home.mq4 |
//|                                       Copyright © 2011, Mediator |
//|                                                                  |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2011, Mediator"
#property link      ""

#property indicator_separate_window
#property indicator_buffers 1
#property indicator_color1 Blue

#property indicator_level1 0.0
#include <stderror.mqh>

//---- input parameters;


int barstime;
extern string    FirstPair="EURUSD"; 
extern string    SecondPair="USDCHF";
extern int stochentry = 80;
extern int stochexit = 20;    
 double Spread = 2;
 double Lots1 =1;
 double Lots2 = 1;
 bool UseProfitFactor = false;
bool UseOptimizer = false;
extern bool UseTimelessGraph = true;
bool Alerts_On = false;
bool bAlertSounded;
 extern bool    InvertFirstSymbol = false;
extern  bool    InvertSecondSymbol = false;
extern int K = 72;
extern int D = 1;
extern int S = 1;
string m = "";
double Value1,Value2;  
//---- buffers
double PFBuffer[];
double backarray[];
//double Uptrend[];
//double Dntrend[];
//double ExtMapBuffer[]; 
//double vect[], trend[];
datetime BarTime, AlertTime;
double stoch1,stoch2,diff;

   datetime dt;
   int OpenOrder = 0;
   int i;
   int Signal = 0;
   double OpenPriceF = 0.0;
   double OpenPriceS = 0.0;
   double ClosePriceF = 0.0;
   double ClosePriceS = 0.0;
   double Equ = 0.0;
   double Acc = 0.0;
   double prof =0.0;
   double verl =0.0;
   bool ontime = false;
   int trades = 0;
   double temp;
   int END1,END2;
 // double prof = 0.0;
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
   m = StringSubstr(Symbol(),6,StringLen(Symbol())-6);
      SecondPair = SecondPair+m;
      if (FirstPair == "" )
         FirstPair = Symbol();
      else
         FirstPair = FirstPair+m;
//---- indicators
 /*if(Lots1 <0) InvertFirstSymbol = true;
 if(Lots2 <0) InvertSecondSymbol = true;
 Lots1 = MathAbs(Lots1);
 Lots2 = MathAbs(Lots2);*/
   IndicatorBuffers(2);
   SetIndexStyle(0,DRAW_LINE);
   SetIndexBuffer(0,PFBuffer);
   SetIndexBuffer(1,backarray);
    //ArraySetAsSeries(Uptrend, true); 
  
   
   //Print(DoubleToStr(MarketInfo(FirstPair,MODE_TICKVALUE),4) + " : " + DoubleToStr(MarketInfo(SecondPair,MODE_TICKVALUE),4));
    
   
   //ArrayResize(backarray,Bars);
   
   
   
   return(0);
   
  }
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function                       |
//+------------------------------------------------------------------+
int deinit()
  {
//----
   
//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int start()
  {
   
   //if(dt == iTime(Symbol(),0,0) && ontime) return(0);
   //dt = iTime(Symbol(),0,0);
   ontime = true;
       //i=IndicatorCounted();
  
      
     i=MathMin(iBars(FirstPair,0),iBars(SecondPair,0))-K; 
//----
   Acc = 0.0;
   prof = 0.0;
   verl = 0.0; 
   Signal = 0;
   OpenOrder = 0;
   trades = 0;
   while(i>=0)
   {
      //Up Box
      
     
      if (OpenOrder != 0)
      {
         CheckExit();
         
         
      }
      
      //DrawEquity();
      
      if (OpenOrder == 0) 
      {
         GetSignal();
        // Print(Signal);
      }
      
         
     
      if(UseProfitFactor)
      {
         if(verl !=0.0 )
         {
            if (UseTimelessGraph)
            {
               backarray[trades] = (prof / MathAbs(verl));
            } else
            {
               PFBuffer[i+1] = (prof / MathAbs(verl));
            }          
         }   
      } else           
      {
         if (UseTimelessGraph)
         {
            backarray[trades] = Acc;
         } else
         {
            PFBuffer[i+1] = Acc;
         }
      }
       i--;
   }
   
   if (UseTimelessGraph)
   {
      int e = trades+1; 
      for(i=0; i<=trades; i++)
      {
         PFBuffer[i+1] = backarray[trades-i];
      }
      
   } else
   {
      e = Bars+ 1;
   }
   
    
   return(0);
  }

void GetSignal()
{
   string s;
   barstime = iBarShift(SecondPair,0,iTime(FirstPair,0,i));
   
   
   if ( InvertFirstSymbol)
                stoch1 = 100-iStochastic(FirstPair,0,K,D,S,0,0,0,barstime+1);
            else
               stoch1 = iStochastic(FirstPair,0,K,D,S,0,0,0,barstime+1);   
            if ( InvertSecondSymbol )
                stoch2 = 100-iStochastic(SecondPair,0,K,D,S,0,0,0,barstime+1);
            else
                stoch2 = iStochastic(SecondPair,0,K,D,S,0,0,0,barstime+1);
   
   
   double diff = MathAbs(stoch1-stoch2);
   if (diff >= stochentry && stoch1 > stoch2) 
   {
      Signal = -1;
      
      //Sell-Signal
      OpenPriceF = iOpen(FirstPair,0,barstime);
      OpenPriceS = iOpen(SecondPair,0,barstime);
      OpenOrder = 1;
      if (Alerts_On && bAlertSounded == false && BarTime > AlertTime ) 
      {
         Alert("SELL: " + FirstPair + " BUY: " + SecondPair +" : " + Period());
         bAlertSounded = true;
         AlertTime = TimeCurrent();
         Print(trades);
      }
      return(0);
   }
   if (diff >= stochentry && stoch1 < stoch2)
   {
      
      Signal = 1;
      //Buy-Signal
      OpenPriceF = iOpen(FirstPair,0,barstime);
      OpenPriceS = iOpen(SecondPair,0,barstime);
      OpenOrder = 1;
      if (Alerts_On && bAlertSounded == false && BarTime > AlertTime ) 
      {
         Alert("BUY: " + FirstPair + " SELL: " + SecondPair +" : " + Period());
         bAlertSounded = true;
         AlertTime = TimeCurrent();
         Print(trades);
      }
      return(0);
   } 
      Signal = 0;
   
   bAlertSounded = false;
}


void CheckExit()
{
   string s;
  barstime = iBarShift(SecondPair,0,iTime(FirstPair,0,i));
  Value1 = ConvertCurrency(1,FirstPair,"USD",iOpen(FirstPair,0,barstime),s);
  Value2 = ConvertCurrency(1,SecondPair,"USD",iOpen(SecondPair,0,barstime),s);
  
   if ( InvertFirstSymbol)
                stoch1 = 100-iStochastic(FirstPair,0,K,D,S,0,0,0,barstime+1);
            else
               stoch1 = iStochastic(FirstPair,0,K,D,S,0,0,0,barstime+1);   
            if ( InvertSecondSymbol )
                stoch2 = 100-iStochastic(SecondPair,0,K,D,S,0,0,0,barstime+1);
            else
                stoch2 = iStochastic(SecondPair,0,K,D,S,0,0,0,barstime+1);
   double diff = MathAbs(stoch1-stoch2);
   
   if(Signal==-1 && diff <= stochexit)
   {
      //if(iClose(Symbol(),0,i+1) >  iOpen(Symbol(),0,i+1))
      {
         OpenOrder = 0;
         ClosePriceF = iOpen(FirstPair,0,barstime);
         ClosePriceS = iOpen(SecondPair,0,barstime);
        // Equ = (OpenPrice- iOpen(Symbol(),0,i))-(Spread*Point);
         Equ =  ((OpenPriceF - ClosePriceF)/Point*Lots1*Value1) +  ((ClosePriceS-OpenPriceS)/Point*Lots2*Value2);
         //Equ =  ((OpenPriceF - iOpen(FirstPair,0,i))/Point) + ( (iOpen(SecondPair,0,i)-OpenPriceS)/Point) +(Spread);//   -(Spread*Point);
         Acc = Acc + Equ;
         if(Equ >= 0.0) prof = prof + Equ;
         if(Equ < 0.0 ) verl = verl + Equ;
         Equ = 0;
         Signal = 0;
         trades++;
         
         return(0);
      }
   }
   if(Signal==1  && diff <= stochexit)
   {
      //if( iClose(Symbol(),0,i+1) < iOpen(Symbol(),0,i+1))
      {
         OpenOrder = 0;
        // Equ = (iOpen(Symbol(),0,i)-OpenPrice);
        ClosePriceF = iOpen(FirstPair,0,barstime);
         ClosePriceS = iOpen(SecondPair,0,barstime);
        Equ = ((ClosePriceF- OpenPriceF)/Point*Lots1*Value1) + ( (OpenPriceS - ClosePriceS)/Point*Lots2*Value2);
       // Equ = ( (iOpen(FirstPair,0,i)- OpenPriceF)/Point) + ((OpenPriceS - iOpen(SecondPair,0,i))/Point)+(Spread);
         Acc = Acc + Equ;
         if(Equ >= 0.0) prof = prof + Equ;
         if(Equ < 0.0 ) verl = verl + Equ;
         Equ = 0;
         Signal = 0;
         trades++;
         
         return(0);
      }
   }
   return(0);
}

void DrawEquity()
{
   if(OpenOrder !=0)
   {
      if(Signal == -1)
      {
         Acc =Acc+  Equ;
         if(Equ >= 0.0) prof = prof + Equ;
         if(Equ < 0.0 ) verl = verl + Equ;
      }
      if(Signal == 1)
      {
         Acc =Acc+  Equ;
         if(Equ >= 0.0) prof = prof + Equ;
         if(Equ < 0.0 ) verl = verl + Equ;
      }
   }
}

double PointValueFor1Lot(string symbol)
//+------------------------------------------------------------------+
{
  // PtVal = TickValue * Point / TickSize;
  double result = MarketInfo(symbol,MODE_TICKVALUE)*MarketInfo(symbol,MODE_POINT)/MarketInfo(symbol,MODE_TICKSIZE) ;
  if(Digits == 5 || Digits == 3)
  {   
      result = result /10;
  }
  return ( result );
}

string AlltrimSpacesOnly(string s)//normal Metatrader functions behaviour
   {
   string r;
   r=StringTrimLeft(StringTrimRight(s));
   return(r);
   }
   
double ConvertCurrency(double pips,string contract,string currency,double forceprice,string &errormsg)
  {
  errormsg="OK";
  double res=0;
  double initpoints;
  string woncrrcy,crrcytest,final,appendix;
  int poscr=1;
  double pr;
  contract=AlltrimSpacesOnly(contract);
  currency=AlltrimSpacesOnly(currency);
  bool ctex=ContractExists(contract);
  if (ctex==false)
     {
     errormsg="INVALID CONTRACT.";
     return(res);
     }
  woncrrcy=SubstrBetween(contract,3,5);
  appendix="";
  if (StringLen(contract)>6)
     {
     appendix=SubstrBetween(contract,6,StringLen(contract));    
     }
  if (woncrrcy==currency)
     {     
     res=pips;
     return(res);
     }
  crrcytest=currency+woncrrcy;
  poscr=1;  
  if (ContractExists(StringConcatenate(crrcytest,appendix))==true)     
     final=StringConcatenate(crrcytest,appendix);
  else
     {
     crrcytest=StringConcatenate(woncrrcy,currency);
     poscr=2;
     if (ContractExists(StringConcatenate(crrcytest,appendix))==true)
        final=StringConcatenate(crrcytest,appendix);
     else
        {
        errormsg="CONVERSION IMPOSSIBLE."; // still, could be tried cascade conversions...
        return(res);
        }
     } 
  if (forceprice==0)
     {
     if (poscr==1)
        res=MarketInfo(contract,MODE_POINT)/MarketInfo(final,MODE_POINT)*pips/MarketInfo(final,MODE_ASK);
     else
        res=MarketInfo(contract,MODE_POINT)/MarketInfo(final,MODE_POINT)*pips*MarketInfo(final,MODE_BID);
     }       
  else
     {
     if (poscr==1)
        res=MarketInfo(contract,MODE_POINT)/MarketInfo(final,MODE_POINT)*pips/forceprice;
     else
        res=MarketInfo(contract,MODE_POINT)/MarketInfo(final,MODE_POINT)*pips*forceprice;
     }  
  return(res);
  }
  
bool ContractExists(string symbol)
  {
  int Gle;
  double data;
  bool res;
  data=MarketInfo(symbol,MODE_POINT);
  Gle=GetLastError();
  if (Gle!=ERR_UNKNOWN_SYMBOL)
     res=true;
  return(res);
  }
  
string SubstrBetween(string stri,int p1,int p2)
   {
   string res="";
   if (p2<p1||p1>StringLen(stri))
      return(res);
   if (p2>StringLen(stri))
      p2=StringLen(stri);
   for (int k=p1;k<=p2;k++)
      {
      res=StringConcatenate(res,StringElement(stri,k));
      }
   return(res);
   }
   
string StringElement(string s,int pos)
   {
   int g=0;
   string empty="";
   string given="x";
   if (pos<0||pos>StringLen(s)-1)
      return(empty);
   else
      {
      g=StringGetChar(s,pos);
      given=StringSetChar(given,0,g);
      return(given);   
      }
   }
   

