HQChart实战教程1-外汇分时图

需求

对接第3方外汇数据, 显示外汇分时图,
注意这种分时图是固定时间段的, 是不能左右拖动的。如果要左右拖动的使用K线面积图来做。
第3方数据,接触下来, 一般好像没有当日分时的API接口, 都是给1分钟K线。 所以这边就以1分钟K线来对接。 但如果由当日分钟K线的接口这最好。
数据格式如下
C是收盘价,Tick时间, O是开盘价,H是最高价,L是最低价,A是交易额,V是交易量, D日期+时间

var TEST_DATA={
	"code": 0,
	"obj": [
		{
			"C": 1.1022400000000001,
			"Tick": 1574666640,
			"D": "2019-11-25 15:24:00",
			"O": 1.1022099999999999,
			"H": 1.10225,
			"L": 1.1022099999999999,
			"A": 0,
			"V": 24
		},
		{
			"C": 1.10222,
			"Tick": 1574666580,
			"D": "2019-11-25 15:23:00",
			"O": 1.10225,
			"H": 1.10226,
			"L": 1.1022000000000001,
			"A": 0,
			"V": 58
		},
		.........
		]
}

HQChart需要的数据

  1. 时间段 6:00 - 第2天的5:59 , 1分钟1个数据,一共1440 个数据
  2. 当天的前收盘, 这个是用来画Y 轴中线和计算涨幅用的。
  3. 1分钟数据需要
    price=收盘价 open=开盘价 high=最高 low=最低 amount=金额 vol=成交量 注意了都是数值型,不要字符串
    date=日期 整型 格式 yyyymmdd 如: 20191010 ->2019-10-10
    time=时间 整型 格式 hhmm 如 925 =》 9:15 1318=》13:15

品种代码

hqchart设计的时候要求支持所有品种, 所以内部使用统一的品种代码防止代码重名,品种代码+品种类型后缀。 外汇品种后缀是.FOREX, 如EURUSD =》EURUSD.FOREX

网络协议名字

MinuteChartContainer::RequestMinuteData 分时数据就这1个协议, 当天全量数据和更新都是使用这个协议。

网络协议回调

使用NetworkFilter回调,并且处理 MinuteChartContainer::RequestMinuteData 协议。
把单个协议处理放到不同的函数里面处理, 这样逻辑比较清楚点, 如果都放在NetworkFilter会很乱不方面阅读。如果你们有codeview的话,可以让阅读你代码的人更了解你的思虑。切记一个函数的代码千万不要太长, 太长了不方便阅读。

//网络协议回调
NetworkFilter(data, callback)
{
    console.log('[MinuteChart::NetworkFilter] data', data);
    switch(data.Name)
    {
        case 'MinuteChartContainer::RequestMinuteData':     //当天数据下载
            this.RequestMinuteData(data, callback);
            break;
    }
},

分时数据下载

这里把我数据请求分成2部分,1. 是当前的全量数据下载 2. 当天的最新的分钟数据更细数据
通过判断data.Self.ChartSplashPaint.IsEnableSplash 状态可以知道 是全量还是增量下载数据

RequestMinuteData(data, callback)   //请求分钟数据
{
     data.PreventDefault=true;   //禁止使用HQChart内部请求
     var stock={OriginalSymbol:this.OriginalSymbol, Symbol:data.Request.Data.symbol[0]};    //原始代码, 内部代码
     if (data.Self.ChartSplashPaint.IsEnableSplash)
     {
         console.log('[MinuteChart::RequestMinuteData] first reqeust');
         this.RequestDayMinuteData(data, callback,stock);    //全量数据
     }
     else 
     {
         console.log('[MinuteChart::RequestMinuteData] update reqeust');
         this.RequestUpdateMinuteData(data, callback,stock); //增量数据
     }
 },

当天全量数据下载

这里我把数据保存到了本地, 直接读本地数据了。实际使用的时候改成ajax请求就可以。
stock.OriginalSymbol 是外部的原始代码, 根据这个请求第3方api.

RequestDayMinuteData(data,callback, stock) //请求当天的所有分钟数据
{
     console.log(`[MinuteChart::RequestDayMinuteData] request all minute data . OriginalSymbol=${stock.OriginalSymbol}, Symbol=${stock.Symbol}`);

     //模拟异步请求数据
     setTimeout(() => {
         this.RecvMinuteData(Data.TEST_DATA, callback,stock);
     }, 200);
 },

全量数据转hqchart格式

  1. 由于数据是1分钟K线, 所有需要找到开盘的第1个数据位置(6:00)
  2. 前收盘也需要自己找下, 去6:00的上一个数据收盘价就是当天的昨收盘
  3. 把分钟数据都成hqchart格式的数据
    name:品种的中文名称,
    symbol:品种的代码(带统一后缀的)
    yclose:前收盘 数值型
    minute:当天所有的分钟数据, 数组
  4. 把数据缓存下, 更新数据的时候就更新这个数据就可以了。
  5. 把数据通过 callback() 传个hqchart
RecvMinuteData(recvData,callback,stock)
{
    //分时显示固定时间段 6:00-第2天的5:59
    var startIndex=-1;
    for(var i in recvData.obj) //取最近的一个6点数据
    {
        var item=recvData.obj[i];
        var dateTime=item.D.split(' ');
        if (dateTime[1]=='06:00:00')
        {
            startIndex=parseInt(i);
            break;
        }
    }

    var yClose=parseFloat(recvData.obj[startIndex+1].C);    //昨收盘
    var minuteData=[];   //HQChart 分时数据格式

    //symbol:填hqchart统一的内部代码, name:名称,这个使用原始代码 你也可以用中文名字
    var stockData={name:stock.OriginalSymbol, symbol:stock.Symbol, yclose:yClose, minute:minuteData };

    for(var i=startIndex;i>=0;--i)
    {
        var item=recvData.obj[i];
        var dateTime=new Date(item.D);
        //数据都是数值类型!!!
        var date=dateTime.getFullYear()*10000+(dateTime.getMonth()+1)*100+dateTime.getDate();
        var time=dateTime.getHours()*100+dateTime.getMinutes();
        var stockItem=
        { 
            date:date,
            time:time,
            price:parseFloat(item.C), 
            open:parseFloat(item.O),
            high:parseFloat(item.H),
            low:parseFloat(item.L),
            amount:parseFloat(item.A),
            vol:parseFloat(item.V),
        }

        minuteData.push(stockItem);
    }

    this.Cache=stockData;   //把当天全量数据保存起来

    var hqchartData={stock:[stockData]};	//最后的hqchart格式数据
    callback(hqchartData);
},

增量数据更新下载

这边我没有写请求,用了一个定时器模拟异步,后面的数据也是假的, 实际你们使用ajax请求增量数据就可以。

RequestUpdateMinuteData(data,callback,stock)  //请求当天的最新的分钟数据
{
     console.log(`[MinuteChart::RequestDayMinuteData] request update latest minute data . OriginalSymbol=${stock.OriginalSymbol}, Symbol=${stock.Symbol}`);

     //模拟异步请求数据
     setTimeout(() => 
     {
         var recvData={};
         this.RecvUpdateMinuteData(recvData, callback,stock);
     }, 200);
 },

增量数据更新到hqchart

  1. 取上次缓存的当天的全量数据
  2. 最新数据和全量数据对比下, 得出是增加新的分钟数据还是更新缓存里的最后1条数据。
    如果是新的1分钟数据, 就再minute里面插入
    如果不是新的1分钟, 就更新缓存里的最后1条数据。
  3. 把全量数据通过 callback() 传个hqchart
RecvUpdateMinuteData(recvData,callback,stock)
{
     //最后1分钟时间不变,更新缓存中最后1分钟数据
     var latestItem=this.Cache.minute[this.Cache.minute.length-1];
     latestItem.price=latestItem.price+(Math.ceil(Math.random()*10)*0.0001);   //随便用一个随机数据更新数据  

     //如果有最新一分钟的数据,就往minute.push() 往后插入


      var hqchartData={stock:[this.Cache]};  //把全量数据传给hqchart
      callback(hqchartData);
 }

自动更新频率控制

AutoUpdateFrequency 自动更新频率 单位ms
下面是开启5秒自动更新配置例子。

const option=
 {
      Type: '分钟走势图', //历史分钟走势图
      .......
      IsAutoUpdate: true, //是自动更新数据
      AutoUpdateFrequency:5000,   //数据更新频率
      .......

没有,打完收工了。

上面例子代码 我上传到群文件了 forex.2019.11.26.zip,有兴趣的可以自己下载看看

如果还有问题可以加交流QQ群: 950092318

HQChart代码地址
地址:github.com/jones2000/HQChart

猜你喜欢

转载自blog.csdn.net/jones2000/article/details/103254501