Indikatoren: Bollinger Squeeze Basic MT5

 

Bollinger Squeeze Basic MT5:

Bollinger Squeeze Basic MetaTrader Indikator - ist ein komplexer Indikator, der auf Momentum, Bollinger Bändern und Keltner-Kanal basiert. Der Indikator wird in einem separaten Fenster des Charts als Momentum-Histogramm und eine Reihe von Punkten gezeichnet, die das Verhältnis zwischen den aktuellen Werten der Bollinger-Bänder und des Keltner-Kanals anzeigen. Dieser Indikator ist sowohl für die MT4- als auch für die MT5-Version der Handelsplattform verfügbar.

Bollinger Squeeze Basic MT5

Author: Tuan Nguyen Van

 
Klingt wie ein Trend und eine Bestätigung im selben Indikator. Interessant!
 

Hallo Danke für das Teilen Ihres Indikatorcodes, ich habe versucht, den Sqeeze Momentum Indicator von Trading View zu konvertieren, hier ist der Code, den ich habe... er ist etwas anders... Ich würde gerne von Ihnen dazu etwas hören! Danke!


//+------------------------------------------------------------------------+
//|SqueezeMomentumIndicator.mq5 |
//|Konvertiert von Pine Script durch LazyBear |
//||
//+------------------------------------------------------------------------+
#property copyright "Converted from Pine Script by LazyBear"
#property link      ""
#property version   "1.02"
#property indicator_separate_window
#property indicator_buffers 4
#property indicator_plots   2
#property indicator_type1   DRAW_COLOR_HISTOGRAM
#property indicator_color1  clrLime, clrGreen, clrRed, clrMaroon
#property indicator_style1  STYLE_SOLID
#property indicator_width1  4
#property indicator_label1  "Squeeze Momentum"
#property indicator_type2   DRAW_COLOR_LINE
#property indicator_color2  clrBlue, clrBlack, clrGray
#property indicator_style2  STYLE_SOLID
#property indicator_width2  2
#property indicator_label2  "Squeeze"

//--- Eingabeparameter
input int    LengthBB = 20;         // BB Länge
input double MultBB = 2.0;          // BB MultFactor
input int    LengthKC = 20;         // KC Länge
input double MultKC = 1.5;          // KC MultFactor
input bool   UseTrueRange = true;   // TrueRange (KC) verwenden

//--- Indikatorpuffer
double MomentumBuffer[];       // Momentum-Werte
double MomentumColorBuffer[];  // Momentum-Farben
double SqueezeBuffer[];        // Werte quetschen
double SqueezeColorBuffer[];   // Farben quetschen

//+------------------------------------------------------------------+
//| Benutzerdefinierte Indikator-Initialisierungsfunktion|
//+------------------------------------------------------------------+
int OnInit()
{
   //--- Zuordnung von Indikatorpuffern
   SetIndexBuffer(0, MomentumBuffer, INDICATOR_DATA);
   SetIndexBuffer(1, MomentumColorBuffer, INDICATOR_COLOR_INDEX);
   SetIndexBuffer(2, SqueezeBuffer, INDICATOR_DATA);
   SetIndexBuffer(3, SqueezeColorBuffer, INDICATOR_COLOR_INDEX);
   
   //--- Farbindizes festlegen
   PlotIndexSetInteger(0, PLOT_COLOR_INDEXES, 4); // 4 Farben für das Histogramm
   PlotIndexSetInteger(1, PLOT_COLOR_INDEXES, 3); // 3 Farben für die Linie
   
   //--- Name des Indikators festlegen
   IndicatorSetString(INDICATOR_SHORTNAME, "SQZMOM_LB [LazyBear]");
   
   //--- Genauigkeit einstellen
   IndicatorSetInteger(INDICATOR_DIGITS, 5);
   
   //--- Arrays als Serien einstellen
   ArraySetAsSeries(MomentumBuffer, true);
   ArraySetAsSeries(MomentumColorBuffer, true);
   ArraySetAsSeries(SqueezeBuffer, true);
   ArraySetAsSeries(SqueezeColorBuffer, true);
   
   return(INIT_SUCCEEDED);
}

//+------------------------------------------------------------------+
//| Einfacher gleitender Durchschnitt|
//+------------------------------------------------------------------+
double SimpleMA(const double &price[], int period, int shift)
{
   double sum = 0.0;
   for(int i = 0; i < period; i++)
   {
      sum += price[shift + i];
   }
   return sum / period;
}

//+------------------------------------------------------------------+
//| Standardabweichung|
//+------------------------------------------------------------------+
double StdDev(const double &price[], int period, int shift)
{
   double avg = SimpleMA(price, period, shift);
   double sum = 0.0;
   
   for(int i = 0; i < period; i++)
   {
      sum += MathPow(price[shift + i] - avg, 2);
   }
   
   return MathSqrt(sum / period);
}

//+------------------------------------------------------------------+
//| Lineare Regression|
//+------------------------------------------------------------------+
double LinReg(const double &price[], int period, int shift)
{
   double sum_x = 0.0;
   double sum_y = 0.0;
   double sum_xy = 0.0;
   double sum_x2 = 0.0;
   
   for(int i = 0; i < period; i++)
   {
      sum_x += i;
      sum_y += price[shift + i];
      sum_xy += i * price[shift + i];
      sum_x2 += i * i;
   }
   
   double m = period;
   double slope = (m * sum_xy - sum_x * sum_y) / (m * sum_x2 - sum_x * sum_x);
   double intercept = (sum_y - slope * sum_x) / m;
   
   return intercept;
}

//+------------------------------------------------------------------+
//| Benutzerdefinierte Indikator-Iterationsfunktion|
//+------------------------------------------------------------------+
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[])
{
   // Prüfung auf Mindestdaten
   int min_bars = MathMax(LengthBB, LengthKC) + 1;
   if(rates_total < min_bars) return(0);
   
   // Arrays als Serien für die richtige Indizierung festlegen
   ArraySetAsSeries(high, true);
   ArraySetAsSeries(low, true);
   ArraySetAsSeries(close, true);
   
   // Berechnung des Startpunkts
   int limit;
   if(prev_calculated == 0)
      limit = rates_total - min_bars;
   else
      limit = rates_total - prev_calculated;
   
   limit = MathMin(limit, rates_total - min_bars);
   
   // Arrays für die Quellenberechnung vorbereiten
   double source[];
   ArrayResize(source, rates_total);
   ArraySetAsSeries(source, true);
   
   // Hauptberechnungsschleife
   for(int i = limit; i >= 0; i--)
   {
      // Bollinger-Bänder berechnen
      double basis = 0.0;
      for(int j = 0; j < LengthBB; j++)
         basis += close[i+j];
      basis /= LengthBB;
      
      double dev = 0.0;
      for(int j = 0; j < LengthBB; j++)
         dev += MathPow(close[i+j] - basis, 2);
      dev = MultBB * MathSqrt(dev / LengthBB);
      
      double upperBB = basis + dev;
      double lowerBB = basis - dev;
      
      // Keltner-Kanäle berechnen
      double ma = 0.0;
      for(int j = 0; j < LengthKC; j++)
         ma += close[i+j];
      ma /= LengthKC;
      
      double range_sum = 0.0;
      for(int j = 0; j < LengthKC; j++)
      {
         double tr;
         if(UseTrueRange && i+j+1 < rates_total)
            tr = MathMax(high[i+j] - low[i+j], 
                 MathMax(MathAbs(high[i+j] - close[i+j+1]), 
                         MathAbs(low[i+j] - close[i+j+1])));
         else
            tr = high[i+j] - low[i+j];
         
         range_sum += tr;
      }
      double range_ma = range_sum / LengthKC;
      
      double upperKC = ma + MultKC * range_ma;
      double lowerKC = ma - MultKC * range_ma;
      
      // Berechnung der Quetschungsbedingungen
      bool sqzOn = (lowerBB > lowerKC) && (upperBB < upperKC);
      bool sqzOff = (lowerBB < lowerKC) && (upperBB > upperKC);
      bool noSqz = !sqzOn && !sqzOff;
      
      // Höchster Höchstwert und niedrigster Tiefstwert für den KC-Zeitraum ermitteln
      double highest = high[i];
      double lowest = low[i];
      
      for(int j = 1; j < LengthKC; j++)
      {
         if(i+j >= rates_total) break;
         if(high[i+j] > highest) highest = high[i+j];
         if(low[i+j] < lowest) lowest = low[i+j];
      }
      
      // Berechnung der Quelle für linreg
      double avg_hl = (highest + lowest) / 2;
      double avg_val = (avg_hl + ma) / 2;
      
      for(int j = 0; j < LengthKC; j++)
      {
         if(i+j >= rates_total) break;
         source[i+j] = close[i+j] - avg_val;
      }
      
      // Berechnung des Impulses mit linearer Regression
      MomentumBuffer[i] = LinReg(source, LengthKC, i);
      
      // Wert der Quetschkante einstellen (immer 0)
      SqueezeBuffer[i] = 0;
      
      // Farben basierend auf den Bedingungen genau wie in Pine Script einstellen
      // bcolor = iff(val > 0, iff(val > nz(val[1]), lime, green), iff(val < nz(val[1]), red, maroon))
      if(i < rates_total - 1)
      {
         if(MomentumBuffer[i] > 0)
         {
            if(MomentumBuffer[i] > MomentumBuffer[i+1])
               MomentumColorBuffer[i] = 0; // Kalk
            else
               MomentumColorBuffer[i] = 1; // grün
         }
         else
         {
            if(MomentumBuffer[i] < MomentumBuffer[i+1])
               MomentumColorBuffer[i] = 2; // rot
            else
               MomentumColorBuffer[i] = 3; // kastanienbraun
         }
      }
      else
      {
         // Für den ersten Takt
         MomentumColorBuffer[i] = (MomentumBuffer[i] > 0) ? 0 : 2; // Limette oder rot
      }
      
      // scolor = noSqz ? blau : sqzOn ? schwarz : grau
      if(noSqz)
         SqueezeColorBuffer[i] = 0; // blau
      else if(sqzOn)
         SqueezeColorBuffer[i] = 1; // schwarz
      else
         SqueezeColorBuffer[i] = 2; // grau
   }
   
   return(rates_total);
}
//+------------------------------------------------------------------+



Dateien: