_SAR_Slave

This script functions as a sophisticated technical analysis tool designed to identify price trends and potential reversal points by modifying the behavior of the Parabolic SAR (Stop and Reverse) indicator. Rather than using a static fixed rate, this script employs a dynamic, multi-layered logic to adapt to changing market conditions.

Core Logic Overview

The indicator operates through three primary layers of calculation:

1. The Dynamic Acceleration Engine (Master-Slave System) Unlike standard Parabolic SAR indicators that use a constant acceleration factor, this script utilizes an external "Master" signal to determine its speed. It pulls data from a secondary source (which can be adjusted by the user to be based on volatility, price movement, or other metrics). This "Master" value dictates how aggressively the indicator should react:

  • When market activity is high or follows specific patterns, the acceleration factor increases.
  • When market activity settles, the factor decreases. This ensures that the indicator remains responsive during trending moves but becomes less erratic during consolidation phases.

2. Trend Detection and Directional Awareness The script continuously monitors price action to establish a primary direction (Long or Short). It keeps track of "Extreme Points"—the highest highs or lowest lows reached during a current trend.

  • In an Uptrend: It monitors the lowest prices to set "floor" levels.
  • In a Downtrend: It monitors the highest prices to set "ceiling" levels. The logic is designed to distinguish between minor price fluctuations and genuine trend exhaustion by comparing current prices against historical extreme points.

3. The Adaptive Stop-and-Reverse Mechanism The indicator places visual markers (dots) on the chart that act as trailing stop-loss levels. Its movement is governed by two strict rules:

  • Movement: As price moves in the direction of the trend, the indicator "trails" behind it, moving further away to allow for market "breathing room."
  • The Flip: If the price penetrates the plotted dot (the SAR value), the script interprets this as a potential trend reversal. It immediately flips the direction, recalculates the acceleration based on the new trend, and repositions the dots on the opposite side of the price action.

Summary for the User

In practical terms, this script provides a more "intelligent" version of the Parabolic SAR. By blending a secondary signal (the Master-Slave input) with standard trend-following math, it attempts to filter out market noise. It seeks to stay "behind" a strong trend as long as possible while reacting quickly when price action suggests that the current move has lost its momentum and a reversal is occurring.

Miscellaneous
Implements a curve of type %1
12 Views
0 Downloads
0 Favorites
_SAR_Slave
#property indicator_chart_window // â îêíå èíñòðóìåíòà
#property indicator_buffers 2
#property indicator_color1 Blue

// âõîäíûå ïàðàìåòðû Parabolic SAR
extern double StepFrom=0.005; // íà÷àëüíîå çíà÷åíèå è øàã ôàêòîðà óñêîðåíèÿ îò
extern double StepTo=0.02; // äî
extern double Maximum=0.2; // êîíå÷íîå çíà÷åíèå ôàêòîðà óñêîðåíèÿ
// Âîõîäíûå ïàðàìåòðû MasterSlave
extern int Source=1; // 0 - îáúåì; 1 - ATR; 2 - ñò.äåâèàöèÿ öåíû; 
extern int SourcePeriod=33; // ïåðèîä âõîäíîãî èíäèêàòîðà
extern int Window=88; // äëèíà âûáîðêè íîðìèðîâàíèÿ
extern double Sensitivity=0; // ÷óâñòâèòåëüíîñòü
extern int Signal=33; // ñãëàæèâàíèå íîðìèðîâàííîãî èíäèêàòîðà (ñèãíàëüíàÿ)
//--
int History=0;

// èíäèêàòîðíûå áóôåðû
double   SarBuffer[], // ïàðàáîëèê
         Step[]; // øàã ôàêòîðà óñêîðåíèÿ
// îáùèå ïåðåìåííûå äëÿ ïàðàáîëèêà
int    save_lastreverse;
bool   save_dirlong;
double save_start;
double save_last_high;
double save_last_low;
double save_ep;
double save_sar;
int    bartime;
//
bool First=1;
//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int init()
  {
//---- indicators
   SetIndexBuffer(0,SarBuffer);
   SetIndexStyle(0,DRAW_ARROW);
   SetIndexArrow(0,159);
   SetIndexLabel(0,"SAR");

   SetIndexBuffer(1,Step);
   SetIndexStyle(1,DRAW_NONE,2);

   SetIndexEmptyValue(0,0.0);
   SetIndexEmptyValue(1,0.0);
//----
   return(0);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int start() {
   int ic=IndicatorCounted();
   if(!First && Bars-ic>2) ic=reinit(); // åñëè åñòü ïðîïóùåííûå áàðû íå íà ïîäêëþ÷åíèè (â ðàáîòå)
   First=0; //  ñáðîñ ôëàãà ïåðâîãî çàïóñêà
// Ìàñòåð
   int limit=Bars-ic-1;
   for(int i=limit; i>0; i--) {
      // óïðàâëÿþùèé ñèãíàë
      double ms=iCustom(NULL,0,"_MasterSlave",Source,SourcePeriod,Window,Sensitivity,Signal, 0,i);
      Step[i-1]=StepFrom+ms*(StepTo-StepFrom);
     }
//===========ïàðàáîëèê========================
   static bool first = true;
   bool   dirlong;
   double start, last_high, last_low;
   double ep, sar, price_low, price_high, price;
   int    counted_bars = IndicatorCounted();
//----
   if(Bars < 3) 
       return(0);
//---- initial settings
   i = Bars - 2;
//----
   if(counted_bars == 0 || first)
     {
       first = false;
       dirlong = true;
       start = Step[i];
       last_high = -10000000.0;
       last_low = 10000000.0;
       //----
       while(i > 0)
         {
           save_lastreverse = i;
           price_low = Low[i];
           //----
           if(last_low > price_low)
               last_low = price_low;
           price_high = High[i];
           //----
           if(last_high < price_high)
               last_high = price_high;
           //----
           if(price_high > High[i+1] && price_low > Low[i+1]) 
               break;
           //----
           if(price_high < High[i+1] && price_low < Low[i+1])
             { 
               dirlong = false; 
               break; 
             }
           i--;
         }
       //---- initial zero
       int k = i;
       Print("  k=", k, "  Bars=", Bars);      
       //----
       while(k < Bars)
         {
           SarBuffer[k] = 0.0;
           k++;
         }
       //---- check further
       if(dirlong)
         { 
           SarBuffer[i] = Low[i+1];
           ep = High[i];
         }
       else        
         { 
           SarBuffer[i] = High[i+1]; 
           ep = Low[i]; 
         }
       i--;
     }
   else
     {
       i =         save_lastreverse;
       start =     save_start;
       dirlong =   save_dirlong;
       last_high = save_last_high;
       last_low =  save_last_low;
       ep =        save_ep;
       sar =       save_sar;
       // Fix1 start
       // If new bar increment index   
       if(Time[0] != bartime)       
         {
           bartime = Time[0];
           i++;
         }
       //Fix1 end         
     }
//----
   while(i >= 0)
     {
       price_low = Low[i];
       price_high = High[i];
       //--- check for reverse from long to short
       if(dirlong && price_low < SarBuffer[i+1])
         {
           SaveLastReverse(i, true, start, price_low, last_high, ep, sar);
           start = Step[i]; 
           dirlong = false;
           ep = price_low;  
           last_low = price_low;
           SarBuffer[i] = last_high;
           i--;
           continue;
         }
       //--- check for reverse from short to long  
       if(!dirlong && price_high > SarBuffer[i+1])
         {
           SaveLastReverse(i, false, start, last_low, price_high, ep, sar);
           start = Step[i]; 
           dirlong = true;
           ep = price_high; 
           last_high = price_high;
           SarBuffer[i] = last_low;
           i--;
           continue;
         }
       //sar(i) = sar(i+1)+start*(ep-sar(i+1))
       price = SarBuffer[i+1];
       sar = price + start*(ep - price);
       //----
       if(dirlong)
         {
           if(ep < price_high && (start + Step[i]) <= Maximum) 
               start += Step[i];
           //----
           if(price_high < High[i+1] && i == Bars - 2)  
               sar = SarBuffer[i+1];
           price = Low[i+1];
           //----
           if(sar > price)
               sar = price;
           price = Low[i+2];
           //----
           if(sar > price)
               sar = price;
           //----
           if(sar > price_low)
             {
               SaveLastReverse(i, true, start, price_low, last_high, ep, sar);
               start = Step[i]; 
               dirlong = false; 
               ep = price_low;
               last_low = price_low;
               SarBuffer[i] = last_high;
               i--;
               continue;
             }
           //----
           if(ep < price_high)
             {
               last_high = price_high;
               ep = price_high;
             }
         }     //dir-long
       else
         {
           if(ep > price_low && (start + Step[i]) <= Maximum) 
               start += Step[i];
           //----
           if(price_low < Low[i+1] && i == Bars - 2)  
               sar = SarBuffer[i+1];
           price = High[i+1];
           //----
           if(sar < price)
               sar = price;
           price = High[i+2];
           //----
           if(sar < price)
               sar = price;
           //----
           if(sar < price_high)
             {
               SaveLastReverse(i, false, start, last_low, price_high, ep,sar);
               start = Step[i]; 
               dirlong = true; 
               ep = price_high;
               last_high = price_high;
               SarBuffer[i] = last_low;
               i--;
               continue;
             }
           //----
           if(ep > price_low)
             {
               last_low = price_low; 
               ep = price_low; 
             }
         }     //dir-short
       SarBuffer[i] = sar;
       i--;
     }        //while   
//   sar=SarBuffer[0];
//   price=iSAR(NULL,0,Step,Maximum,0);
//   if(sar!=price) Print("custom=",sar,"   SAR=",price,"   counted=",counted_bars);
//   if(sar==price) Print("custom=",sar,"   SAR=",price,"   counted=",counted_bars);
//----
//----
   return(0);
  }
//=====================================================================================
void SaveLastReverse(int last, int dir, double start, double low, double high, 
                     double ep, double sar)
  {
   save_lastreverse = last;
   save_dirlong = dir;
   save_start = start;
   save_last_low = low;
   save_last_high = high;
   save_ep = ep;
   save_sar = sar;
  }

int reinit() { // äîïîëíèòåëüíàÿ èíèöèàëèçàöèÿ
   ArrayInitialize(SarBuffer,0.0); 
   ArrayInitialize(Step,0.0); 
   return(0);
  }

Comments