//+------------------------------------------------------------------+
//|                                                      MAMA_v1.mq4 |
//|                                Copyright © 2009, TrendLaboratory |
//|            http://finance.groups.yahoo.com/group/TrendLaboratory |
//|                                   E-mail: igorad2003@yahoo.co.uk |
//+------------------------------------------------------------------+
//mod osc
// List of Prices:
// Price    = 0 - Close  
// Price    = 1 - Open  
// Price    = 2 - High  
// Price    = 3 - Low  
// Price    = 4 - Median Price   = (High+Low)/2  
// Price    = 5 - Typical Price  = (High+Low+Close)/3  
// Price    = 6 - Weighted Close = (High+Low+Close*2)/4
// Price    = 7 - Heiken Ashi Close  
// Price    = 8 - Heiken Ashi Open
// Price    = 9 - Heiken Ashi High
// Price    =10 - Heiken Ashi Low
#property copyright "Copyright © 2009, TrendLaboratory"
#property link      "http://finance.groups.yahoo.com/group/TrendLaboratory"
#property indicator_separate_window
#property indicator_buffers 4
#property indicator_color1  Yellow
#property indicator_width1  1  
#property indicator_color2  SkyBlue
#property indicator_width2  1
#property indicator_color3  SkyBlue
#property indicator_width3  2
#property indicator_color4  Tomato
#property indicator_width4  2 
//---- 
extern int     TimeFrame         =     60;   //Time Frame in min
extern int     Price             =     4;   //Price Mode (0...10)
extern double  FastLimit         =   0.5;   //Laguerre Period(or Order,max=10)
extern double  SlowLimit         =  0.05;   //Adaptive Factor Length
extern int     SignalMode        =     1;   //Switch of Signal mode(0-off,1-on)
extern int     AlertMode         =     0;   //Sound Alert switch(0...2) 
extern int     WarningMode       =     0;   //Warning Mode (0-off,1-on)
extern string   note_Price  = "0C 1O 2H 3L 4Md 5Tp 6WghC"; 
extern string   _________   = "Md(HL/2)4,Tp(HLC/3)5,Wgh(HLCC/4)6";
extern string   HA_price_   = "7haC 8haO 9haH 10haL";
extern string   _______     = "haC=(O+H+L+C)/4; haO=(O[i1]+C[i1])/2;haH=Max(H,haO,haC);haL=Min(L,hO,hC)";
extern string   TimeFrames = "M1;5,15,30,60H1;240H4;1440D1;10080W1;43200MN";
//---- 
double MAMA[];
double FAMA[];
double UpSignal[];
double DnSignal[];
double sig[];
//----
double haClose[], haOpen[], haHigh[], haLow[];
int    draw_begin, pBars, mcnt_bars, per; 
string short_name1, short_name2;
datetime pTime;
bool   UpTrendAlert=false, DnTrendAlert=false;
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
{
//---- 
   SetIndexStyle(0,DRAW_LINE);
//   SetIndexStyle(1,DRAW_NONE);
   SetIndexStyle(2,DRAW_ARROW);
   SetIndexArrow(2,158);
   SetIndexStyle(3,DRAW_ARROW);
   SetIndexArrow(3,158);
   
   if(TimeFrame == 0 || TimeFrame < Period()) TimeFrame = Period();
   per = 2/SlowLimit;   
   draw_begin=2*per*TimeFrame/Period();
//---- 
   switch(TimeFrame)
   {
   case 1     : string TF = "M1"; break;
   case 5     : TF = "M5"; break;
   case 15    : TF = "M15"; break;
   case 30    : TF = "M30"; break;
   case 60    : TF = "H1"; break;
   case 240   : TF ="H4"; break;
   case 1440  : TF="D1"; break;
   case 10080 : TF="W1"; break;
   case 43200 : TF="MN"; break;
   default    : TF="CurrentTF";
   } 
   short_name1 = "MAMA";
   short_name2 = "FAMA";
   IndicatorShortName(short_name1+"("+DoubleToStr(FastLimit,2)+","+DoubleToStr(SlowLimit,2)+")"+" "+TF);
   SetIndexLabel(0,short_name1+"("+DoubleToStr(FastLimit,2)+","+DoubleToStr(SlowLimit,2)+")"+" "+TF);
   SetIndexLabel(1,short_name2+"("+DoubleToStr(FastLimit,2)+","+DoubleToStr(SlowLimit,2)+")"+" "+TF);
   SetIndexLabel(2,"UpSignal");
   SetIndexLabel(3,"DnSignal");
   
   SetIndexDrawBegin(0,draw_begin);
//   SetIndexDrawBegin(1,draw_begin);
   SetIndexDrawBegin(2,draw_begin);
   SetIndexDrawBegin(3,draw_begin);
   
//---- 
   IndicatorBuffers(6);
   SetIndexBuffer(0,MAMA);
   SetIndexBuffer(5,FAMA);   
   SetIndexBuffer(2,UpSignal);
   SetIndexBuffer(3,DnSignal);
   SetIndexBuffer(4,sig);
//---- 
   return(0);
}
//+------------------------------------------------------------------+
//| MAMA_v1                                              |
//+------------------------------------------------------------------+
int start()
{
   int limit, y, i, shift, cnt_bars=IndicatorCounted(); 
   double price[], mMAMA[], mFAMA[], Smooth[], Detrender[], Q1[], I1[], JL[], JQ[], I2[], Q2[], 
          Re[], Im[], period[], Phase[], mUpsig[], mDnsig[], trend[];
    
   if(TimeFrame!=Period()) int mBars = iBars(NULL,TimeFrame); else mBars = Bars;   
   
   if(mBars != pBars)
   {
   ArrayResize(price,mBars);
   ArrayResize(mMAMA,mBars);
   ArrayResize(mFAMA,mBars);
   ArrayResize(Smooth,mBars);
   ArrayResize(Detrender,mBars);
   ArrayResize(Q1,mBars);
   ArrayResize(I1,mBars);
   ArrayResize(JL,mBars);
   ArrayResize(JQ,mBars);
   ArrayResize(I2,mBars);
   ArrayResize(Q2,mBars);
   ArrayResize(Re,mBars);
   ArrayResize(Im,mBars);
   ArrayResize(period,mBars);
   ArrayResize(Phase,mBars);     
      if(Price > 6 && Price <= 10)
      {
      ArrayResize(haClose,mBars);
      ArrayResize(haOpen,mBars);
      ArrayResize(haHigh,mBars);
      ArrayResize(haLow,mBars);
      }
  
      if(SignalMode>0)
      {
      ArrayResize(trend,mBars);
      ArrayResize(mUpsig,mBars);
      ArrayResize(mDnsig,mBars);
      }
   pBars = mBars;
   }  
   
   if(cnt_bars<1)
   {
      for(i=Bars-1;i>0;i--) 
      {
      MAMA[i]=EMPTY_VALUE;
      FAMA[i]=EMPTY_VALUE;
      UpSignal[i]=EMPTY_VALUE;
      DnSignal[i]=EMPTY_VALUE;
      }
   mcnt_bars = 0;
   }
//---- 
   if(mcnt_bars > 0) mcnt_bars--;
   
   for(y=mcnt_bars;y<mBars;y++)
   {
      if(Price <= 6) price[y] = iMA(NULL,TimeFrame,1,0,0,Price,mBars-y-1);   
      else
      if(Price > 6 && Price <= 10) price[y] = HeikenAshi(TimeFrame,Price-7,mBars-y-1);
   
   if(y >= 3) Smooth[y] = (4*price[y] + 3*price[y-1] + 2*price[y-2] + price[y-3])/10.0;
   Detrender[y] = (0.0962*Smooth[y] + 0.5769*Smooth[y-2] - 0.5769*Smooth[y-4] - 0.0962*Smooth[y-6])*(0.075*period[y-1] + 0.54);
   
   Q1[y] = (0.0962*Detrender[y] + 0.5769*Detrender[y-2] - 0.5769*Detrender[y-4] - 0.0962*Detrender[y-6])*(0.075*period[y-1] + 0.54);
	I1[y] = Detrender[y-3];     
     
   JL[y] = (0.0962*I1[y] + 0.5769*I1[y-2] - 0.5769*I1[y-4] - 0.0962*I1[y-6])*(0.075*period[y-1] + 0.54);
	JQ[y] = (0.0962*Q1[y] + 0.5769*Q1[y-2] - 0.5769*Q1[y-4] - 0.0962*Q1[y-6])*(0.075*period[y-1] + 0.54);
    
   I2[y] = I1[y] - JQ[y];
	Q2[y] = Q1[y] + JL[y];     
        
   I2[y] = 0.2*I2[y] + 0.8*I2[y-1];
	Q2[y] = 0.2*Q2[y] + 0.8*Q2[y-1];
	
	Re[y] = I2[y]*I2[y-1] + Q2[y]*Q2[y-1];
	Im[y] = I2[y]*Q2[y-1] - Q2[y]*I2[y-1];
	
	Re[y] = 0.2*Re[y] + 0.8*Re[y-1];
	Im[y] = 0.2*Im[y] + 0.8*Im[y-1];
	double rad2Deg = 45.0/MathArctan(1);
   
   if(Im[y] != 0 && Re[y] != 0) period[y] = 360.0/MathArctan(Im[y]/Re[y])/rad2Deg;
   
	if(period[y] > 1.5 *period[y-1]) period[y] = 1.5*period[y-1];
	if(period[y] < 0.67*period[y-1]) period[y] = 0.67*period[y-1];
	if(period[y] <  6) period[y] = 6;
	if(period[y] > 50) period[y] = 50;
	
	period[y] = 0.2*period[y] + 0.8*period[y-1];
	
	if(I1[y] != 0) Phase[y] = MathArctan(Q1[y]/I1[y])*rad2Deg;
	
	double DeltaPhase = Phase[y-1] - Phase[y];
	if(DeltaPhase < 1) DeltaPhase = 1;
	
	double Alpha = FastLimit / DeltaPhase;
	
	if(Alpha < SlowLimit) Alpha = SlowLimit;
	if(Alpha > FastLimit) Alpha = FastLimit;
	
	mMAMA[y] = Alpha*price[y] + (1.0 - Alpha)*mMAMA[y-1];
	mFAMA[y] = 0.5*Alpha*mMAMA[y] + (1.0 - 0.5*Alpha)*mFAMA[y-1];
    
      
      if(SignalMode > 0)
      {
      trend[y] = trend[y-1];
      if(mFAMA[y]-mMAMA[y] < 0 && trend[y-1]<=0) trend[y]= 1; 
      if(mFAMA[y]-mMAMA[y] > 0 && trend[y-1]>=0) trend[y]=-1;  
               
         if(trend[y] > 0)
         {  
            if(trend[y-1] <= 0)
            { 
            mUpsig[y] = mFAMA[y]-mMAMA[y];
            if (WarningMode>0 && y==mBars-1) PlaySound("alert2.wav");
            }
            else
            mUpsig[y]= EMPTY_VALUE; 
         mDnsig[y]= EMPTY_VALUE;
         }
         else
         if (trend[y] < 0) 
         {
            if(trend[y-1] >= 0) 
            {
            mDnsig[y] =mFAMA[y]-mMAMA[y];
            if (WarningMode>0 && y==mBars-1) PlaySound("alert2.wav");  
            }
            else
            mDnsig[y]= EMPTY_VALUE; 
            mUpsig[y]= EMPTY_VALUE;
         }
      }                               
      
      if(TimeFrame == Period()) 
      {
      MAMA[mBars-y-1] = mMAMA[y]-mFAMA[y];
      FAMA[mBars-y-1] = mFAMA[y];
            
         if(SignalMode > 0)
         {
         UpSignal[mBars-y-1] = mUpsig[y];
         DnSignal[mBars-y-1] = mDnsig[y];
         }
      }
      mcnt_bars = mBars-1;
   }
   
   if(TimeFrame > Period())
   { 
      if(cnt_bars>0) cnt_bars--;
      limit = Bars-cnt_bars+TimeFrame/Period()-1;
      
      for(shift=0,y=0;shift<limit;shift++)
      {
      if (Time[shift] < iTime(NULL,TimeFrame,y)) y++; 
      MAMA[shift] = mMAMA[mBars-y-1]-mFAMA[mBars-y-1];
      FAMA[shift] = mFAMA[mBars-y-1];   
         if(SignalMode > 0)
         {
         UpSignal[shift] = mUpsig[mBars-y-1];
         DnSignal[shift] = mDnsig[mBars-y-1];
         sig[mBars-y-1] = trend[y];
         }
      }
   }
//----------   
   string Message;
   
   if (trend[mBars-2]<0 && trend[mBars-1]>0 && !UpTrendAlert && AlertMode == 1)
	{
	Message = " "+Symbol()+" TF M"+TimeFrame+" chart M"+Period()+": MAMA Signal for BUY";
	if (isNewBar()) Alert (Message); 
	UpTrendAlert=true; DnTrendAlert=false;
	} 
	else 	  
	if (trend[mBars-2]>0 && trend[mBars-1]<0 && !DnTrendAlert && AlertMode == 1)
	{
	Message = " "+Symbol()+" TF M"+TimeFrame+" chart M"+Period()+": MAMA Signal for SELL";
	if (isNewBar()) Alert (Message); 
	DnTrendAlert=true; UpTrendAlert=false;
	} 	         
   return(0);
}
double HeikenAshi(int tf,int price,int bar)
{ 
   if(bar == iBars(NULL,TimeFrame)- 1) 
   {
   haClose[bar] = iClose(NULL,tf,bar);
   haOpen[bar]  = iOpen(NULL,tf,bar);
   haHigh[bar]  = iHigh(NULL,tf,bar);
   haLow[bar]   = iLow(NULL,tf,bar);
   }
   else
   {
   haClose[bar] = (iOpen(NULL,tf,bar)+iHigh(NULL,tf,bar)+iLow(NULL,tf,bar)+iClose(NULL,tf,bar))/4;
   haOpen[bar]  = (haOpen[bar+1]+haClose[bar+1])/2;
   haHigh[bar]  = MathMax(iHigh(NULL,tf,bar),MathMax(haOpen[bar], haClose[bar]));
   haLow[bar]   = MathMin(iLow(NULL,tf,bar),MathMin(haOpen[bar], haClose[bar]));
   }
   
   switch(price)
   {
   case 0: return(haClose[bar]);break;
   case 1: return(haOpen[bar]);break;
   case 2: return(haHigh[bar]);break;
   case 3: return(haLow[bar]);break;
   }
}     
bool isNewBar()
{
   bool res=false;
   if (iTime(NULL,TimeFrame,0)!=pTime)
   {
   res=true;
   pTime=iTime(NULL,TimeFrame,0);
   }   
   return(res);
}        		
             
            
            
            
Comments