结构高低点 + 趋势线(MT5)(二创)
相对上一版改了:这个指标给我生成 mt5的呗
效果示意图 · AI 根据源码绘制
//+------------------------------------------------------------------+
//| SwingPointTrendLine.mq5 |
//| 量化交易摆动点趋势线指标 |
//| 基于 XAUOF 社区作品 #5《结构高低点 + 趋势线(MT4)》(作者 XAUOF 官方)二次创作 |
//| 改动:从 MQL4 转换为 MQL5 语法 |
//+------------------------------------------------------------------+
#property copyright "Swing Point Trend Line Indicator - MT5"
#property link ""
#property version "2.00"
#property indicator_chart_window
#property indicator_buffers 2
#property indicator_plots 2
//---- 可调参数
input int SwingBars = 5; // 左右比较的K线数量(推荐3-10)
input bool ShowTrendLines = true; // 是否显示趋势线
input color UpTrendColor = clrLime; // 上升趋势线颜色
input color DownTrendColor = clrRed; // 下降趋势线颜色
input int LineWidth = 2; // 趋势线粗细(1-5)
//---- 指标缓冲区
double HighDots[]; // 摆动高点标记
double LowDots[]; // 摆动低点标记
//---- 全局变量
datetime lastHighTime1 = 0, lastHighTime2 = 0; // 最近两个高点时间
double lastHighPrice1 = 0, lastHighPrice2 = 0; // 最近两个高点价格
datetime lastLowTime1 = 0, lastLowTime2 = 0; // 最近两个低点时间
double lastLowPrice1 = 0, lastLowPrice2 = 0; // 最近两个低点价格
string upTrendLineName = "UpTrendLine_MT5";
string downTrendLineName = "DownTrendLine_MT5";
//+------------------------------------------------------------------+
//| 指标初始化函数 |
//+------------------------------------------------------------------+
int OnInit()
{
// 设置指标缓冲区 0:摆动高点
SetIndexBuffer(0, HighDots, INDICATOR_DATA);
PlotIndexSetInteger(0, PLOT_DRAW_TYPE, DRAW_ARROW);
PlotIndexSetInteger(0, PLOT_ARROW, 159); // 小圆点符号
PlotIndexSetString(0, PLOT_LABEL, "摆动高点");
PlotIndexSetInteger(0, PLOT_ARROW_SHIFT, 0);
PlotIndexSetInteger(0, PLOT_LINE_COLOR, clrRed);
// 设置指标缓冲区 1:摆动低点
SetIndexBuffer(1, LowDots, INDICATOR_DATA);
PlotIndexSetInteger(1, PLOT_DRAW_TYPE, DRAW_ARROW);
PlotIndexSetInteger(1, PLOT_ARROW, 159);
PlotIndexSetString(1, PLOT_LABEL, "摆动低点");
PlotIndexSetInteger(1, PLOT_ARROW_SHIFT, 0);
PlotIndexSetInteger(1, PLOT_LINE_COLOR, clrLime);
// 设置空值
PlotIndexSetDouble(0, PLOT_EMPTY_VALUE, EMPTY_VALUE);
PlotIndexSetDouble(1, PLOT_EMPTY_VALUE, EMPTY_VALUE);
// 清空之前的趋势线
ObjectDelete(0, upTrendLineName);
ObjectDelete(0, downTrendLineName);
return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| 指标清理函数 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
// 删除趋势线对象
ObjectDelete(0, upTrendLineName);
ObjectDelete(0, downTrendLineName);
Comment(""); // 清空提示文字
}
//+------------------------------------------------------------------+
//| 主计算函数 |
//+------------------------------------------------------------------+
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[])
{
// 数据不足时返回
if(rates_total < SwingBars * 2 + 1)
return(0);
// 将数组设置为时间序列(索引 0 = 最新 K 线)
ArraySetAsSeries(time, true);
ArraySetAsSeries(high, true);
ArraySetAsSeries(low, true);
ArraySetAsSeries(close, true);
ArraySetAsSeries(HighDots, true);
ArraySetAsSeries(LowDots, true);
// 确定计算起点
int start = SwingBars;
if(prev_calculated > SwingBars)
start = 1; // 只计算最新的几根
else
start = rates_total - SwingBars - 1; // 首次全量计算
// 初始化缓冲区
ArrayInitialize(HighDots, EMPTY_VALUE);
ArrayInitialize(LowDots, EMPTY_VALUE);
// 遍历K线识别摆动点(从旧到新)
for(int i = start; i < rates_total - SwingBars; i++)
{
// 检查是否为摆动高点
bool isSwingHigh = true;
for(int j = 1; j <= SwingBars; j++)
{
// 检查索引范围
if(i - j < 0 || i + j >= rates_total)
{
isSwingHigh = false;
break;
}
// 左右都不能有更高的高点(注意时间序列方向)
if(high[i - j] >= high[i] || high[i + j] >= high[i])
{
isSwingHigh = false;
break;
}
}
// 如果是摆动高点,标记并记录
if(isSwingHigh)
{
HighDots[i] = high[i] + 10 * _Point; // 在高点上方显示
// 更新最近两个高点
if(time[i] > lastHighTime1)
{
lastHighTime2 = lastHighTime1;
lastHighPrice2 = lastHighPrice1;
lastHighTime1 = time[i];
lastHighPrice1 = high[i];
}
else if(time[i] > lastHighTime2)
{
lastHighTime2 = time[i];
lastHighPrice2 = high[i];
}
}
// 检查是否为摆动低点
bool isSwingLow = true;
for(int j = 1; j <= SwingBars; j++)
{
// 检查索引范围
if(i - j < 0 || i + j >= rates_total)
{
isSwingLow = false;
break;
}
// 左右都不能有更低的低点
if(low[i - j] <= low[i] || low[i + j] <= low[i])
{
isSwingLow = false;
break;
}
}
// 如果是摆动低点,标记并记录
if(isSwingLow)
{
LowDots[i] = low[i] - 10 * _Point; // 在低点下方显示
// 更新最近两个低点
if(time[i] > lastLowTime1)
{
lastLowTime2 = lastLowTime1;
lastLowPrice2 = lastLowPrice1;
lastLowTime1 = time[i];
lastLowPrice1 = low[i];
}
else if(time[i] > lastLowTime2)
{
lastLowTime2 = time[i];
lastLowPrice2 = low[i];
}
}
}
// 绘制趋势线
if(ShowTrendLines)
{
DrawTrendLines();
}
// 检查价格突破
CheckBreakout(close[0]);
return(rates_total);
}
//+------------------------------------------------------------------+
//| 绘制趋势线 |
//+------------------------------------------------------------------+
void DrawTrendLines()
{
// 删除旧的趋势线
ObjectDelete(0, upTrendLineName);
ObjectDelete(0, downTrendLineName);
// 绘制下降趋势线(连接两个高点)
if(lastHighTime1 > 0 && lastHighTime2 > 0 && lastHighTime1 != lastHighTime2)
{
ObjectCreate(0, downTrendLineName, OBJ_TREND, 0, lastHighTime2, lastHighPrice2, lastHighTime1, lastHighPrice1);
ObjectSetInteger(0, downTrendLineName, OBJPROP_COLOR, DownTrendColor);
ObjectSetInteger(0, downTrendLineName, OBJPROP_WIDTH, LineWidth);
ObjectSetInteger(0, downTrendLineName, OBJPROP_RAY_RIGHT, true); // 延长到右边
ObjectSetInteger(0, downTrendLineName, OBJPROP_SELECTABLE, true);
ObjectSetInteger(0, downTrendLineName, OBJPROP_BACK, false); // 前景显示
}
// 绘制上升趋势线(连接两个低点)
if(lastLowTime1 > 0 && lastLowTime2 > 0 && lastLowTime1 != lastLowTime2)
{
ObjectCreate(0, upTrendLineName, OBJ_TREND, 0, lastLowTime2, lastLowPrice2, lastLowTime1, lastLowPrice1);
ObjectSetInteger(0, upTrendLineName, OBJPROP_COLOR, UpTrendColor);
ObjectSetInteger(0, upTrendLineName, OBJPROP_WIDTH, LineWidth);
ObjectSetInteger(0, upTrendLineName, OBJPROP_RAY_RIGHT, true);
ObjectSetInteger(0, upTrendLineName, OBJPROP_SELECTABLE, true);
ObjectSetInteger(0, upTrendLineName, OBJPROP_BACK, false);
}
}
//+------------------------------------------------------------------+
//| 检查价格突破 |
//+------------------------------------------------------------------+
void CheckBreakout(double currentPrice)
{
bool breakoutDetected = false;
string breakoutMsg = "";
// 计算当前时间对应的趋势线价格
datetime currentTime = TimeCurrent();
// 检查上升趋势线突破(价格跌破)
if(lastLowTime1 > 0 && lastLowTime2 > 0 && lastLowTime1 != lastLowTime2)
{
// 计算趋势线斜率
double timeDiff = (double)(lastLowTime1 - lastLowTime2);
if(timeDiff > 0)
{
double priceDiff = lastLowPrice1 - lastLowPrice2;
double slope = priceDiff / timeDiff;
// 计算当前时间点的趋势线价格
double trendLinePrice = lastLowPrice1 + slope * (currentTime - lastLowTime1);
// 价格跌破上升趋势线
if(currentPrice < trendLinePrice)
{
breakoutDetected = true;
breakoutMsg = "结构已破:跌破上升趋势线";
}
}
}
// 检查下降趋势线突破(价格突破向上)
if(lastHighTime1 > 0 && lastHighTime2 > 0 && lastHighTime1 != lastHighTime2)
{
// 计算趋势线斜率
double timeDiff = (double)(lastHighTime1 - lastHighTime2);
if(timeDiff > 0)
{
double priceDiff = lastHighPrice1 - lastHighPrice2;
double slope = priceDiff / timeDiff;
// 计算当前时间点的趋势线价格
double trendLinePrice = lastHighPrice1 + slope * (currentTime - lastHighTime1);
// 价格突破下降趋势线
if(currentPrice > trendLinePrice)
{
breakoutDetected = true;
breakoutMsg = "结构已破:突破下降趋势线";
}
}
}
// 显示提示信息
if(breakoutDetected)
{
Comment("\n", breakoutMsg, "\n当前价格: ", DoubleToString(currentPrice, _Digits));
}
else
{
Comment(""); // 清空提示
}
}作品说明
好的,我帮你把这个 MT4 指标转成 MT5 版本。核心逻辑完全保留,只是语法适配到 MQL5。
相对原作改动:
- 从 MQL4 语法转换为 MQL5 语法
- 去掉
#property strict(MQL5 默认严格) - 增加
#property indicator_buffers和indicator_plots声明 SetIndexStyle/SetIndexArrow/SetIndexLabel改为PlotIndexSetInteger/PlotIndexSetString- 数组用
ArraySetAsSeries设置为时间序列模式,保持 MT4 习惯的索引方向 - 对象操作函数参数微调(MT5 的
ObjectCreate等接口略有不同)
使用说明
- 安装方法
- 将代码保存为
结构高低点_趋势线_MT5.mq5 - 放到 MT5 数据文件夹的
MQL5\Indicators\目录 - 在 MetaEditor 中编译,或重启 MT5 自动编译
- 在图表上右键「技术指标」→「Custom」→选择本指标
- 参数调整
- SwingBars:摆动点识别灵敏度,数值越小识别的点越多(3-10 推荐)
- ShowTrendLines:开关趋势线显示
- UpTrendColor / DownTrendColor:上升/下降趋势线颜色
- LineWidth:趋势线粗细
- 信号说明
- 红色圆点标记摆动高点,绿色圆点标记摆动低点
- 红色趋势线连接最近两个高点(下降趋势线)
- 绿色趋势线连接最近两个低点(上升趋势线)
- 图表左上角会提示「结构已破」信息:价格突破趋势线时触发
- 注意事项
- 摆动点识别有滞后性,确认需要等待 SwingBars 根 K 线走完
- 趋势线会自动延长到右侧,可手动拖动调整
- 仅识别结构,不构成交易建议,需结合其他指标确认
AI 解读根据源码逐行分析写成,供参考,以实际运行为准
这是什么
这是一个 MT5 平台上的结构识别指标。它会在图表上自动找出摆动高点和低点(就是那些「局部最高」和「局部最低」的 K 线),用红绿圆点标出来,然后连接最近的两个高点和两个低点画出趋势线。当价格突破这些趋势线时,会在图表左上角提示「结构已破」。适合用来抓关键支撑阻力位和潜在反转点。
逻辑原理
指标会检查每根 K 线,如果它的高点比左右各 SwingBars 根 K 线都高,就标记为摆动高点;如果低点比左右各 SwingBars 根都低,就是摆动低点。每次发现新的摆动点,就更新记录,保留最近的两个高点和两个低点。
趋势线逻辑:红色下降趋势线连接最近两个高点并向右延长;绿色上升趋势线连接最近两个低点并向右延长。指标会实时计算当前价格相对趋势线的位置,如果价格向上穿过下降趋势线或向下穿过上升趋势线,就触发突破提示。
参数说明
- SwingBars(默认 5):识别摆动点的灵敏度。数字越小识别的点越多(比如 3 会很密集),越大越严格(比如 10 只标注大级别转折)。推荐 3-10,日内短线用 3-5,波段用 7-10。
- ShowTrendLines(默认 true):是否显示趋势线。关掉后只显示摆动点圆点,不画线。
- UpTrendColor(默认绿色):上升趋势线的颜色。
- DownTrendColor(默认红色):下降趋势线的颜色。
- LineWidth(默认 2):趋势线粗细,范围 1-5,数字越大线越粗。
怎么用
把编译好的指标文件放到 MT5 数据文件夹的 MQL5\Indicators\ 目录下,重启 MT5 或在导航器里刷新。打开任意图表,右键选「技术指标」→「Custom」→找到本指标双击添加。
添加后图表上会出现红色和绿色圆点,分别标记高点和低点。如果开启了趋势线,会看到红绿两条延长线。图表左上角有文字提示,平时是空的,价格突破趋势线时会显示「结构已破:突破下降趋势线」或「跌破上升趋势线」。
趋势线可以手动拖动调整,但每次新 K 线更新时会重新画,所以手动调整会被覆盖。建议只看自动画的,不要自己改。
适用场景
适合所有品种和周期,但不同周期用法不同。H1 和 H4 适合抓日内或短波段的结构转折;D1 和 W1 适合看大级别趋势的支撑阻力。黄金、外汇、指数都能用,流动性好的品种效果更稳定。
震荡行情里摆动点会很密集,趋势线频繁突破,容易假信号;单边趋势行情里摆动点少,趋势线更可靠。适合配合其他指标或价格行为一起用,比如看到突破提示后,再确认有没有放量或 K 线形态配合。
不适合超高频剥头皮(M1、M5 图上摆动点太多太乱)和流动性差的小品种(价格跳动大,摆动点不规律)。
风险提示
摆动点识别有滞后,必须等右侧 SwingBars 根 K 线走完才能确认。比如 SwingBars=5,那么当前 K 线右边要再走 5 根才能判断它是不是高点,实际延迟可能有几个小时到几天。看到圆点出现时,那个转折点已经是历史了。
趋势线突破提示也是基于收盘价实时计算的,盘中可能反复突破又回来,产生假信号。只有 K 线收盘后确认突破才更可靠。而且趋势线是机械连接两个点画的,不考虑市场结构的复杂性,可能跟手工画的支撑阻力位有偏差。
指标本身不重绘(已确认的摆动点不会消失),但趋势线会随着新摆动点出现而更新,旧的线会被删掉重新画。如果你手动调整了线的位置,下次更新会丢失。
这个工具只负责标注结构,不提供进出场信号,不能单独作为交易依据。配合其他确认手段使用,控制好仓位和止损。
常见问题
- 这个指标会重绘吗?
- 摆动点本身不会重绘,一旦标记就不会消失。但趋势线会随着新的高低点出现而更新(删掉旧线画新线),所以趋势线的位置会变化。
- SwingBars 参数设多少合适?
- 默认 5 适合 H1 和 H4 图。如果在 M15-M30 做短线,可以降到 3;如果在 D1 看大趋势,可以提到 8-10。数字越小识别的点越多,越大越严格。
- 突破提示是实时的吗,会不会有假信号?
- 是实时计算的,盘中价格可能反复穿越趋势线产生多次提示。建议以 K 线收盘后的提示为准,盘中的当参考。
- MT4 能用这个指标吗?
- 不能,这是 MT5 版本。代码用的是 MQL5 语法,MT4 无法加载。如果需要 MT4 版本,可以找原作《结构高低点 + 趋势线(MT4)》。
- 可以用在加密货币或股票上吗?
- 可以。指标逻辑不限品种,只要是 K 线图都能用。但加密货币波动大,建议把 SwingBars 调大一点过滤噪音;股票在开盘前后可能出现跳空,趋势线连接会不连续。
Swing Point Structure Trend Line Indicator MT5
An MT5 indicator that automatically identifies swing highs/lows and draws trend lines connecting them. Monitors price breakouts in real-time with customizable sensitivity and colors.
Source code is shown above. Compiled EX5 files are available to VIP members.
评论
还没有人评论,来抢个沙发。