//+------------------------------------------------------------------+
//|                                   GI_Weekly Cam + Pivot_BT.mq5  |
//|                        Copyright 2022, MetaQuotes Software Corp. |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2022, MetaQuotes Software Corp."
#property link      "https://www.mql5.com"
#property version   "1.01"
#property strict

#property indicator_chart_window
#property indicator_buffers 20
#property indicator_plots   20

#property indicator_label1  "WP"
#property indicator_label2  "WS1"
#property indicator_label3  "WR1"
#property indicator_label4  "WS2"
#property indicator_label5  "WR2"
#property indicator_label6  "WS3"
#property indicator_label7  "WR3"
#property indicator_label8  "WMid"
#property indicator_label9  "WRovr"
#property indicator_label10 "WL3"
#property indicator_label11 "WH3"
#property indicator_label12 "WL4"
#property indicator_label13 "WH4"
#property indicator_label14 "WL5"
#property indicator_label15 "WH5"
#property indicator_label16 "LWLow"
#property indicator_label17 "LWHigh"
#property indicator_label18 "WOpen"
#property indicator_label19 "buf19"
#property indicator_label20 "buf20"

#property indicator_color1  Magenta
#property indicator_color2  Blue
#property indicator_color3  Red
#property indicator_color4  Red
#property indicator_color5  Red
#property indicator_color6  Yellow
#property indicator_color7  Red
#property indicator_color8  White
#property indicator_color9  Yellow
#property indicator_color10 Orange
#property indicator_color11 Aqua
#property indicator_color12 Yellow
#property indicator_color13 Orange
#property indicator_color14 Yellow
#property indicator_color15 Lime
#property indicator_color16 Crimson
#property indicator_color17 Lime
#property indicator_color18 White
#property indicator_color19 clrNONE
#property indicator_color20 clrNONE

#property indicator_type1   DRAW_LINE
#property indicator_type2   DRAW_LINE
#property indicator_type3   DRAW_LINE
#property indicator_type4   DRAW_LINE
#property indicator_type5   DRAW_LINE
#property indicator_type6   DRAW_LINE
#property indicator_type7   DRAW_LINE
#property indicator_type8   DRAW_LINE
#property indicator_type9   DRAW_LINE
#property indicator_type10  DRAW_LINE
#property indicator_type11  DRAW_LINE
#property indicator_type12  DRAW_LINE
#property indicator_type13  DRAW_LINE
#property indicator_type14  DRAW_LINE
#property indicator_type15  DRAW_LINE
#property indicator_type16  DRAW_LINE
#property indicator_type17  DRAW_LINE
#property indicator_type18  DRAW_LINE
#property indicator_type19  DRAW_NONE
#property indicator_type20  DRAW_NONE

#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
#property indicator_style11 STYLE_SOLID
#property indicator_style12 STYLE_SOLID
#property indicator_style13 STYLE_SOLID
#property indicator_style14 STYLE_SOLID
#property indicator_style15 STYLE_SOLID
#property indicator_style16 STYLE_SOLID
#property indicator_style17 STYLE_SOLID
#property indicator_style18 STYLE_SOLID

#property indicator_width1  1
#property indicator_width2  1
#property indicator_width3  1
#property indicator_width4  1
#property indicator_width5  1
#property indicator_width6  1
#property indicator_width7  1
#property indicator_width8  1
#property indicator_width9  1
#property indicator_width10 1
#property indicator_width11 1
#property indicator_width12 1
#property indicator_width13 1
#property indicator_width14 1
#property indicator_width15 1
#property indicator_width16 1
#property indicator_width17 1
#property indicator_width18 1

//---- input parameters
input ENUM_TIMEFRAMES  TimeFrame            = PERIOD_W1;
input int              Shift                = 1;
input int              Distance_from_chart  = 550;
input string           button_note1         = "------------------------------";
input int              btn_Subwindow        = 0;
input ENUM_BASE_CORNER btn_corner           = CORNER_LEFT_UPPER;
input string           btn_Font             = "Arial";
input int              btn_FontSize         = 10;
input color            btn_text_ON_color    = clrLime;
input color            btn_text_OFF_color   = clrRed;
input string           btn_pressed          = "WCamPivot OFF";
input string           btn_unpressed        = "WCamPivot ON";
input color            btn_background_color = clrDimGray;
input color            btn_border_color     = clrBlack;
input int              button_x             = 40;
input int              button_y             = 100;
input int              btn_Width            = 130;
input int              btn_Height           = 20;
input string           button_note2         = "------------------------------";

int fontsize = 8;

//---- buffers
double WPivot[];
double WSupp1[], WRes1[];
double WSupp2[], WRes2[];
double WSupp3[], WRes3[];
double WSupp4[], WRes4[];
double WSupp5[], WRes5[];
double WSupp6[], WRes6[];
double WSupp7[], WRes7[];
double WSupp8[], WRes8[];
double WSupp9[], WRes9[];

string buttonId = "CamPivotWeekly_";

//+------------------------------------------------------------------+
int OnInit()
  {
   SetIndexBuffer(0,  WPivot, INDICATOR_DATA);
   SetIndexBuffer(1,  WSupp1, INDICATOR_DATA);
   SetIndexBuffer(2,  WRes1,  INDICATOR_DATA);
   SetIndexBuffer(3,  WSupp2, INDICATOR_DATA);
   SetIndexBuffer(4,  WRes2,  INDICATOR_DATA);
   SetIndexBuffer(5,  WSupp3, INDICATOR_DATA);
   SetIndexBuffer(6,  WRes3,  INDICATOR_DATA);
   SetIndexBuffer(7,  WSupp4, INDICATOR_DATA);
   SetIndexBuffer(8,  WRes4,  INDICATOR_DATA);
   SetIndexBuffer(9,  WSupp5, INDICATOR_DATA);
   SetIndexBuffer(10, WRes5,  INDICATOR_DATA);
   SetIndexBuffer(11, WSupp6, INDICATOR_DATA);
   SetIndexBuffer(12, WRes6,  INDICATOR_DATA);
   SetIndexBuffer(13, WSupp7, INDICATOR_DATA);
   SetIndexBuffer(14, WRes7,  INDICATOR_DATA);
   SetIndexBuffer(15, WSupp8, INDICATOR_DATA);
   SetIndexBuffer(16, WRes8,  INDICATOR_DATA);
   SetIndexBuffer(17, WSupp9, INDICATOR_DATA);
   SetIndexBuffer(18, WRes9,  INDICATOR_DATA);

   static double _d1[], _d2[];
   SetIndexBuffer(19, _d1, INDICATOR_CALCULATIONS);
   SetIndexBuffer(20, _d2, INDICATOR_CALCULATIONS);

   ArraySetAsSeries(WPivot, true);
   ArraySetAsSeries(WSupp1, true); ArraySetAsSeries(WRes1, true);
   ArraySetAsSeries(WSupp2, true); ArraySetAsSeries(WRes2, true);
   ArraySetAsSeries(WSupp3, true); ArraySetAsSeries(WRes3, true);
   ArraySetAsSeries(WSupp4, true); ArraySetAsSeries(WRes4, true);
   ArraySetAsSeries(WSupp5, true); ArraySetAsSeries(WRes5, true);
   ArraySetAsSeries(WSupp6, true); ArraySetAsSeries(WRes6, true);
   ArraySetAsSeries(WSupp7, true); ArraySetAsSeries(WRes7, true);
   ArraySetAsSeries(WSupp8, true); ArraySetAsSeries(WRes8, true);
   ArraySetAsSeries(WSupp9, true); ArraySetAsSeries(WRes9, true);

   CreateButton(buttonId, btn_unpressed, btn_Width, btn_Height, btn_Font, btn_FontSize,
                btn_background_color, btn_border_color, btn_text_ON_color);
   ObjectSetInteger(ChartID(), buttonId, OBJPROP_YDISTANCE, button_y);
   ObjectSetInteger(ChartID(), buttonId, OBJPROP_XDISTANCE, button_x);

   return INIT_SUCCEEDED;
  }

//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
   string names[] = {
      "WPivot","WSupp1","WRes1","WSupp2","WRes2","WSupp3","WRes3",
      "WSupp4","WRes4","WSupp5","WRes5","WSupp6","WRes6",
      "WSupp7","WRes7","WSupp8","WRes8","WSupp9","WRes9"
   };
   for(int n = 0; n < ArraySize(names); n++) ObjectDelete(0, names[n]);
   ObjectDelete(0, buttonId);
  }

//+------------------------------------------------------------------+
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[])
  {
   ArraySetAsSeries(time,  true);
   ArraySetAsSeries(open,  true);
   ArraySetAsSeries(high,  true);
   ArraySetAsSeries(low,   true);
   ArraySetAsSeries(close, true);

   bool isOn = (ObjectGetString(ChartID(), buttonId, OBJPROP_TEXT) == btn_unpressed);

   int limit = rates_total - prev_calculated;
   if(prev_calculated > 0) limit++;
   if(limit > rates_total) limit = rates_total;

   for(int i = 0; i < limit; i++)
     {
      datetime DayDate = time[i];
      int DailyBar     = iBarShift(_Symbol, TimeFrame, DayDate, false) + Shift;
      double WOpen     = iOpen(_Symbol,  PERIOD_W1, 0);
      double WHigh     = iHigh(_Symbol,  TimeFrame, DailyBar);
      double WLow      = iLow(_Symbol,   TimeFrame, DailyBar);
      double WClose    = iClose(_Symbol, TimeFrame, DailyBar);

      double WP  = (WHigh + WLow + WClose) / 3.0;
      double WS1 = (2*WP) - WHigh;
      double WR1 = (2*WP) - WLow;
      double WS2 = WP - (WHigh - WLow);
      double WR2 = WP + (WHigh - WLow);
      double WS3 = (2*WP) - ((2*WHigh) - WLow);
      double WR3 = (2*WP) + (WHigh - (2*WLow));
      double WS4 = (WHigh + WLow) / 2.0;
      double WR4 = WClose;
      double WS5 = WClose - (WHigh - WLow)*1.1/4.0;
      double WR5 = WClose + (WHigh - WLow)*1.1/4.0;
      double WS6 = WClose - (WHigh - WLow)*1.1/2.0;
      double WR6 = WClose + (WHigh - WLow)*1.1/2.0;
      double WS7 = WClose - (WHigh - WLow);
      double WR7 = WClose + (WHigh - WLow);
      double WS8 = WLow;
      double WR8 = WHigh;
      double WS9 = WOpen;

      WPivot[i] = WP;
      WSupp1[i] = WS1; WRes1[i] = WR1;
      WSupp2[i] = WS2; WRes2[i] = WR2;
      WSupp3[i] = WS3; WRes3[i] = WR3;
      WSupp4[i] = WS4; WRes4[i] = WR4;
      WSupp5[i] = WS5; WRes5[i] = WR5;
      WSupp6[i] = WS6; WRes6[i] = WR6;
      WSupp7[i] = WS7; WRes7[i] = WR7;
      WSupp8[i] = WS8; WRes8[i] = WR8;
      WSupp9[i] = WS9;

      if(i == 0 && isOn)
        {
         datetime labelTime = GetLabelTime();

         string  names[] = {"WPivot","WSupp1","WRes1","WSupp2","WRes2","WSupp3","WRes3",
                            "WSupp4","WRes4","WSupp5","WRes5","WSupp6","WRes6",
                            "WSupp7","WRes7","WSupp8","WRes8","WSupp9"};
         double  vals[]  = {WP, WS1, WR1, WS2, WR2, WS3, WR3, WS4, WR4, WS5, WR5, WS6, WR6, WS7, WR7, WS8, WR8, WS9};
         color   clrs[]  = {Magenta,Blue,Red,Red,Red,Yellow,Red,White,Yellow,Orange,Aqua,Yellow,Orange,Yellow,Lime,Crimson,Lime,White};
         string  txts[]  = {
            " WP:"      +DoubleToString(WP, _Digits),
            " WS1:"     +DoubleToString(WS1,_Digits),
            " WR1:"     +DoubleToString(WR1,_Digits),
            " WS2:"     +DoubleToString(WS2,_Digits),
            " WR2:"     +DoubleToString(WR2,_Digits),
            " WS3:"     +DoubleToString(WS3,_Digits),
            " WR3:"     +DoubleToString(WR3,_Digits),
            " WMid:"    +DoubleToString(WS4,_Digits),
            " WRovr:"   +DoubleToString(WR4,_Digits),
            " WL3:"     +DoubleToString(WS5,_Digits),
            " WH3:"     +DoubleToString(WR5,_Digits),
            "WL4:"      +DoubleToString(WS6,_Digits),
            " WH4:"     +DoubleToString(WR6,_Digits),
            " WL5:"     +DoubleToString(WS7,_Digits),
            " WH5:"     +DoubleToString(WR7,_Digits),
            " LW Low:"  +DoubleToString(WS8,_Digits),
            " LW High:" +DoubleToString(WR8,_Digits),
            " WOpen:"   +DoubleToString(WS9,_Digits)
         };

         for(int n = 0; n < ArraySize(names); n++)
           {
            if(ObjectFind(0, names[n]) < 0)
              {
               ObjectCreate(0, names[n], OBJ_TEXT, 0, labelTime, vals[n]);
               ObjectSetInteger(0, names[n], OBJPROP_ANCHOR,     ANCHOR_LEFT);
               ObjectSetString(0,  names[n], OBJPROP_FONT,       "Arial");
               ObjectSetInteger(0, names[n], OBJPROP_FONTSIZE,   fontsize);
               ObjectSetInteger(0, names[n], OBJPROP_SELECTABLE, false);
               ObjectSetInteger(0, names[n], OBJPROP_HIDDEN,     false);
              }
            ObjectSetInteger(0, names[n], OBJPROP_TIME,  labelTime);
            ObjectSetDouble(0,  names[n], OBJPROP_PRICE, vals[n]);
            ObjectSetString(0,  names[n], OBJPROP_TEXT,  txts[n]);
            ObjectSetInteger(0, names[n], OBJPROP_COLOR, clrs[n]);
           }
        }
     }

   ChartRedraw(0);
   return rates_total;
  }

//+------------------------------------------------------------------+
datetime GetLabelTime()
  {
   int firstBar    = (int)ChartGetInteger(0, CHART_FIRST_VISIBLE_BAR);
   int visibleBars = (int)ChartGetInteger(0, CHART_VISIBLE_BARS);
   int labelBar    = MathMax(0, firstBar - visibleBars + 3);
   datetime t[];
   ArraySetAsSeries(t, true);
   if(CopyTime(_Symbol, _Period, labelBar, 1, t) > 0)
      return t[0];
   return TimeCurrent();
  }

//+------------------------------------------------------------------+
void OnChartEvent(const int id,
                  const long   &lparam,
                  const double &dparam,
                  const string &sparam)
  {
   if(id == CHARTEVENT_CHART_CHANGE)
     {
      bool isOn = (ObjectGetString(ChartID(), buttonId, OBJPROP_TEXT) == btn_unpressed);
      if(isOn)
        {
         datetime labelTime = GetLabelTime();
         string names[] = {"WPivot","WSupp1","WRes1","WSupp2","WRes2","WSupp3","WRes3",
                           "WSupp4","WRes4","WSupp5","WRes5","WSupp6","WRes6",
                           "WSupp7","WRes7","WSupp8","WRes8","WSupp9"};
         for(int n = 0; n < ArraySize(names); n++)
            if(ObjectFind(0, names[n]) >= 0)
               ObjectSetInteger(0, names[n], OBJPROP_TIME, labelTime);
         ChartRedraw(0);
        }
     }

   if(id == CHARTEVENT_OBJECT_CLICK && sparam == buttonId)
     {
      string txt = ObjectGetString(ChartID(), sparam, OBJPROP_TEXT);
      if(txt == btn_unpressed)
        {
         ObjectSetString(ChartID(),  sparam, OBJPROP_TEXT,  btn_pressed);
         ObjectSetInteger(ChartID(), sparam, OBJPROP_COLOR, btn_text_OFF_color);
         ObjectSetInteger(ChartID(), sparam, OBJPROP_STATE, false);
         for(int p = 0; p < 20; p++) PlotIndexSetInteger(p, PLOT_DRAW_TYPE, DRAW_NONE);
         string names[] = {"WPivot","WSupp1","WRes1","WSupp2","WRes2","WSupp3","WRes3",
                           "WSupp4","WRes4","WSupp5","WRes5","WSupp6","WRes6",
                           "WSupp7","WRes7","WSupp8","WRes8","WSupp9","WRes9"};
         for(int n = 0; n < ArraySize(names); n++) ObjectDelete(0, names[n]);
        }
      else
        {
         ObjectSetString(ChartID(),  sparam, OBJPROP_TEXT,  btn_unpressed);
         ObjectSetInteger(ChartID(), sparam, OBJPROP_COLOR, btn_text_ON_color);
         ObjectSetInteger(ChartID(), sparam, OBJPROP_STATE, false);
         for(int p = 0; p < 18; p++) PlotIndexSetInteger(p, PLOT_DRAW_TYPE, DRAW_LINE);
         ChartSetSymbolPeriod(0, _Symbol, _Period);
        }
     }
  }

//+------------------------------------------------------------------+
void CreateButton(string buttonID, string buttonText, int width, int height,
                  string font, int fontSize, color bgColor, color borderColor, color txtColor)
  {
   ObjectDelete(ChartID(), buttonID);
   ObjectCreate(ChartID(), buttonID, OBJ_BUTTON, btn_Subwindow, 0, 0);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_COLOR,        txtColor);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_BGCOLOR,      bgColor);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_BORDER_COLOR, borderColor);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_XSIZE,        width);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_YSIZE,        height);
   ObjectSetString (ChartID(), buttonID, OBJPROP_FONT,         font);
   ObjectSetString (ChartID(), buttonID, OBJPROP_TEXT,         buttonText);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_FONTSIZE,     fontSize);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_SELECTABLE,   0);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_CORNER,       btn_corner);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_HIDDEN,       1);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_XDISTANCE,    9999);
   ObjectSetInteger(ChartID(), buttonID, OBJPROP_YDISTANCE,    9999);
  }
//+------------------------------------------------------------------+
