#property copyright "LuxAlgo (Converted to MT4)"
#property link      "https://tradingview.com"
#property version   "1.00"
#property indicator_separate_window

// 将总缓冲区和绘图数量
#property indicator_buffers 8
#property indicator_plots   8

// 设定原有图表样式
#property indicator_label1  "Oscillator" 
#property indicator_type1   DRAW_HISTOGRAM
#property indicator_color1  clrGreen
#property indicator_width1  2

#property indicator_label2  "Histogram" 
#property indicator_type2   DRAW_HISTOGRAM
#property indicator_color2  clrSilver
#property indicator_width2  1

#property indicator_label3  "Signal" 
#property indicator_type3   DRAW_LINE
#property indicator_color3  clrBlue
#property indicator_width3  2

#property indicator_label4  "SignalLine" 
#property indicator_type4   DRAW_NONE

// 设定 4 个新箭头的图表样式
#property indicator_label5  "Hist_Cross_Up"
#property indicator_type5   DRAW_ARROW
#property indicator_label6  "Hist_Cross_Dn"
#property indicator_type6   DRAW_ARROW
#property indicator_label7  "Osc_Cross_Up"
#property indicator_type7   DRAW_ARROW
#property indicator_label8  "Osc_Cross_Dn"
#property indicator_type8   DRAW_ARROW

// 输入参数
input int    Length   = 10; // SuperTrend Length
input double Mult     = 2.0; // SuperTrend Multiplier
input int    Smooth   = 72; // Histogram Smoothing Period

// --- 灰色柱箭头设置 (Histogram) ---
input color  InpHistUpColor = clrLightSeaGreen; // 灰色柱上穿箭头颜色
input color  InpHistDnColor = clrOrangeRed;     // 灰色柱下穿箭头颜色
input int    InpHistArrowSize = 2;              // 灰色柱箭头大小 (1-5)

// --- 绿色柱箭头设置 (Oscillator) ---
input color  InpOscUpColor   = clrGreenYellow;   // 绿色柱上穿箭头颜色
input color  InpOscDnColor   = clrRed;           // 绿色柱下穿箭头颜色
input int    InpOscArrowSize   = 3;              // 绿色柱箭头大小 (1-5)

// 内部数组缓冲区
double OscBuffer[];
double HistBuffer[];
double AmaBuffer[];
double SigLineBuffer[];

// 箭头专用缓冲区
double HistUpArrowBuffer[];
double HistDnArrowBuffer[];
double OscUpArrowBuffer[];
double OscDnArrowBuffer[];

// 逻辑计算辅助数组
double SptTrend[];
double SptUpper[];
double SptLower[];
double AmaInternal[];

//+------------------------------------------------------------------+
//| Custom indicator initialization function                         |
//+------------------------------------------------------------------+
int OnInit()
{
   // 绑定缓冲区
   SetIndexBuffer(0, OscBuffer);
   SetIndexBuffer(1, HistBuffer);
   SetIndexBuffer(2, AmaBuffer);
   SetIndexBuffer(3, SigLineBuffer);
   
   // 绑定箭头缓冲区
   SetIndexBuffer(4, HistUpArrowBuffer);
   SetIndexBuffer(5, HistDnArrowBuffer);
   SetIndexBuffer(6, OscUpArrowBuffer);
   SetIndexBuffer(7, OscDnArrowBuffer);
   
   // 设置箭头图标
   SetIndexArrow(4, 233);
   SetIndexArrow(5, 234);
   SetIndexArrow(6, 233);
   SetIndexArrow(7, 234);
   
   // 定义箭头
   SetIndexStyle(4, DRAW_ARROW, STYLE_SOLID, InpHistArrowSize, InpHistUpColor);
   SetIndexStyle(5, DRAW_ARROW, STYLE_SOLID, InpHistArrowSize, InpHistDnColor);
   SetIndexStyle(6, DRAW_ARROW, STYLE_SOLID, InpOscArrowSize, InpOscUpColor);
   SetIndexStyle(7, DRAW_ARROW, STYLE_SOLID, InpOscArrowSize, InpOscDnColor);

   // 分配逻辑数组
   ArrayResize(SptTrend, Bars);
   ArrayResize(SptUpper, Bars);
   ArrayResize(SptLower, Bars);
   ArrayResize(AmaInternal, Bars);

   // 设置水平线
   IndicatorSetDouble(INDICATOR_LEVELVALUE, 0, 80.0);
   IndicatorSetDouble(INDICATOR_LEVELVALUE, 1, -80.0);
   IndicatorSetInteger(INDICATOR_LEVELCOLOR, 0, clrBlue);
   IndicatorSetInteger(INDICATOR_LEVELCOLOR, 1, clrBlue);
   IndicatorSetInteger(INDICATOR_LEVELSTYLE, 0, STYLE_DOT);
   IndicatorSetInteger(INDICATOR_LEVELSTYLE, 1, STYLE_DOT);

   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[])
{
   int i = 0;
   int j = 0;

   // 数组大小
   if(rates_total < Length + Smooth + 2) return(0);

   int limit = rates_total - prev_calculated;
   if(limit > 0) {
      limit = rates_total - 1;
      ArrayInitialize(OscBuffer, 0.0);
      ArrayInitialize(HistBuffer, 0.0);
      ArrayInitialize(AmaBuffer, 0.0);
      ArrayInitialize(SigLineBuffer, EMPTY_VALUE);
      
      // 初始化箭头缓冲区
      ArrayInitialize(HistUpArrowBuffer, EMPTY_VALUE);
      ArrayInitialize(HistDnArrowBuffer, EMPTY_VALUE);
      ArrayInitialize(OscUpArrowBuffer, EMPTY_VALUE);
      ArrayInitialize(OscDnArrowBuffer, EMPTY_VALUE);
   }

   // 防止越界
   if(ArraySize(SptTrend) < rates_total) {
      ArrayResize(SptTrend, rates_total);
      ArrayResize(SptUpper, rates_total);
      ArrayResize(SptLower, rates_total);
      ArrayResize(AmaInternal, rates_total);
   }

   // 计算 SuperTrend 核心Oscillator(AMA)
   for(i = limit; i >= 0; i--)
   {
      if(i >= rates_total - Length - 1) {
         SptUpper[i] = high[i];
         SptLower[i] = low[i];
         SptTrend[i] = 0;
         AmaInternal[i] = 0;
         continue;
      }

      double atr = iATR(NULL, 0, Length, i) * Mult;
      double hl2 = (high[i] + low[i]) / 2.0;
      double up = hl2 + atr;
      double dn = hl2 - atr;

      if(close[i+1] < SptUpper[i+1])
         SptUpper[i] = MathMin(up, SptUpper[i+1]);
      else
         SptUpper[i] = up;

      if(close[i+1] > SptLower[i+1])
         SptLower[i] = MathMax(dn, SptLower[i+1]);
      else
         SptLower[i] = dn;

      if(close[i] > SptUpper[i+1])
         SptTrend[i] = 1;
      else if(close[i] < SptLower[i+1])
         SptTrend[i] = 0;
      else
         SptTrend[i] = SptTrend[i+1];

      double Spt = (SptTrend[i] == 1) ? SptLower[i] : SptUpper[i];
      double diff = SptUpper[i] - SptLower[i];
      double osc = 0;
      if(diff != 0) {
         osc = (close[i] - Spt) / diff;
         if(osc > 1.0) osc = 1.0;
         if(osc < -1.0) osc = -1.0;
      }
      OscBuffer[i] = osc * 100.0;

      double alpha = MathPow(osc, 2.0) / (double)Length;
      AmaInternal[i] = AmaInternal[i+1] + alpha * (osc - AmaInternal[i+1]);
      AmaBuffer[i] = AmaInternal[i] * 100.0;

      if(OscBuffer[i] > 0)
         ObjectSetInteger(0, "OscColor_"+IntegerToString(i), OBJPROP_COLOR, clrGreen);
      else
         ObjectSetInteger(0, "OscColor_"+IntegerToString(i), OBJPROP_COLOR, clrRed);
   }

   // 4. 直方图平滑 (EMA)
   double k = 2.0 / (Smooth + 1.0);
   for(i = rates_total - Smooth - 2; i >= 0; i--)
   {
      double expr = (OscBuffer[i] - AmaBuffer[i]);
      HistBuffer[i] = (expr * k) + (HistBuffer[i+1] * (1.0 - k));
   }

   // 循环判断箭头
   int crossLimit = (limit < rates_total - 2) ? limit : rates_total - 2;
   for(i = crossLimit; i >= 0; i--)
   {
      // 箭头缓冲区数据
      HistUpArrowBuffer[i] = EMPTY_VALUE;
      HistDnArrowBuffer[i] = EMPTY_VALUE;
      OscUpArrowBuffer[i] = EMPTY_VALUE;
      OscDnArrowBuffer[i] = EMPTY_VALUE;

      // 第一组
      if(HistBuffer[i+1] <= 0 && HistBuffer[i] > 0) {
         HistUpArrowBuffer[i] = -95.0; 
      }
      else if(HistBuffer[i+1] >= 0 && HistBuffer[i] < 0) {
         HistDnArrowBuffer[i] = -95.0; 
      }

      // 第二组
      if(OscBuffer[i+1] <= 0 && OscBuffer[i] > 0) {
         OscUpArrowBuffer[i] = 95.0; 
      }
      else if(OscBuffer[i+1] >= 0 && OscBuffer[i] < 0) {
         OscDnArrowBuffer[i] = 95.0; 
      }
   }

   // 5. 错误信号检测与标记 (❌ 标签绘制)
   for(i = limit; i >= 0; i--)
   {
      if(i >= rates_total - 5) continue;
      bool crossover = (close[i+1] <= SptLower[i+1] && close[i] > SptUpper[i+1]);
      bool crossunder = (close[i+1] >= SptUpper[i+1] && close[i] < SptLower[i+1]);

      if(crossover || crossunder)
      {
         int prev_cross_idx = -1;
         for(j = i + 1; j < rates_total - 1; j++) {
            bool cx = (close[j+1] <= SptLower[j+1] && close[j] > SptUpper[j+1]) ||
                      (close[j+1] >= SptUpper[j+1] && close[j] < SptLower[j+1]);
            if(cx) { prev_cross_idx = j; break; }
         }
         
         if(prev_cross_idx != -1) {
            if(crossover) {
               if(close[i] > close[prev_cross_idx]) {
                  CreateXLabel(i, -80.0, "False_Sell_X_"+IntegerToString(i));
               }
            }
            if(crossunder) {
               if(close[i] < close[prev_cross_idx]) {
                  CreateXLabel(i, 80.0, "False_Buy_X_"+IntegerToString(i));
               }
            }
         }
      }
   }
   return(rates_total);
}

//+------------------------------------------------------------------+
//| 辅助函数：在副图绘制 ❌ 标签                                      |
//+------------------------------------------------------------------+
void CreateXLabel(int barIndex, double priceLevel, string objName)
{
   if(ObjectFind(0, objName) < 0)
    {
      int window = ChartWindowFind(0, "SuperOsc [LuxAlgo]");
      if(window < 0) window = 1;
      ObjectCreate(0, objName, OBJ_TEXT, window, Time[barIndex], priceLevel);
      ObjectSetString(0, objName, OBJPROP_TEXT, "❌");
      ObjectSetString(0, objName, OBJPROP_FONT, "Arial");
      ObjectSetInteger(0, objName, OBJPROP_FONTSIZE, 10);
      ObjectSetInteger(0, objName, OBJPROP_COLOR, clrRed);
      ObjectSetInteger(0, objName, OBJPROP_ANCHOR, ANCHOR_CENTER);
    }
}
//+------------------------------------------------------------------+
//| Indicator deinitialization function                              |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
  ObjectsDeleteAll(0, "False_");
}