tradingview 是什么?

当你点开这片博文的的时候相信不需要我介绍你也应该知道tradingview是什么的工具了,而我也是刚接触这个工具不久,国内的资料少之又少,在掉落99根头发的情况下可以简单的运用,特此在此处记录一下,希望正在看博客的你可以少掉一些头发~


申请图表库

准备好公司的营业执照与公章,进入官网申请授权。申请需要等待7个工作日,届时会有工作人员和你邮箱联系。收集了一些资源在下方链接,你可以在申请期间阅读查看,不过这有些难度。

在这里插入图片描述


在选择框架时取决于公司的框架要求,tradingview 官方也为不同的框架提供了实例,这使得我们开发的过程更加简单了一点点,但无论选择什么框架都是大同小异的,这里我从我选择的vuejs框架进行记录学习开发过程的步骤,希望可以帮助到正在看这篇博客的你!

附件:

1.tradingview 申请地址
2.github 项目地址
3.tradingview 官方文档
4.在不同的框架上运行 tradingview
5.超级详细的中文文档


框架的选择

在选择框架时取决于公司的框架要求,tradingview 官方也为不同的框架提供了实例,这使得我们开发的过程更加简单了一点点,但无论选择什么框架都是大同小异的,这里我从我选择的vuejs框架进行记录学习开发过程的步骤,希望可以帮助到正在看这篇博客的你!

在这里插入图片描述


运行官方的实例

在下载好官方的实例后,我选择了vuejs的框架,在readme.md文件中告诉你如何启动文件。

  1. Install dependencies npm install.

  2. Copy charting_library folder from https://github.com/tradingview/charting_library/ to /public folder. The earliest supported version of the Charting Library is 1.12. If you get 404 then you need to request an access to this repository.

  3. Copy charting_library.min.js from https://github.com/tradingview/charting_library/ to /src folder.

  4. Copy datafeeds folder from https://github.com/tradingview/charting_library/ to /public.

  5. Run npm run serve. It will build the project and open a default browser with the Charting Library.

执行npm install命令下载所有依赖,如果node-sass报错可以执行npm install node-sass@latest --save-dev下载解决;第二部我们需要把charting_library文件和datafeeds文件移入到public文件夹中,再将charting_library文件夹中的charting_library.min.js文件复制到src文件夹下,执行npm run serve即可在浏览器中看见K线的组件在运行了,不过这个不是我们自己的数据,我们需要连接自己的数据!!!

在这里插入图片描述

如果你想要在自己的创建的项目中引入这个组件,你还需要在index.html中引入polyfills.js和bundle.js


链接自己的数据

这一步应该是至关重要的,也应该是大部分小伙伴最头疼的一部分,在此处推荐大家看一下附件5中的超级详细的中文文档,这可能会让你很头疼,但是后期一个项目想要完善就离不开这个文档,当然在接下的记录中我也是过呢根据文档来进行一步一步的来连接自己的数据!!!


1.绘制界面

我们讲图表的对象创建出来,绑定在#tv_chart_container的元素上面,接下来的事情就全部的交给JS Api,也就是自定义的Datafeed类。不要企图跳过这一段落,这是tradingview能够现在在页面中显示关键一步。下面的代码请仔细看哦,看着很多内容,但是其实很简单,从头到尾看一遍应该就会明白的。

<template>
  <div class="exchage" id="tv_chart_container"></div>
</template>

<script>
import { widget } from '../charting_library.min';
import http from '../util/http';
import Datafeed from '../util/datafeed';

// 定义变量读取参数
let datafeed;

export default {
  data(){
    return {
      // 定义参数接收接受图表
      tvWidget: null,
    }
  },
  mounted(){
  	// 创建datafeed实例,此时实例为自己编写的类,需要按照官网的规则编写
    datafeed = new Datafeed();
    // 实例化的widget里的参数都是图表的配置项,具体解析可以看一下文档,后续还有有很多的配置对tradingview进行美化,暂时我们将忽略这不无关紧要的配置。
    this.tvWidget = new widget({
      symbol: 'btc_usdt',
      datafeed,
      interval: '15',
      container_id: 'tv_chart_container',
      library_path: '/charting_library/',
      timezone: 'Asia/Shanghai',
      debug: false,
      autosize: true
    });
  }
}
</script>

<style scoped>
.exchage{
  height: calc(100vh - 80px);
}
</style>

2.编辑Datafeed类

DataFeed类有很多函数,其中思数据渲染出来关键的函数有四个,所以我们将用这四个函数来完成K线图的渲染工作。

class DataFeed {
  constructor() {

  }

  // 服务端配置
  onReady(cb) {

  }

  // 解析数据
  resolveSymbol(symbolName, onSymbolResolvedCallback, onResolveErrorCallback) {

  }

  // 渲染首次视图的数据
  getBars(symbolInfo, resolution, from, to, onHistoryCallback, onErrorCallback, firstDataRequest) {

  }

  // 新数据更新
  subscribeBars(symbolInfo, resolution, onRealtimeCallback, listenerGuid, onResetCacheNeededCallback) {

  }
}

export default DataFeed;

onReady(callback)

此方法可以设置图表库支持的图表配置。这些数据会影响到图表支持的功能,所以它被称为服务端定制。
图表库要求您使用回调函数来传递datafeed的 configurationData参数。


以上就是官方文档的原话,我们需要通过回调函数传递一个参数,这个参数如下,特别提一下supported_resolutions参数是K线的周期数组,单位为分钟,也就是分线日线等。其他的想都不要想,继续向下写就能见证奇迹!

  onReady(cb) {
    cb({
      exchanges: [],
      symbols_types: [],
      supports_time: true,
      supported_resolutions: [1, 5, 15, 30, 60, 240, 360, 480, 720, 1440, 10080, 44640],
      supports_marks: false,
      supports_timescale_marks: false
    })
  }

resolveSymbol(…arg)

在这个函数里我们可以设置表可以显示那些数据也就是上面说的分线日线等

  resolveSymbol(symbolName, onSymbolResolvedCallback, onResolveErrorCallback) {
    var data = {
      name: symbolName,
      has_intraday: true, // 分钟数据
      has_daily: true, // 日k线数据
      has_weekly_and_monthly: true, // 月,周数据
    };

    if (!this.onSymbolResolvedCallback) {
      this.onSymbolResolvedCallback = onSymbolResolvedCallback;
    }

    setTimeout(function() {
      onSymbolResolvedCallback(data);
    }, 0);
  }

getBars(…agr)

在这个函数里我们可以设置表可以显示那些数据也就是上面说的分时线等,同时最关键的异步就是这一步可以将K线数据渲染在页面!!!

  // 渲染首次视图的数据
  getBars(symbolInfo, resolution, from, to, onHistoryCallback, onErrorCallback, firstDataRequest) {
    this.firstDataRequest = firstDataRequest;
    this.onHistoryCallback = onHistoryCallback;
    this.resolution = resolution;
    // 封装函数渲染视图
    this.history(from * 1000, to * 1000, onHistoryCallback);
  }

  // 封装渲染视图的函数
  async history(from, to, cb) {

    if (to && to < 1262275200000) {
      this.bar = [];
      cb([], {
        noData: true
      });
      return;
    }
    let bar = [];
    const step = this.resolution * 60

    if (this.firstDataRequest) {
      try {
    	// 请求k线数据
        http.send().then(res => {
          if(res.status === 200) {
            const { data } = res;
            const len = data.length;
            if(len > 0) {
              data.map(item => {
                let barValue = {};
                // 时间戳
                barValue.time = Number(item[0]);
                // 开
                barValue.open = Number(item[1]);
                // 高
                barValue.high = Number(item[2]);
                // 低
                barValue.low = Number(item[3]);
                // 收
                barValue.close = Number(item[4]);
                // 量
                barValue.volume = Number(item[5]);
                bar.push(barValue);
              })
              cb(bar, {
                noData: false
              });
            } else {
              cb([], {
                noData: true
              });
            }
          } else {
            cb([], {
              noData: true
            });
          }
        })
      } catch (err) {}
    }
    this.bar = bar;
  }

当你完成此步骤时,按下 Ctrl+S 键时,页面将会展现出K线的数据,一切都是那么妙不可言呀~

subscribeBars(…agr)

想要实现数据实时更新,你看可以使用websocket或者http轮询的方式,这里看个人选择;在subscribeBars中当您调用onRealtimeCallback且K线时间等于最新K线时间时,那么这条最新K线将被您传入的K线所替换,这样就可以实现数据实时更新,关键的问题就是怎么去调用onRealtimeCallback函数,由于本人也不知道如何去调用这个onRealtimeCallback函数,于是我便把这个函数给了一个公共的参数,把websocket推送过来的数据写在公众的数据里面,写一个轮询去执行这个函数实现数据更新。

  subscribeBars(symbolInfo, resolution, onRealtimeCallback, listenerGuid, onResetCacheNeededCallback) {
    this.onResetCacheNeededCallback = onResetCacheNeededCallback
    if (this._subscribers.hasOwnProperty(listenerGuid)) {
      return;
    }
    this._subscribers[listenerGuid] = {
      lastBarTime: null,
      listener: onRealtimeCallback,
      resolution: resolution,
      symbolInfo: symbolInfo
    };
  }
  
  // 更新
  update(listenerGuid, lastBar) {
    // 已取消监听取消追加
    if (!this._subscribers.hasOwnProperty(listenerGuid)) {
      return;
    }
    let subscriptionRecord = this._subscribers[listenerGuid];
    if (
      subscriptionRecord.lastBarTime !== null &&
      lastBar.time < subscriptionRecord.lastBarTime
    ) {
      return;
    }
    const isNewBar =
      subscriptionRecord.lastBarTime !== null &&
      lastBar.time > subscriptionRecord.lastBarTime;
    if (isNewBar) {
      subscriptionRecord.lastBarTime = lastBar.time;
    }
    subscriptionRecord.listener(lastBar);
  }

  // 循环读取实时数据
  async readTicker() {
    // ws 将数据存放在 windown.g_k_ticker 中
    if(window.g_k_ticker && window.g_k_ticker.length) {
        for (let listenerGuid in this._subscribers) {
          let item = window.g_k_ticker;
          if (item[0]) {
            let d = {
              time : parseInt(item[0]),
              open : Number(item[1]),
              high : Number(item[2]),
              low : Number(item[3]),
              close : Number(item[4]),
              volume : Number(item[5])
            };
            // 更新 tradingView 视图
            this.update(listenerGuid, d);
          }
        }
    }
    // 更新完成后清空上次的数据
    window.g_k_ticker = [];
    // 轮询延时
    await new Promise(resolve => {
      setTimeout(resolve, 300);
    });
    // 轮询
    this.readTicker();
  }

总结

一个简单的tradingview图表就这样实现了,在以上的代码中可能你会看的有点懵懂的状态,不过没关系,一步一步的写下去,一步一步的输出打印,但最后就一定会可以实现K线的功能,而接下来的就是一下UI界面的调整来适配,这些都是次要的,仔细看文档的配置就可以慢慢调整UI样式,当然如果以上的写法中有什么不足或者错误的地方欢迎在评论区浏览,看到后一定第一时间与大家互动交流~

Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐