//+------------------------------------------------------------------+
//| Value Charts.mq5 |
//| Copyright 2011, FxGeek. |
//| Modified by AI Assistant|
//+------------------------------------------------------------------+
#property copyright "2011, FxGeek."
#property version "2.1"
//--- indicator settings
#property indicator_separate_window
#property indicator_buffers 7
#property indicator_plots 1
#property indicator_type1 DRAW_COLOR_CANDLES
#property indicator_color1 clrRed, clrGreen, clrDodgerBlue // 0:红(涨),1:绿(跌),2:蓝(极端)
#property indicator_width1 1
#property indicator_label1 "Open;High;Low;Close"
//--- indicator include
#include <MovingAverages.mqh>
//--- indicator input parameters
input int Periode = 5; // 移动平均周期
input bool Show_Arrow = true; // 显示箭头
input bool Show_Alert = false; // 显示弹窗提示
input int Arrow_Width = 3; // 箭头宽度
input color Arrow_Up = clrGreen; // 上箭头颜色 (±10)
input color Arrow_Down = clrRed; // 下箭头颜色 (±10)
input color Arrow_Up_Strong = clrLime; // 强烈上箭头颜色 (±12)
input color Arrow_Down_Strong = clrMagenta; // 强烈下箭头颜色 (±12)
//--- 极端水平阈值
#define LEVEL_10 10.0 // ±10 蓝色K线+箭头
#define LEVEL_12 12.0 // ±12 蓝色K线+强烈箭头+弹窗
//--- indicator buffers
double ExtOBuffer[];
double ExtHBuffer[];
double ExtLBuffer[];
double ExtCBuffer[];
double ExtColorBuffer[];
double RangeAverage[];
double MiddleAverage[];
#define DATA_LIMIT Periode
double _AValue;
double _BValue;
//--- 记录每个K线的信号状态
bool SignalTriggered[]; // 统一记录是否已触发过信号
//+------------------------------------------------------------------+
//| Custom indicator initialization function |
//+------------------------------------------------------------------+
void OnInit()
{
//--- indicator buffers mapping
SetIndexBuffer(0,ExtOBuffer,INDICATOR_DATA);
SetIndexBuffer(1,ExtHBuffer,INDICATOR_DATA);
SetIndexBuffer(2,ExtLBuffer,INDICATOR_DATA);
SetIndexBuffer(3,ExtCBuffer,INDICATOR_DATA);
SetIndexBuffer(4,ExtColorBuffer,INDICATOR_COLOR_INDEX);
SetIndexBuffer(5,RangeAverage,INDICATOR_CALCULATIONS);
SetIndexBuffer(6,MiddleAverage,INDICATOR_CALCULATIONS);
//--- 设置图表属性
IndicatorSetInteger(INDICATOR_DIGITS,2); // 标准化值显示2位小数
IndicatorSetString(INDICATOR_SHORTNAME,"Value Chart ("+IntegerToString(Periode)+")");
//--- 设置水平线 - 4条水平线: ±10 和 ±12
IndicatorSetInteger(INDICATOR_LEVELS,4);
IndicatorSetDouble(INDICATOR_LEVELVALUE,0,12.0);
IndicatorSetDouble(INDICATOR_LEVELVALUE,1,10.0);
IndicatorSetDouble(INDICATOR_LEVELVALUE,2,-10.0);
IndicatorSetDouble(INDICATOR_LEVELVALUE,3,-12.0);
IndicatorSetInteger(INDICATOR_LEVELSTYLE,0,STYLE_DASH);
IndicatorSetInteger(INDICATOR_LEVELSTYLE,1,STYLE_DOT);
IndicatorSetInteger(INDICATOR_LEVELSTYLE,2,STYLE_DOT);
IndicatorSetInteger(INDICATOR_LEVELSTYLE,3,STYLE_DASH);
IndicatorSetInteger(INDICATOR_LEVELWIDTH,0,1);
IndicatorSetInteger(INDICATOR_LEVELWIDTH,1,1);
IndicatorSetInteger(INDICATOR_LEVELWIDTH,2,1);
IndicatorSetInteger(INDICATOR_LEVELWIDTH,3,1);
IndicatorSetInteger(INDICATOR_LEVELCOLOR,0,clrRed);
IndicatorSetInteger(INDICATOR_LEVELCOLOR,1,clrOrange);
IndicatorSetInteger(INDICATOR_LEVELCOLOR,2,clrOrange);
IndicatorSetInteger(INDICATOR_LEVELCOLOR,3,clrRed);
IndicatorSetString(INDICATOR_LEVELTEXT,0,"+12 ★★★");
IndicatorSetString(INDICATOR_LEVELTEXT,1,"+10 ★★");
IndicatorSetString(INDICATOR_LEVELTEXT,2,"-10 ★★");
IndicatorSetString(INDICATOR_LEVELTEXT,3,"-12 ★★★");
Print("═══════════════════════════════════════════════════════════");
Print("Value Chart v2.1 初始化完成");
Print("提示规则:");
Print(" 当 High >= +10 或 Low <= -10: 蓝色K线 + 箭头");
Print(" 当 High >= +12 或 Low <= -12: 蓝色K线 + 强烈箭头 + 弹窗");
Print("═══════════════════════════════════════════════════════════");
}
//+------------------------------------------------------------------+
//| Custom indicator deinitialization function |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
ClearMyObjects();
Print("Deinit Value Chart, reason = "+IntegerToString(reason));
}
//+------------------------------------------------------------------+
//| Value Chart |
//+------------------------------------------------------------------+
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 &TickVolume[],
const long &Volume[],
const int &Spread[])
{
int i,limit;
//--- 动态调整信号数组大小
if(ArraySize(SignalTriggered) != rates_total)
{
ArrayResize(SignalTriggered, rates_total);
ArrayInitialize(SignalTriggered, false);
}
//--- 设置数组为序列
ArraySetAsSeries(SignalTriggered, true);
//--- check for bars count
if(rates_total < DATA_LIMIT)
return(0);
//--- 计算起始位置
if(prev_calculated < DATA_LIMIT)
limit = DATA_LIMIT;
else
limit = prev_calculated - 1;
if(limit < DATA_LIMIT)
limit = DATA_LIMIT;
//--- 主循环
for(i = limit; i < rates_total && !IsStopped(); i++)
{
//--- 计算范围平均值
RangeAverage[i] = High[i] - Low[i];
_AValue = 0.2 * SimpleMA(i, Periode, RangeAverage);
//--- 防止除以零
if(_AValue == 0 || _AValue < 0.0001)
_AValue = 0.0001;
//--- 计算中间价平均值
MiddleAverage[i] = (High[i] + Low[i]) / 2.0;
_BValue = SimpleMA(i, Periode, MiddleAverage);
//--- 计算标准化值
ExtOBuffer[i] = (Open[i] - _BValue) / _AValue;
ExtHBuffer[i] = (High[i] - _BValue) / _AValue;
ExtLBuffer[i] = (Low[i] - _BValue) / _AValue;
ExtCBuffer[i] = (Close[i] - _BValue) / _AValue;
//--- 检查是否达到极端水平
bool isExtreme = false;
bool isUpExtreme = false; // 低价极端 (Low <= -10)
bool isDownExtreme = false; // 高价极端 (High >= 10)
double extremeValue = 0;
// 检查低价极端 (向上信号)
if(ExtLBuffer[i] <= -LEVEL_10)
{
isExtreme = true;
isUpExtreme = true;
extremeValue = ExtLBuffer[i];
}
// 检查高价极端 (向下信号)
if(ExtHBuffer[i] >= LEVEL_10)
{
isExtreme = true;
isDownExtreme = true;
extremeValue = ExtHBuffer[i];
}
//--- 设置K线颜色
if(isExtreme)
{
// 极端信号:蓝色K线
ExtColorBuffer[i] = 2.0;
}
else
{
// 正常情况:根据涨跌设置颜色
if(ExtCBuffer[i] > ExtOBuffer[i])
ExtColorBuffer[i] = 0.0; // 红色上涨
else
ExtColorBuffer[i] = 1.0; // 绿色下跌
}
//--- 触发信号(仅当极端且未触发过)
if(isExtreme && !SignalTriggered[i])
{
SignalTriggered[i] = true;
// 判断是±10还是±12
bool isStrong = false;
if((isUpExtreme && extremeValue <= -LEVEL_12) ||
(isDownExtreme && extremeValue >= LEVEL_12))
{
isStrong = true;
}
// 显示箭头
if(Show_Arrow)
{
if(isUpExtreme) // 低价信号 - 向上箭头
{
double arrowPrice = Low[i] - (High[i] - Low[i]) * 0.2;
color arrowColor = isStrong ? Arrow_Up_Strong : Arrow_Up;
Trace("Value_Chart_Up_"+IntegerToString(i), 1, arrowPrice, Time[i], arrowColor);
}
else if(isDownExtreme) // 高价信号 - 向下箭头
{
double arrowPrice = High[i] + (High[i] - Low[i]) * 0.2;
color arrowColor = isStrong ? Arrow_Down_Strong : Arrow_Down;
Trace("Value_Chart_Down_"+IntegerToString(i), -1, arrowPrice, Time[i], arrowColor);
}
}
// 弹窗提示(仅强烈信号±12)
if(Show_Alert && isStrong)
{
string signalType = isUpExtreme ? "低价" : "高价";
Alert(" |