沿时间轴滚动图表

MetaTrader 5 用户都很熟悉快速图表导航面板,可通过双击时间轴左上方或按下 SpaceInput 键来打开该面板。通过 ChartNavigate函数同样能以编程实现类似功能。

bool ChartNavigate(long chartId, ENUM_CHART_POSITION position, int shift = 0)

该函数将 chartId图表相对于position 参数指定的预定义图表位置,按指定的柱线数量进行移动。它属于 ENUM_CHART_POSITION 枚举类型,包含以下元素:

标识符

说明

CHART_BEGIN

图表起始位置(最早的价格)

CHART_CURRENT_POS

当前位置

CHART_END

图表结束位置(最新价格)

shift参数用于设置图表应移动的柱线数量。正数会将图表向右移动(向结束位置),负数会将图表向左移动(向起始位置)。

如果成功,该函数返回 true,如果发生错误,则返回 false

为了测试该函数,我们来创建一个简单脚本ChartNavigate.mq5。通过输入变量,用户可以选择起始点和偏移量(以柱线为单位)。

#property script_show_inputs
 
input ENUM_CHART_POSITION Position = CHART_CURRENT_POS;
input int Shift = 0;
   
void OnStart()
{
   ChartSetInteger(0CHART_AUTOSCROLLfalse);
   const int start = (int)ChartGetInteger(0CHART_FIRST_VISIBLE_BAR);
   ChartNavigate(0PositionShift);
   const int stop = (int)ChartGetInteger(0CHART_FIRST_VISIBLE_BAR);
   Print("Moved by: "stop - start", from "start" to "stop);
}

日志会显示移动前后第一个可见柱线的编号。

一个更实用的示例是脚本ChartSynchro.mq5,该脚本允许在手动滚动其中一个图表时,同步滚动所有运行该脚本的图表。因此,你可以同步同一金融工具不同时间范围的窗口,或分析不同金融工具的平行价格走势。

void OnStart()
{
   datetime bar = 0// current position (time of the first visible bar)
  
   conststring namePosition =__FILE__;// global variable name
  
   ChartSetInteger(0,CHART_AUTOSCroll,false); // disable autoscroll
  
   while(!IsStopped())
   {
      const bool active = ChartGetInteger(0CHART_BRING_TO_TOP);
      const int move = (int)ChartGetInteger(0CHART_FIRST_VISIBLE_BAR);
   
      // the active chart is the leader, and the rest are slaves
      if(active)
      {
         const datetime first = iTime(_Symbol_Periodmove);
         if(first != bar)
         {
            // if the position has changed, save it in a global variable
            bar = first;
            GlobalVariableSet(namePositionbar);
            Comment("Chart "ChartID(), " scrolled to "bar);
         }
      }
      else
      {
         const datetime b = (datetime)GlobalVariableGet(namePosition);
      
         if(b != bar)
         {
            // if the value of the global variable has changed, adjust the position
            bar = b;
            const int difference = move - iBarShift(_Symbol_Periodbar);
            ChartNavigate(0CHART_CURRENT_POSdifference);
            Comment("Chart "ChartID(), " forced to "bar);
         }
      }
    
      Sleep(250);
   }
   Comment("");
}

通过第一个可见柱线的日期和时间 (CHART_FIRST_VISIBLE_BAR) 实现对齐。该脚本通过循环检测此值,如果在活动图表上运行,则将其写入一个全局变量。其他图表上的脚本读取此变量,并通过ChartNavigate相应地调整其位置。参数指定图表的相对移动 (CHART_CURRENT_POS),而移动的柱线数量则定义为当前第一个可见柱线的编号与从全局变量中读取的编号之间的差值。

下图展示了 EURUSD 的 H1 和 M15 图表的同步结果。

用于同步图表位置的脚本示例

用于同步图表位置的脚本示例

在熟悉系统 图表事件后,我们将会将此脚本转换为指标,并移除无限循环。