Redraw indicator for new candles. Help with my first indicator written.

 

Hello, this is the first indicator I have written and it hast some flaws. I would be happy I someone could help.

What it should do:

  • A: Draw 3 candle long line and and arrow on candle which's close crosses the small EMA (10) from below, if it is above the big EMA (200)
  • B: Contrary draw 3 candle long line and an arrow on candle which's close crosses the small EMA (10) from above, if it is below the big EMA (200)
  • C: Give an alert if this happens

It works okay on past candles, however

  • nothing is added to new candles and I get alerts If candle closes above EMA for A and B.
  • also the arrow is added to wrong candles, even though the line is dawn to the correct ones

I hope some can help me out.

Also, this is probably not the most elegant way of coding, sorry for that.
I'd also be happy about any improvement suggestions (efficiency etc.), since I don't have a background in programming. 

//+------------------------------------------------------------------+
//|                               Close Cross MA Indicator Alert.mq4 |
//|                                              Copyright 2017, xxx |
//|                                                                  |
//+------------------------------------------------------------------+
#property copyright "Copyright 2017, xxx"
#property link      ""
#property version   "1.00"
#property strict
#property indicator_chart_window
#property indicator_buffers 8
#property indicator_color1 clrBlue
#property indicator_color2 clrBlue
#property indicator_color3 clrBlue
#property indicator_color4 clrBlue
#property indicator_color5 clrBlue
#property indicator_color6 clrBlue
#property indicator_color7 clrBlue
#property indicator_color8 clrBlue
#property indicator_width1 2
#property indicator_width2 2
#property indicator_width3 2
#property indicator_width4 2
#property indicator_width5 2
#property indicator_width6 2
#property indicator_width7 2
#property indicator_width8 2
#property indicator_style1 STYLE_SOLID
#property indicator_style2 STYLE_SOLID
#property indicator_style3 STYLE_SOLID
#property indicator_style4 STYLE_SOLID
#property indicator_style5 STYLE_SOLID
#property indicator_style6 STYLE_SOLID
#property indicator_style7 STYLE_SOLID
#property indicator_style8 STYLE_SOLID

//Inputs
extern int       TimeFrame = 0;
extern int       InputMAval_big=200;
extern int       InputMAtype_big=1; // 0 for Simple (SMA), 1 for Exponential (EMA), 2 for Smoothed (SMMA), 3 for LWMA
extern int       InputMAshift_big=0;
extern int       InputMAprice_big=0; // 0=close, 1=open, 2=high, 3=low, 4=Median, 5=Typical, 6=Weighted

extern int       InputMAval_small=10;
extern int       InputMAtype_small=1; // 0 for Simple (SMA), 1 for Exponential (EMA), 2 for Smoothed (SMMA), 3 for LWMA
extern int       InputMAshift_small=0;
extern int       InputMAprice_small=0; // 0=close, 1=open, 2=high, 3=low, 4=Median, 5=Typical, 6=Weighted
extern int       DnArrowDist=60;
extern int       UpArrowDist=20;
extern int       IndicatorDist=2000;
extern bool    AlertAbove  = true,
               AlertBelow  = true,
               AlertSound  = true;
//Buffer Arrays               
double BodyHigh[],BodyLow[],BodyHigh2[], BodyLow2[],
       BodyHigh3[],BodyLow3[],BodyHigh4[], BodyLow4[];
           
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int OnInit()
  {
//--- indicator buffers mapping
   SetIndexBuffer(0,BodyHigh);
   SetIndexBuffer(1,BodyLow);
   SetIndexBuffer(2,BodyHigh2);
   SetIndexBuffer(3,BodyLow2);
   SetIndexBuffer(4,BodyHigh3);
   SetIndexBuffer(5,BodyLow3);
   SetIndexBuffer(6,BodyHigh4);
   SetIndexBuffer(7,BodyLow4);
   SetIndexStyle(0,DRAW_LINE);
   SetIndexStyle(1,DRAW_LINE);
   SetIndexStyle(2,DRAW_LINE);
   SetIndexStyle(3,DRAW_LINE);
   SetIndexStyle(4,DRAW_LINE);
   SetIndexStyle(5,DRAW_LINE);
   SetIndexStyle(6,DRAW_LINE);
   SetIndexStyle(7,DRAW_LINE);
//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int OnCalculate(const int rates_total,
                const int prev_calculated,
                const datetime &time[],
                const double &open[],
                const double &high[],
                const double &low[],
                const double &close[],
                const long &tick_volume[],
                const long &volume[],
                const int &spread[])
  {
//---
   
   //--- Indicator

   for(int i = IndicatorDist;i>=1;i--)
   {
      double test_high=MathMax(close[i],open[i]);
      double test_low=MathMin(close[i],open[i]);
      static int AlertPrevTime = 0;
      double test_close = iClose(NULL,TimeFrame,i);
      double test_close2 = iClose(NULL,TimeFrame,i+1);
      double EMA_big = iMA(NULL, TimeFrame, InputMAval_big, InputMAshift_big, InputMAtype_big, InputMAprice_big, i);
      double EMA_small = iMA(NULL, TimeFrame, InputMAval_small, InputMAshift_small, InputMAtype_small, InputMAprice_small, i);
      double EMA_small2 = iMA(NULL, TimeFrame, InputMAval_small, InputMAshift_small, InputMAtype_small, InputMAprice_small, i+1);
      string soundfile = "alert.wav";

      // Draw line and arrow to candle if its close crosses EMA
      // Because line is 3 candles long, check if buffer is occupied and use different one if so
      if(EMA_small<EMA_big) {
	//check if previous candle was above its EMA value, if so and current is below execute
        if((test_close2>EMA_small2) && (test_close<EMA_small)){
          if(BodyLow[i]!=EMPTY_VALUE){
            if(BodyLow2[i]!=EMPTY_VALUE){
               if(BodyLow3[i]!=EMPTY_VALUE){
                   BodyLow4[i]=test_low;
                   BodyLow4[i-1]=test_low;
                   BodyLow4[i-2]=test_low;
                   BodyLow4[i-3]=test_low;
               }else{
                BodyLow3[i]=test_low;
                BodyLow3[i-1]=test_low;
                BodyLow3[i-2]=test_low;
                BodyLow3[i-3]=test_low;
               }
             }else{
              BodyLow2[i]=test_low;
              BodyLow2[i-1]=test_low;
              BodyLow2[i-2]=test_low;
              BodyLow2[i-3]=test_low;
             }
          }
          else{
            BodyLow[i]=test_low;
            BodyLow[i-1]=test_low;
            BodyLow[i-2]=test_low;
            BodyLow[i-3]=test_low;
          }
         //Draw arraw down to obove the candle 
         string name = "name"+IntegerToString(i);
         ObjectDelete(name);
         ObjectCreate(name, OBJ_ARROW, 0, Time[i], High[i]+DnArrowDist*Point);
         ObjectSet(name, OBJPROP_STYLE, STYLE_SOLID);
         ObjectSet(name, OBJPROP_WIDTH, 2);
         ObjectSet(name, OBJPROP_ARROWCODE, SYMBOL_ARROWDOWN);
         ObjectSet(name, OBJPROP_COLOR,Red);
          
          //Give alert if close cross has happened
          if (Time[0] > AlertPrevTime){
            if(AlertAbove)Alert("["+Symbol()+"]" + " Close below EMA -- Sell");
            if(AlertSound)PlaySound(soundfile);
            AlertPrevTime  = Time[0];
          }
        }
      }
      if(EMA_small>EMA_big) {
        if((test_close2<EMA_small2) && (test_close>EMA_small)){
          if(BodyHigh[i]!=EMPTY_VALUE){
            if(BodyHigh2[i]!=EMPTY_VALUE){
               if(BodyHigh3[i]!=EMPTY_VALUE){
                   BodyHigh4[i]=test_high;
                   BodyHigh4[i-1]=test_high;
                   BodyHigh4[i-2]=test_high;
                   BodyHigh4[i-3]=test_high;
               }else{
                BodyHigh3[i]=test_high;
                BodyHigh3[i-1]=test_high;
                BodyHigh3[i-2]=test_high;
                BodyHigh3[i-3]=test_high;
               }
             }else{
              BodyHigh2[i]=test_high;
              BodyHigh2[i-1]=test_high;
              BodyHigh2[i-2]=test_high;
              BodyHigh2[i-3]=test_high;
             }
          }
          else{
            BodyHigh[i]=test_high;
            BodyHigh[i-1]=test_high;
            BodyHigh[i-2]=test_high;
            BodyHigh[i-3]=test_high;
          }
          
         string name = "name"+IntegerToString(i);
         ObjectDelete(name);
         ObjectCreate(name, OBJ_ARROW, 0, Time[i], Low[i]-UpArrowDist*Point); //draw an up arrow
         ObjectSet(name, OBJPROP_STYLE, STYLE_SOLID);
         ObjectSet(name, OBJPROP_WIDTH, 2);
         ObjectSet(name, OBJPROP_ARROWCODE, SYMBOL_ARROWUP);
         ObjectSet(name, OBJPROP_COLOR,Blue);
          
          if (Time[0] > AlertPrevTime){
            if(AlertAbove)Alert("["+Symbol()+"]" + " Close above EMA -- Buy");
            if(AlertSound)PlaySound(soundfile);
            AlertPrevTime  = Time[0];
          }
        }
      }
   }
   
//--- return value of prev_calculated for next call
   return(rates_total);
  }
//+------------------------------------------------------------------+

 
  1. Why did you post your MT4 question in the Root / MT5 Indicators section instead of the MQL4 section, (bottom of the Root page?)
              General rules and best pratices of the Forum. - General - MQL5 programming forum
    Next time post in the correct place. The moderators will likely move this thread there soon.

  2. extern int       IndicatorDist=2000;
    int OnCalculate(...){
    //---
       
       //--- Indicator
    
       for(int i = IndicatorDist;i>=1;i--)
          double test_high=MathMax(close[i],open[i]);
    
    What happens if your chart doesn't have 2000 bars? Why are you recomputing every bar every tick?
              How to do your lookbacks correctly.

  3. There is a difference between the arrays passed to OnCalculate (e.g. low[]) and the predefined variables (e.g. Low[].) The predefined variables are all ordered AsSeries. The passed arrays have no default direction.
    To determine the indexing direction of time[], open[], high[], low[], close[], tick_volume[], volume[] and spread[], call ArrayGetAsSeries(). In order not to depend on default values, you should unconditionally call the ArraySetAsSeries() function for those arrays, which are expected to work with.
              Event Handling Functions - Functions - Language Basics - MQL4 Reference

  4. if((test_close2>EMA_small2) && (test_close<EMA_small)){
              if(BodyLow[i]!=EMPTY_VALUE){
    Since you haven't assigned a value to the buffer yet, when will that condition ever be true?

  5.    for(int i = IndicatorDist;i>=1;i--){
    :
                       BodyLow4[i]=test_low;
                       BodyLow4[i-1]=test_low;
                       BodyLow4[i-2]=test_low;
                       BodyLow4[i-3]=test_low;
    What happens when i becomes one?

  6. string name = "name"+IntegerToString(i);
             ObjectDelete(name);
             ObjectCreate(name, OBJ_ARROW, 0,
    The moment a new bar occurs you will have an arrow with a name that doesn't match the bar index (i.e. name1 on bar 2.) Then you will try to create another name1
    • Use time[i] not i
    • Use non-series index (Bars - 1 - i).
    • Don't use objects. Why don't you use an buffer of type arrow.
 

Thank you very much whroeder1 for you great help!

I have implemented most of your suggestions and the redrawing already works.

Why did you post your MT4 question in the Root / MT5 Indicators section instead of the MQL4 section, (bottom of the Root page?) 
          General rules and best pratices of the Forum. - General - MQL5 programming forum


Sorry for this, I will do next time.


Since you haven't assigned a value to the buffer yet, when will that condition ever be true?

This will be true when the candle is occupied by a line of the previous candle, because the lines are 3 candles long. I.e. When candle 5 is triggered buffer will be assigned to the next 3 candles. Thus, when candle 3 is also triggered it cannot use buffer, but instead has to use buffer2.

The way I coded it now only provides a 1 candle long line for new candles, since I cannot assign the buffer to future candles. Do you have a suggestion how this can be solved?


//+------------------------------------------------------------------+
//|                               Close Cross MA Indicator Alert.mq4 |
//|                                              Copyright 2017, xxx |
//|                                                                  |
//+------------------------------------------------------------------+
#property copyright "Copyright 2017, xxx"
#property link      ""
#property version   "1.00"
#property strict
#property indicator_chart_window
#property indicator_buffers 12
#property indicator_color1 clrBlue
#property indicator_color2 clrBlue
#property indicator_color3 clrBlue
#property indicator_color4 clrBlue
#property indicator_color5 clrBlue
#property indicator_color6 clrBlue
#property indicator_color7 clrBlue
#property indicator_color8 clrBlue
#property indicator_color9 clrBlue
#property indicator_color10 clrBlue
#property indicator_color11 clrBlue
#property indicator_color12 clrRed
#property indicator_width1 2
#property indicator_width2 2
#property indicator_width3 2
#property indicator_width4 2
#property indicator_width5 2
#property indicator_width6 2
#property indicator_width7 2
#property indicator_width8 2
#property indicator_width9 2
#property indicator_width10 2
#property indicator_style1 STYLE_SOLID
#property indicator_style2 STYLE_SOLID
#property indicator_style3 STYLE_SOLID
#property indicator_style4 STYLE_SOLID
#property indicator_style5 STYLE_SOLID
#property indicator_style6 STYLE_SOLID
#property indicator_style7 STYLE_SOLID
#property indicator_style8 STYLE_SOLID
#property indicator_style9 STYLE_SOLID
#property indicator_style10 STYLE_SOLID

//Inputs
extern int       TimeFrame = 0;
extern int       InputMAval_big=200;
extern int       InputMAtype_big=1; // 0 for Simple (SMA), 1 for Exponential (EMA), 2 for Smoothed (SMMA), 3 for LWMA
extern int       InputMAshift_big=0;
extern int       InputMAprice_big=0; // 0=close, 1=open, 2=high, 3=low, 4=Median, 5=Typical, 6=Weighted

extern int       InputMAval_small=10;
extern int       InputMAtype_small=1; // 0 for Simple (SMA), 1 for Exponential (EMA), 2 for Smoothed (SMMA), 3 for LWMA
extern int       InputMAshift_small=0;
extern int       InputMAprice_small=0; // 0=close, 1=open, 2=high, 3=low, 4=Median, 5=Typical, 6=Weighted
extern int       DnArrowDist=20;
extern int       UpArrowDist=20;
extern bool    AlertAbove  = true,
               AlertBelow  = true,
               AlertSound  = true;
//Buffer Arrays               
double BodyHigh[],BodyLow[],BodyHigh2[], BodyLow2[],
       BodyHigh3[],BodyLow3[],BodyHigh4[], BodyLow4[],
       BodyHigh5[],BodyLow5[],ArrowUp[],ArrowDown[];
           
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int OnInit()
  {
//--- indicator buffers mapping
   SetIndexBuffer(0,BodyHigh);
   SetIndexBuffer(1,BodyLow);
   SetIndexBuffer(2,BodyHigh2);
   SetIndexBuffer(3,BodyLow2);
   SetIndexBuffer(4,BodyHigh3);
   SetIndexBuffer(5,BodyLow3);
   SetIndexBuffer(6,BodyHigh4);
   SetIndexBuffer(7,BodyLow4);
   SetIndexBuffer(8,BodyHigh5);
   SetIndexBuffer(9,BodyLow5);
   SetIndexBuffer(10,ArrowUp);
   SetIndexBuffer(11,ArrowDown);
   SetIndexStyle(0,DRAW_LINE);
   SetIndexStyle(1,DRAW_LINE);
   SetIndexStyle(2,DRAW_LINE);
   SetIndexStyle(3,DRAW_LINE);
   SetIndexStyle(4,DRAW_LINE);
   SetIndexStyle(5,DRAW_LINE);
   SetIndexStyle(6,DRAW_LINE);
   SetIndexStyle(7,DRAW_LINE);
   SetIndexStyle(8,DRAW_LINE);
   SetIndexStyle(9,DRAW_LINE);
   SetIndexStyle(10,DRAW_ARROW);
   SetIndexStyle(11,DRAW_ARROW);
   SetIndexArrow(10, 241);
   SetIndexArrow(11, 242);
//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int OnCalculate(const int rates_total,
                const int prev_calculated,
                const datetime &time[],
                const double &open[],
                const double &high[],
                const double &low[],
                const double &close[],
                const long &tick_volume[],
                const long &volume[],
                const int &spread[])
   {
//---
   
   //--- Indicator
   int lookback = 3;
   for(int iBar = rates_total-1-MathMax(lookback,prev_calculated);iBar>=1;--iBar)
   {
      ArraySetAsSeries(close, true);
      ArraySetAsSeries(open, true);
      double test_high=MathMax(close[iBar],open[iBar]);
      double test_low=MathMin(close[iBar],open[iBar]);
      static int AlertPrevTime = 0;
      double test_close = iClose(NULL,TimeFrame,iBar);
      double test_close2 = iClose(NULL,TimeFrame,iBar+1);
      double EMA_big = iMA(NULL, TimeFrame, InputMAval_big, InputMAshift_big, InputMAtype_big, InputMAprice_big, iBar);
      double EMA_small = iMA(NULL, TimeFrame, InputMAval_small, InputMAshift_small, InputMAtype_small, InputMAprice_small, iBar);
      double EMA_small2 = iMA(NULL, TimeFrame, InputMAval_small, InputMAshift_small, InputMAtype_small, InputMAprice_small, iBar+1);
      string soundfile = "alert.wav";

      // Draw line to candle if its close crosses EMA
      // Beacuse line is 3 candles long, check if buffer is occupied and use different one if so
      if(EMA_small<EMA_big) {
        if((test_close2>EMA_small2) && (test_close<EMA_small)){
            if(BodyLow[iBar]!=EMPTY_VALUE){
                     if(BodyLow2[iBar]!=EMPTY_VALUE){
                              if(BodyLow3[iBar]!=EMPTY_VALUE){
                                    if(BodyLow4[iBar]!=EMPTY_VALUE){
                                             if(iBar>2){
                                                BodyLow5[iBar]=test_low;
                                                BodyLow5[iBar-1]=test_low;
                                                BodyLow5[iBar-2]=test_low;
                                                BodyLow5[iBar-3]=test_low;
                                              }
                                              if(iBar==2){
                                                BodyLow5[iBar]=test_low;
                                                BodyLow5[iBar-1]=test_low;
                                                BodyLow5[iBar-2]=test_low;
                                              }
                                              if(iBar==1){
                                                BodyLow5[iBar]=test_low;
                                                BodyLow5[iBar-1]=test_low;
                                              }
                                        
                                        }else{
                                           if(iBar>2){
                                             BodyLow4[iBar]=test_low;
                                             BodyLow4[iBar-1]=test_low;
                                             BodyLow4[iBar-2]=test_low;
                                             BodyLow4[iBar-3]=test_low;
                                           }
                                           if(iBar==2){
                                             BodyLow4[iBar]=test_low;
                                             BodyLow4[iBar-1]=test_low;
                                             BodyLow4[iBar-2]=test_low;
                                           }
                                           if(iBar==1){
                                             BodyLow4[iBar]=test_low;
                                             BodyLow4[iBar-1]=test_low;
                                           }
                                        }
                              }else{
                               if(iBar>2){
                                 BodyLow3[iBar]=test_low;
                                 BodyLow3[iBar-1]=test_low;
                                 BodyLow3[iBar-2]=test_low;
                                 BodyLow3[iBar-3]=test_low;
                               }
                               if(iBar==2){
                                 BodyLow3[iBar]=test_low;
                                 BodyLow3[iBar-1]=test_low;
                                 BodyLow3[iBar-2]=test_low;
                                }
                                if(iBar==1){
                                 BodyLow3[iBar]=test_low;
                                 BodyLow3[iBar-1]=test_low;
                                }
                              }
                     }else{
                       if(iBar>2){
                        BodyLow2[iBar]=test_low;
                        BodyLow2[iBar-1]=test_low;
                        BodyLow2[iBar-2]=test_low;
                        BodyLow2[iBar-3]=test_low;
                       }
                       if(iBar==2){
                        BodyLow2[iBar]=test_low;
                        BodyLow2[iBar-1]=test_low;
                        BodyLow2[iBar-2]=test_low;
                       }
                       if(iBar==1){
                        BodyLow2[iBar]=test_low;
                        BodyLow2[iBar-1]=test_low;
                       }
                     }
             }
             else{
               if(iBar>2){
                  BodyLow[iBar]=test_low;
                  BodyLow[iBar-1]=test_low;
                  BodyLow[iBar-2]=test_low;
                  BodyLow[iBar-3]=test_low;
               }
               if(iBar==2){
                  BodyLow[iBar]=test_low;
                  BodyLow[iBar-1]=test_low;
                  BodyLow[iBar-2]=test_low;
               }
               if(iBar==1){
                  BodyLow[iBar]=test_low;
                  BodyLow[iBar-1]=test_low;
               }
            }        
            //Draw arrow down - obove the candle 
            ArrowDown[iBar]=High[iBar]+DnArrowDist*Point;
             
            //Give alert if close cross has happened
            if (Time[0] > AlertPrevTime){
              if(AlertAbove)Alert("["+Symbol()+"]" + " Close below EMA -- Sell");
              if(AlertSound)PlaySound(soundfile);
              AlertPrevTime  = Time[0];
             }
        
        }
     
     }
      if(EMA_small>EMA_big) {
        if((test_close2<EMA_small2) && (test_close>EMA_small)){
          if(BodyHigh[iBar]!=EMPTY_VALUE){
                     if(BodyHigh2[iBar]!=EMPTY_VALUE){
                              if(BodyHigh3[iBar]!=EMPTY_VALUE){
                                    if(BodyHigh4[iBar]!=EMPTY_VALUE){
                                              if(iBar>2){
                                                BodyHigh5[iBar]=test_high;
                                                BodyHigh5[iBar-1]=test_high;
                                                BodyHigh5[iBar-2]=test_high;
                                                BodyHigh5[iBar-3]=test_high;
                                              }
                                              if(iBar==2){
                                                BodyHigh5[iBar]=test_high;
                                                BodyHigh5[iBar-1]=test_high;
                                                BodyHigh5[iBar-2]=test_high;
                                              }
                                              if(iBar==1){
                                                BodyHigh5[iBar]=test_high;
                                                BodyHigh5[iBar-1]=test_high;
                                              }
                                      }else{
                                        if(iBar>2){
                                          BodyHigh4[iBar]=test_high;
                                          BodyHigh4[iBar-1]=test_high;
                                          BodyHigh4[iBar-2]=test_high;
                                          BodyHigh4[iBar-3]=test_high;
                                        }
                                        if(iBar==2){
                                          BodyHigh4[iBar]=test_high;
                                          BodyHigh4[iBar-1]=test_high;
                                          BodyHigh4[iBar-2]=test_high;
                                        }
                                        if(iBar==1){
                                          BodyHigh4[iBar]=test_high;
                                          BodyHigh4[iBar-1]=test_high;
                                        }
                                      }
                              }else{
                               if(iBar>2){
                                 BodyHigh3[iBar]=test_high;
                                 BodyHigh3[iBar-1]=test_high;
                                 BodyHigh3[iBar-2]=test_high;
                                 BodyHigh3[iBar-3]=test_high;
                               }
                               if(iBar==2){
                                 BodyHigh3[iBar]=test_high;
                                 BodyHigh3[iBar-1]=test_high;
                                 BodyHigh3[iBar-2]=test_high;
                                }
                                if(iBar==1){
                                 BodyHigh3[iBar]=test_high;
                                 BodyHigh3[iBar-1]=test_high;
                                }
                              }
                     }else{
                       if(iBar>2){
                        BodyHigh2[iBar]=test_high;
                        BodyHigh2[iBar-1]=test_high;
                        BodyHigh2[iBar-2]=test_high;
                        BodyHigh2[iBar-3]=test_high;
                       }
                       if(iBar==2){
                        BodyHigh2[iBar]=test_high;
                        BodyHigh2[iBar-1]=test_high;
                        BodyHigh2[iBar-2]=test_high;
                       }
                       if(iBar==1){
                        BodyHigh2[iBar]=test_high;
                        BodyHigh2[iBar-1]=test_high;
                       }
                     }
             }
             else{
               if(iBar>2){
                  BodyHigh[iBar]=test_high;
                  BodyHigh[iBar-1]=test_high;
                  BodyHigh[iBar-2]=test_high;
                  BodyHigh[iBar-3]=test_high;
               }
               if(iBar==2){
                  BodyHigh[iBar]=test_high;
                  BodyHigh[iBar-1]=test_high;
                  BodyHigh[iBar-2]=test_high;
               }
               if(iBar==1){
                  BodyHigh[iBar]=test_high;
                  BodyHigh[iBar-1]=test_high;
               }
          }
            
         //Draw up arrow
        ArrowUp[iBar]=Low[iBar]+UpArrowDist*Point;
      
        if (Time[0] > AlertPrevTime){
           if(AlertAbove)Alert("["+Symbol()+"]" + " Close above EMA -- Buy");
           if(AlertSound)PlaySound(soundfile);
           AlertPrevTime  = Time[0];
        } 
      }
        
     }
   }
  
   
//--- return value of prev_calculated for next call
   return(rates_total-1);
  }
//+------------------------------------------------------------------
Reason: