- 前端
- 图表库
- 金融科技
- 数据可视化
【免费下载链接】lightweight-charts
Performant financial charts built with HTML5 canvas
Lightweight Charts™ 是一款基于 HTML5 Canvas 的高性能金融图表库。本文以仓库内 website/versioned_docs/version-4.0/intro.md 入门文档为骨架,结合仓库源码,系统讲解其运行环境要求、安装方式、构建变体选择、许可署名要求,以及从创建图表、创建序列到设置与更新数据的完整上手流程。读完本文,你将能够独立完成一个可运行的金融图表页面,并理解createChart、setData、update等核心 API 的底层行为。
运行环境要求:客户端优先,基于 ES2016
Lightweight Charts™ 首先是一个客户端(client-side)库,这意味着它默认无法在服务端(如 Node.js)直接运行,至少开箱即用是不支持的。这一设计决定了它天然适合在浏览器中渲染,服务的职责通常只是提供数据。
lightweight-charts包的代码面向ES2016 语言规范编译。因此,你运行图表的所有浏览器都需要支持这一语言版本(可参考 ECMA-262 7.0 规范及其兼容性表)。如果业务上必须支持更早的语言版本,可以在自己的构建系统中对包进行转译(例如借助 Babel)到目标版本;若转译过程遇到问题,可以向项目仓库提交 issue 并附上详细信息,官方会调查可能的解决方案。
从仓库源码也可以印证这一架构定位:createChart等入口位于 src/api/create-chart.ts,其底层通过 ChartApi 在传入的 DOM 容器中挂载图表控件,整个渲染链路依赖浏览器环境提供的 DOM 与 Canvas 能力。
安装与构建变体
安装lightweight-charts非常简单,使用 npm 即可:
npm install --save lightweight-charts需要注意的是,该包自带 TypeScript 类型声明,因此你可以直接在 TypeScript 代码中使用它,无需额外安装类型定义。仓库根目录的 package.json 中typings字段指向dist/typings.d.ts,主入口module/main指向dist/lightweight-charts.production.mjs,这从发布物层面印证了"开箱即用、自带类型"的承诺。
构建变体(Build variants)
库发布时包含以下构建变体,可按依赖是否内置、开发/生产模式、模块格式进行选择:
| 依赖包含 | 模式 | ES module | CommonJS ⚠️ | IIFE(window.LightweightCharts) | | - | - | - | - | - | | 否 | PROD |lightweight-charts.production.mjs|lightweight-charts.production.cjs| N/A | | 否 | DEV |lightweight-charts.development.mjs|lightweight-charts.development.cjs| N/A | | 是(standalone) | PROD |lightweight-charts.standalone.production.mjs| - |lightweight-charts.standalone.production.js| | 是(standalone) | DEV |lightweight-charts.standalone.development.mjs| - |lightweight-charts.standalone.development.js|
⚠️弃用提示:CommonJS 支持计划在 2024 年初从库中移除。从当前仓库 package.json 的exports字段可以看到,ES module(import)已是主推形态,且通过development/production条件导出自动区分开发与生产构建。fancy-canvas是唯一的运行时依赖,这也是"standalone"变体之所以存在的原因——它把依赖一并打包进去,适用于通过<script>标签直接引入的场景。
许可与署名(License and attribution)
:::tip Lightweight Charts™ 的许可证要求在产品中注明 TradingView 为产品创建者。 :::
你需要在面向用户的网站或移动应用页面中加入来自 NOTICE 文件的"署名声明",并附带指向https://www.tradingview.com的链接。仓库根目录的 NOTICE 文件内容即:
TradingView Lightweight Charts™ Copyright (с) 2025 TradingView, Inc. https://www.tradingview.com/官方希望你将署名声明放置在醒目的位置,作为对 Lightweight Charts™ 创作的回馈。
创建图表:认识createChart入口
安装完成后即可创建你的第一张图表。首先,在需要创建图表的文件中引入库:
import { createChart } from 'lightweight-charts';createChart是创建图表的唯一入口函数,你可以通过它创建任意数量的图表:
import { createChart } from 'lightweight-charts'; // ... // 在代码的任意位置 const firstChart = createChart(document.getElementById('firstContainer')); const secondChart = createChart(document.getElementById('secondContainer'));该函数返回一个IChartApi对象,后续所有与图表实例的交互(操作时间轴、价格轴、事件订阅、销毁等)都通过它完成。
源码视角:createChart如何工作
从 src/api/create-chart.ts 可以看到,createChart的容器参数既可以是 DOM 元素的id 字符串,也可以是HTMLElement 对象本身:
export function fetchHtmlElement(container: string | HTMLElement): HTMLElement { if (isString(container)) { const element = document.getElementById(container); assert(element !== null, `Cannot find element in DOM with id=${container}`); return element; } return container; }若传入的 id 在 DOM 中不存在,会抛出明确的断言错误。createChart内部通过createChartEx配合默认的时间型水平轴行为(HorzScaleBehaviorTime)构造ChartApi实例;更进阶的场景下,你还可以使用createChartEx传入自定义的IHorzScaleBehavior来定制水平轴,或使用defaultHorzScaleBehavior()获取默认实现作为扩展基类。这一点在 src/index.ts 的导出清单中同样可见(createChart、createChartEx、defaultHorzScaleBehavior、createYieldCurveChart、createOptionsChart一并导出)。
创建序列:六种内置类型与统一命名约定
图表创建好后就可以展示数据了。展示数据的基本单元是序列(series)。库内置了六种序列类型:
- Area(面积图)
- Bar(柱状图)
- Baseline(基线图)
- Candlestick(K 线图)
- Histogram(直方图)
- Line(折线图)
创建指定类型的序列,需要使用IChartApi上对应的方法。所有方法遵循统一的命名约定add<type>Series,其中<type>即你想要创建的序列类型:
import { createChart } from 'lightweight-charts'; const chart = createChart(container); const areaSeries = chart.addAreaSeries(); const barSeries = chart.addBarSeries(); const baselineSeries = chart.addBaselineSeries(); // ... 以此类推关于不同序列类型的详细差异,可参考 series-types.md。
需要注意:序列无法从一种类型转换为另一种类型,因为不同类型的序列具有不同的数据结构和选项类型。若需要展示另一种形态,应重新创建一个新序列。
版本演进说明:addXxxSeries与定义式 API
version-4.0 文档中的addAreaSeries()等便捷方法是当时的官方 API。而从当前仓库主版本(package.json 中版本号为 5.2.1)的源码看,便捷方法已演进为定义式 API:通过chart.addSeries(LineSeries, options)传入从 src/index.ts 导出的序列定义对象(LineSeries、AreaSeries、CandlestickSeries等)来创建序列,定义式方法见 src/api/ichart-api.ts。如果你使用的仍是 v4.0 版本,则继续沿用本文的addXxxSeries写法即可;升级到 v5 后需迁移为addSeries定义式写法。
源码视角:序列数据模型
不同序列类型的数据结构由 src/model/data-consumer.ts 定义。例如:
SingleValueData:单值序列(Area、Line、Histogram)的数据基类,含time与value字段;WhitespaceData:仅含time的空数据点,可用于在时间轴上占位(如周末、停牌日),并支持customValues扩展字段供插件使用;AreaData/BaselineData:在单值基础上扩展了lineColor、topColor、bottomColor等逐点颜色覆盖字段。
这些类型通过SeriesDataItemTypeMap与各序列类型映射,保证setData/update的参数在编译期就被严格约束。
设置与更新数据:setData与update
图表和序列创建完成后,就可以向序列写入数据了。无论序列类型如何,API 调用方式都相同(只是数据类型可能不同)。
用setData设置(替换)全部数据
ISeriesApi.setData用于设置数据,或整体替换序列中的全部数据项:
const chartOptions = { layout: { textColor: CHART_TEXT_COLOR, background: { type: 'solid', color: CHART_BACKGROUND_COLOR } } }; const chart = createChart(document.getElementById('container'), chartOptions); const areaSeries = chart.addAreaSeries({ lineColor: LINE_LINE_COLOR, topColor: AREA_TOP_COLOR, bottomColor: AREA_BOTTOM_COLOR, }); areaSeries.setData([ { time: '2018-12-22', value: 32.51 }, { time: '2018-12-23', value: 31.11 }, { time: '2018-12-24', value: 27.02 }, { time: '2018-12-25', value: 27.32 }, { time: '2018-12-26', value: 25.17 }, { time: '2018-12-27', value: 28.89 }, { time: '2018-12-28', value: 25.46 }, { time: '2018-12-29', value: 23.92 }, { time: '2018-12-30', value: 22.68 }, { time: '2018-12-31', value: 22.67 }, ]); const candlestickSeries = chart.addCandlestickSeries({ upColor: BAR_UP_COLOR, downColor: BAR_DOWN_COLOR, borderVisible: false, wickUpColor: BAR_UP_COLOR, wickDownColor: BAR_DOWN_COLOR, }); candlestickSeries.setData([ { time: '2018-12-22', open: 75.16, high: 82.84, low: 36.16, close: 45.72 }, { time: '2018-12-23', open: 45.12, high: 53.90, low: 45.12, close: 48.09 }, { time: '2018-12-24', open: 60.71, high: 60.71, low: 53.39, close: 59.29 }, { time: '2018-12-25', open: 68.26, high: 68.26, low: 59.04, close: 60.50 }, { time: '2018-12-26', open: 67.71, high: 105.85, low: 66.67, close: 91.04 }, { time: '2018-12-27', open: 91.04, high: 121.40, low: 82.70, close: 111.40 }, { time: '2018-12-28', open: 111.51, high: 142.83, low: 103.34, close: 131.25 }, { time: '2018-12-29', open: 131.33, high: 151.17, low: 77.68, close: 96.43 }, { time: '2018-12-30', open: 106.33, high: 110.20, low: 90.39, close: 98.10 }, { time: '2018-12-31', open: 109.87, high: 114.69, low: 85.66, close: 111.26 }, ]); chart.timeScale().fitContent();需要注意几点:
- 时间格式:示例中
time使用的是 ISO 格式的业务日字符串(如'2018-12-22')。从 src/model/horz-scale-behavior-time/types.ts 可以看到,Time类型实际是三种形式的联合:UTCTimestamp | BusinessDay | string,即 UNIX 时间戳(秒)、{ year, month, day }业务日对象、或 ISO 业务日字符串。分时等日内数据建议使用UTCTimestamp(注意是秒而非毫秒,Date.now() / 1000后再断言类型)。 - 数据顺序:
setData要求数据按时间升序排列(更早的时间点在前)。 - 一次性替换:
setData会整体替换旧数据,若只是增量更新,应优先使用update。 - 示例末尾的
chart.timeScale().fitContent()用于让时间轴自动缩放到恰好容纳全部数据。
用update增量更新数据(实时场景)
当数据持续变化(例如实时行情推送)时,频繁调用setData会影响性能,官方不推荐这样做;同时它会整体替换全部序列数据,通常也不是你想要的。此时应使用ISeriesApi.update方法,它允许更新最后一个数据项或追加新数据项,开销远小于setData:
import { createChart } from 'lightweight-charts'; const chart = createChart(container); const areaSeries = chart.addAreaSeries(); areaSeries.setData([ // ... 其他数据项 { time: '2018-12-31', value: 22.67 }, ]); const candlestickSeries = chart.addCandlestickSeries(); candlestickSeries.setData([ // ... 其他数据项 { time: '2018-12-31', open: 109.87, high: 114.69, low: 85.66, close: 111.26 }, ]); // 稍后某个时刻 // 更新最近的一根 bar areaSeries.update({ time: '2018-12-31', value: 25 }); candlestickSeries.update({ time: '2018-12-31', open: 109.87, high: 114.69, low: 85.66, close: 112 }); // 创建新的 bar areaSeries.update({ time: '2019-01-01', value: 20 }); candlestickSeries.update({ time: '2019-01-01', open: 112, high: 112, low: 100, close: 101 });源码视角:update的语义细节
从 src/api/iseries-api.ts 的方法签名可以看到,update(bar, historicalUpdate?)的行为约定如下:
- 新数据项的
time必须大于或等于当前最新数据项的时间; - 若传入数据项的时间与最新数据项相等,则替换现有数据项(这正是"更新最新一根 K 线"的实现方式);
- 可选的第二个参数
historicalUpdate(默认false)允许更新非最新的历史数据点,但官方明确提示:更新历史数据的性能会低于更新最新数据点。
此外,ISeriesApi还提供了pop(count)从序列尾部移除数据、data()获取全部原始数据、dataByIndex(logicalIndex, mismatchDirection)按逻辑索引查询数据、subscribeDataChanged(handler)订阅数据变更事件等一系列配套方法,均可在 src/api/iseries-api.ts 中查看完整的 JSDoc 与使用示例,适合在实现数据加载、增量同步等场景时按需选用。
小结:一条完整的上手链路
回顾整个流程,使用 Lightweight Charts™ 的标准链路是:
- 环境检查:确认目标浏览器支持 ES2016;需要在服务端或旧浏览器运行时,考虑转译方案;
- 安装:
npm install --save lightweight-charts,按需选择 ES module / CommonJS / IIFE 与 PROD / DEV 构建变体; - 创建图表:
createChart(container, options?),容器传元素 id 或 HTMLElement 皆可; - 创建序列:通过
add<type>Series()(v4)或addSeries(LineSeries)(v5)创建六种内置类型之一,注意类型不可转换; - 灌入数据:首次使用
setData全量加载(按时间升序),实时场景使用update更新最新 bar 或追加新 bar; - 视图调整:用
chart.timeScale().fitContent()等 API 控制可见范围。
关于时间轴、价格轴的更多操控方式,可继续阅读仓库内 time-scale.md 与 price-scale.md;若想了解各序列类型的样式与行为差异,series-types.md 是很好的下一站。
- 前端
- 图表库
- 金融科技
- 数据可视化
【免费下载链接】lightweight-charts
Performant financial charts built with HTML5 canvas
相关推荐
SimpleInjector快速上手:10分钟搭建你的第一个依赖注入容器
SimpleInjector快速上手:10分钟搭建你的第一个依赖注入容器 SimpleInjector是一个简单、灵活且高效的依赖注入库,它通过倡导最佳实践引导
软件架构如何快速上手Lightweight Charts:金融图表库完整指南
如何快速上手Lightweight Charts:金融图表库完整指南 Lightweight Charts是一个基于HTML5 Canvas构建的高性能金融图表
前端图表库金融科技数据可视化如何快速集成高性能金融图表?Lightweight Charts™ 完整指南 🚀
如何快速集成高性能金融图表?Lightweight Charts™ 完整指南 🚀 Lightweight Charts™ 是一款基于 HTML5 Canvas
前端图表库金融科技数据可视化
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考