Loading...
Tooltip
是图表交互的核心组件之一,用于动态展示数据点的详细信息,帮助用户快速理解图表中特定区域的数值、分类或其他维度信息。它能够在鼠标悬停、点击或移动到图表中的某个元素(如柱状图中的柱子、折线图中的数据点)时,动态显示相关的数据信息。
{"tooltip": {"title": "name","items": ["genre"]}}
并且结合 view.interaction.tooltip
去配置提示信息的渲染和额外配置。
{"interaction": {"tooltip": {"series": true}}}
当该视图中只有一个标记的时候,通过 mark.interaction.tooltip
配置提示信息的渲染和额外配置也是可以的。
{"interaction": {"tooltip": {"series": true}}}
如果希望不展示该 tooltip 的提示信息,可以通过下面的配置关闭。
{"tooltip": false}
如果希望图表没有提示信息交互,可以通过 chart.interaction
实现。
{"interaction": {"tooltip": false}}
尝试一下
配置项分为两个部分
tooltip
是 Ant Design Charts 中用于展示数据点的详细信息的一个 UI 组件。当用户将鼠标悬停在图表的某个数据点上时,tooltip 会显示该数据点的相关信息,比如坐标值、度量值等。
interaction.tooltip
是 Ant Design Charts 的交互机制的一部分,属于 interaction(交互)模块。它是一种内置的交互行为,用于增强工具提示的功能,特别是在某些特定的交互场景下(如动态显示或隐藏工具提示)。
tooltip
和 interaction.tooltip
中的 tooltip 是两个不同维度的配置,但容易混淆。以下是它们的核心区别:
特性 | tooltip | interaction.tooltip |
---|---|---|
职责 | 定义工具提示的内容、样式和基本行为 | 定义工具提示在交互场景下的行为 |
配置方式 | 通过 chart.tooltip() 配置 | 通过 chart.interaction() 启用或自定义 |
作用范围 | 全局生效,影响整个图表 | 与特定交互行为绑定 |
典型用途 | 设置工具提示的字段、样式、内容等 | 控制工具提示的动态显示/隐藏或其他交互逻辑 |
tooltip
属性 | 描述 | 类型 | 默认值 | 适用于 |
---|---|---|---|---|
title | 设置tooltip 的标题内容:如果值为数据字段名,则会展示数据中对应该字段的数值,如果数据中不存在该字段,将该值作为 title。详见title 配置 | title | ||
nodeTitle | 设置复合图形tooltip 标题的节点title 属性 | title | 桑基图等复合图形 | |
linkTitle | 设置复合图形tooltip 标题的弦title 属性 | title | 桑基图等复合图形 | |
items | 指定tooltip 中显示的字段,默认不同图表有不同的默认字段列表。配合 channel 配置一起使用,效果更佳。详见items 配置 | items | ||
nodeItems | 设置复合图形tooltip 标题的节点items 属性 | items | 桑基图等复合图形 | |
linkItems | 设置复合图形tooltip 标题的弦items 属性 | items | 桑基图等复合图形 |
interaction.tooltip
属性 | 描述 | 类型 | 默认值 | 适用于 |
---|---|---|---|---|
body | 是否展示 tooltip | boolean | true | |
bounding | 控制Tooltip 提示框的显示边界,超出会自动调整位置 | BBox | 图表区域大小 | |
css | 设置 tooltip 样式 | css | ||
crosshairs | 配置是否显示 crosshairs,详见crosshairs 配置 | boolean | ||
crosshairsLineDash | 配置crosshairs 虚线的间隔 | crosshairs 配置 | ||
crosshairsStroke | 配置crosshairs 显示的颜色 | string | ||
crosshairsStrokeWidth | 配置crosshairs 十字辅助线的线条宽度 | number | ||
crosshairsXStroke | 配置crosshairs X 轴显示的颜色 | string | ||
crosshairsXLineDash | 配置crosshairs X 轴虚线的间隔 | crosshairs 配置 | ||
crosshairsXStroke | 配置crosshairs X 轴显示的颜色 | string | ||
crosshairsXStrokeWidth | 配置crosshairs X 轴十字辅助线的线条宽度 | number | ||
crosshairsYStroke | 配置crosshairs Y 轴显示的颜色 | string | ||
crosshairsYLineDash | 配置crosshairs Y 轴虚线的间隔 | crosshairs 配置 | ||
crosshairsYStroke | 配置crosshairs Y 轴显示的颜色 | string | ||
crosshairsYStrokeWidth | 配置crosshairs Y 轴十字辅助线的线条宽度 | number | ||
disableNative | 禁用 pointerover 和 pointerout 事件 | boolean | false | |
enterable | tooltip 是否允许鼠标滑入 | boolean | false | |
filter | item 筛选器 | (d: TooltipItemValue) => any | - | |
groupName | 是否使用 groupName | boolean | true | |
leading | 是否在时间间隔开始的时候更新提示信息 | boolean | true | |
marker | 是否展示 marker | boolean | true | |
marker${StyleAttrs} | marker 的样式 | number | string | - | |
markerType | markerType 是提示框(Tooltip)配置项中的一个属性,用于控制提示框中标记点(Marker)的样式 | 'hollow' | undefined | undefined | |
mount | 指定提示框的挂载节点 | string | HTMLElement | 图表容器 | |
position | 设置 tooltip 的固定展示位置,相对于数据点 | TooltipPosition | ||
offset | 在位置方向上的偏移量 | [number, number] ` | [10, 10] | |
render | 自定义渲染tooltip 内容[render] (#自定义渲染内容) | (event, options) => HTMLElement | string | ||
series | 是否是系列元素的 tooltip | boolean | 多条折线、多组柱状图 | |
shared | 相同 x 的元素是否共享 tooltip | boolean | false | |
sort | item 排序器 | (d: TooltipItemValue) => any | - | |
trailing | 是否在时间间隔结束的时候更新提示信息 | boolean | false | |
trailing | 是否在时间间隔结束的时候更新提示信息 | boolean | false | |
wait | 提示信息更新的时间间隔,单位为毫秒 | number | 50 |
type TooltipPosition = 'top' | 'bottom' | 'left' | 'right' | 'top-left' | 'top-right' | 'bottom-left' | 'bottom-right';type BBox = { x: number, y: number, width: number, height: number };
crosshairs
是提示框(Tooltip)的辅助线功能,用于在图表中标记当前数据点的精确位置,通常以横向或纵向的参考线形式呈现,帮助用户更直观地定位数据。
{"interaction": {"legendFilter": false,"elementPointMove": true,"tooltip": {"crosshairs": true,"crosshairsStroke": "red","crosshairsLineDash": [4,4],"markerType": "hollow"}}}
title
是一个用于显示当前悬停数据点的 主标题 的字段,通常用于表示数据点所属的分类或上下文信息。
title
可以直接写入一个固定显示的字符串,或者一个方法从data
中动态获取标题
{"tooltip": {}}
在不需要设置 title 的时候,可以直接声明为一个数组:
{"tooltip": ["genre","sold"]}
其中完整的 title 结构如下:
细分配置项名称 | 类型 | 功能描述 |
---|---|---|
channel | string | 定义生成 title 的通道 |
field | string | 定义生成 title 的的字段 |
value | string | title 的值 |
valueFormatter | string | Function | 格式化 title |
它们的值(value)可以通过来自原始数据,通过字符串或者 title.field
指定。
{"tooltip": {"title": "sold","items": ["genre"]}}
{"tooltip": {"title": {"field": "sold"},"items": [{"field": "genre"}]}}
它们的值(value)可以来自通道值,通过 title.channel
指定,常常用于使用 mark.transform
生成新通道的图表。
{"tooltip": {"title": {"channel": "x"},"items": [{"channel": "y"}]}}
可以通过 title.valueFormatter
去指定 title 值(value)的展示,title.valueFormatter
可以是一个函数,也可以一个 d3-format 支持的字符串。
chart.options({tooltip: {title: {field: 'sold', valueFormatter: (sold) => sold.toUpperCase()}items: [{ channel: 'y', valueFormatter: '.0%' }],},});
当然对于 title 还提供了回调去获得最大的个性化配置能力。
chart.options({tooltip: {title: (datum, index, data, column) => ({value: `<span style="color: #00ff00; font-style: italic;">${d.letter}</span>`,custom: ...}),items: [(datum, index, data, column) => ({color: d.sold > 150 ? 'red' : 'blue', // 指定 item 的颜色name: index === 0 ? d.genre : `${d.genre} ${data[i].genre}`, // 指定 item 的名字value: column.y.value[i], // 使用 y 通道的值、custom: ...}),],},});
items 返回值可用作 interaction.tooltip.render
的入参,您可以设置一些自定义参数。详见自定义渲染内容
复合图形配置
复合图形在配置tooltip.title
时需要分别配置节点与弦
({tooltip: {nodeTitle: (d) => d.key,linkTitle: (d) => 'link',},});
items
是 tooltip 配置中的一个关键属性,items
是一个数组,表示工具提示中每一项的内容。每一项通常对应于一个数据字段或一个图形元素(例如柱状图的一根柱子、折线图的一个点等)。通过自定义 items
,可以灵活地控制工具提示的显示内容,包括名称、值、颜色等信息。
其中完整的 title 结构如下:
细分配置项名称 | 类型 | 功能描述 |
---|---|---|
color | string | marker 的颜色 |
field | string | 定义生成 item 的的字段 |
name | string | item 的名字 |
value | string | item 的值 |
channel | string | 定义生成 item 的值的通道 |
valueFormatter | string | Function | 格式化 item |
items
的 value
、channel
、valueFormatter
属性的配置方式与title
一致,详细配置请参考title
名称
通过name
可以便捷的修改tooltip
中item
的名字,通过channel
来匹配图标中对应的条目。
chart.options({tooltip: {items: [{name: '张三', channel: 'y1'},{name: '李四', channel: 'y2'},],},});
颜色
tooltip
会自动根据图标内容分配tooltip
item
的颜色,但是实际应用中,可能需要根据一些规则来指定某些颜色,此时就可以通过color
属性来配置。通过channel
来匹配图标中对应的条目。
chart.options({tooltip: {items: [{color: 'pink', channel: 'y1'},{color: '#f00', channel: 'y2'},],},});
复合图形配置
复合图形在配置tooltip.items
时需要分别配置节点与弦
({tooltip: {nodeItems: [(datum, index, data, column) => {return {color: 'red', // 指定 item 的颜色name: '节点', // 指定 item 的名字value: d.key, // 使用 y 通道的值content: '节点自定义属性',};},],linkItems: [(datum, index, data, column) => {return {color: 'red', // 指定 item 的颜色name: '连接线', // 指定 item 的名字value: `${d.source.key}-${d.target.key}`, // 使用 y 通道的值content: '连接线自定义属性',};},],},});
tooltip
的 cssStyle 配置项允许通过 CSS 样式直接自定义提示框的外观, 可快速实现提示框的视觉定制,适配不同主题或交互场景需求。
{"transform": [{"type": "dodgeX"}],"legend": false,"interaction": {"tooltip": {"shared": true,"mount": "body","css": {".g2-tooltip": {"background": "#eee","border-radius": " 0.25em !important"},".g2-tooltip-title": {"font-size": "20px","font-weight": "bold","padding-bottom": "0.25em"},".g2-tooltip-list-item": {"background": "#ccc","padding": "0.25em","margin": "0.25em","border-radius": "0.25em"},".g2-tooltip-list-item-name-label": {"font-weight": "bold","font-size": "16px"},"g2-tooltip-list-item-marker": {"border-radius": "0.25em","width": "15px","height": "15px"},".g2-tooltip-list-item-value": {"font-weight": "bold","font-size": "16px"}}}}}
尝试一下
有时候内置的 Tooltip 无法满足需求,这时候可以通过 mark.interaction.tooltip.render
或者 view.interaction.tooltip.render
的 render 函数来渲染自定义的提示。
该 render 函数接受事件对象 event 和提示数据 tooltipData,返回一个 string 或者 DOM 对象。其中 event 是 @antv/g 抛出的鼠标对象,tooltipData 是通过 mark.tooltip
声明的 title 和 items 数据。如果返回值是一个 string,那么会作为 tooltip 容器的 innerHTML,否则会挂载该返回值。一个提示的 render 函数的定义大概如下:
function render(event, tooltipData) {const { title, items } = tooltipData;return `<div></div>`;}function render(event, tooltipData) {const { title, items } = tooltipData;return `<div></div>`;}
下面是一个简单的例子:
{"interaction": {"tooltip": {}}}
获取自定义 render 参数
render 函数提供了强大的个性化配置能力,通过对tooltip.render
函数返回参数的配置,自定义interaction.tooltip.render
的入参
chart.options({tooltip: {items: [(datum, index, data, column) => ({color: d.sold > 150 ? 'red' : 'blue', // 指定 item 的颜色name: index === 0 ? d.genre : `${d.genre} ${data[i].genre}`, // 指定 item 的名字value: column.y.value[i], // 使用 y 通道的值、custom1: '自定义参数1',custom2: '自定义参数2'}),],},interaction: {tooltip: {// render 回调方法返回一个innerHTML 或者 DOMrender: (event, { title, items }) => {return `<div><h3 style="padding:0;margin:0">${title}</h3><ul>${items.map(({ color, name, value, custom1, custom2 }) => ...)}</ul></div>`,}}}});
桑基图这种复合图形怎么使用 data 中的补充属性实现自定义 tooltip 的展示?
和一般Mark
自定义tooltip
交互的方法类似,先在图形的tooltip.render
里返回自定义属性,然后在interaction.render
里使用。
({data: {value: {nodes: [{ id: 'a', key: '首页', des: '节点自定义属性' },{ id: 'b', key: '页面1', des: '节点自定义属性' },{ id: 'b_1', key: '页面1', des: '节点自定义属性' },{ id: 'c', key: '页面2', des: '节点自定义属性' },{ id: 'c_1', key: '页面2', des: '节点自定义属性' },{ id: 'd', key: '页面3', des: '节点自定义属性' },{ id: 'd_1', key: '页面3', des: '节点自定义属性' },],links: [{ source: 'a', target: 'b', value: 100 },{ source: 'b', target: 'c', value: 80 },{ source: 'b', target: 'd', value: 20 },{ source: 'c', target: 'b_1', value: 80 },{ source: 'b_1', target: 'c_1', value: 40 },{ source: 'b_1', target: 'd_1', value: 40 },],},transform: [{callback: (data) => ({nodes: data.nodes,links: data.links,}),},],},tooltip: {nodeItems: [(datum, index, data, column) => {return {content: d.des,};z;},],linkItems: [(datum, index, data, column) => {return {color: 'red', // 指定 item 的颜色name: '连接线', // 指定 item 的名字value: `${d.source.key}-${d.target.key}`, // 使用 y 通道的值content: '连接线自定义属性',};},],},layout: {nodeId: (d) => d.id,nodeAlign: 'center',nodePadding: 0.03,iterations: 25,},style: {labelSpacing: 3,labelFontWeight: 'bold',linkFillOpacity: 0.2,linkFill: '#3F96FF',},interaction: {tooltip: {render: (e, { items, title }) => {return `<div>${items[0].content}</div>`;},},},});({data: {value: {nodes: [{ id: 'a', key: '首页', des: '节点自定义属性' },{ id: 'b', key: '页面1', des: '节点自定义属性' },{ id: 'b_1', key: '页面1', des: '节点自定义属性' },{ id: 'c', key: '页面2', des: '节点自定义属性' },{ id: 'c_1', key: '页面2', des: '节点自定义属性' },{ id: 'd', key: '页面3', des: '节点自定义属性' },{ id: 'd_1', key: '页面3', des: '节点自定义属性' },],links: [{ source: 'a', target: 'b', value: 100 },{ source: 'b', target: 'c', value: 80 },{ source: 'b', target: 'd', value: 20 },{ source: 'c', target: 'b_1', value: 80 },{ source: 'b_1', target: 'c_1', value: 40 },{ source: 'b_1', target: 'd_1', value: 40 },],},transform: [{callback: (data) => ({nodes: data.nodes,links: data.links,}),},],},tooltip: {nodeItems: [(datum, index, data, column) => {return {content: d.des,};z;},],linkItems: [(datum, index, data, column) => {return {color: 'red', // 指定 item 的颜色name: '连接线', // 指定 item 的名字value: `${d.source.key}-${d.target.key}`, // 使用 y 通道的值content: '连接线自定义属性',};},],},layout: {nodeId: (d) => d.id,nodeAlign: 'center',nodePadding: 0.03,iterations: 25,},style: {labelSpacing: 3,labelFontWeight: 'bold',linkFillOpacity: 0.2,linkFill: '#3F96FF',},interaction: {tooltip: {render: (e, { items, title }) => {return `<div>${items[0].content}</div>`;},},},});({data: {value: {nodes: [{ id: 'a', key: '首页', des: '节点自定义属性' },{ id: 'b', key: '页面1', des: '节点自定义属性' },{ id: 'b_1', key: '页面1', des: '节点自定义属性' },{ id: 'c', key: '页面2', des: '节点自定义属性' },{ id: 'c_1', key: '页面2', des: '节点自定义属性' },{ id: 'd', key: '页面3', des: '节点自定义属性' },{ id: 'd_1', key: '页面3', des: '节点自定义属性' },],links: [{ source: 'a', target: 'b', value: 100 },{ source: 'b', target: 'c', value: 80 },{ source: 'b', target: 'd', value: 20 },{ source: 'c', target: 'b_1', value: 80 },{ source: 'b_1', target: 'c_1', value: 40 },{ source: 'b_1', target: 'd_1', value: 40 },],},transform: [{callback: (data) => ({nodes: data.nodes,links: data.links,}),},],},tooltip: {nodeItems: [(datum, index, data, column) => {return {content: d.des,};z;},],linkItems: [(datum, index, data, column) => {return {color: 'red', // 指定 item 的颜色name: '连接线', // 指定 item 的名字value: `${d.source.key}-${d.target.key}`, // 使用 y 通道的值content: '连接线自定义属性',};},],},layout: {nodeId: (d) => d.id,nodeAlign: 'center',nodePadding: 0.03,iterations: 25,},style: {labelSpacing: 3,labelFontWeight: 'bold',linkFillOpacity: 0.2,linkFill: '#3F96FF',},interaction: {tooltip: {render: (e, { items, title }) => {return `<div>${items[0].content}</div>`;},},},});({data: {value: {nodes: [{ id: 'a', key: '首页', des: '节点自定义属性' },{ id: 'b', key: '页面1', des: '节点自定义属性' },{ id: 'b_1', key: '页面1', des: '节点自定义属性' },{ id: 'c', key: '页面2', des: '节点自定义属性' },{ id: 'c_1', key: '页面2', des: '节点自定义属性' },{ id: 'd', key: '页面3', des: '节点自定义属性' },{ id: 'd_1', key: '页面3', des: '节点自定义属性' },],links: [{ source: 'a', target: 'b', value: 100 },{ source: 'b', target: 'c', value: 80 },{ source: 'b', target: 'd', value: 20 },{ source: 'c', target: 'b_1', value: 80 },{ source: 'b_1', target: 'c_1', value: 40 },{ source: 'b_1', target: 'd_1', value: 40 },],},transform: [{callback: (data) => ({nodes: data.nodes,links: data.links,}),},],},tooltip: {nodeItems: [(datum, index, data, column) => {return {content: d.des,};z;},],linkItems: [(datum, index, data, column) => {return {color: 'red', // 指定 item 的颜色name: '连接线', // 指定 item 的名字value: `${d.source.key}-${d.target.key}`, // 使用 y 通道的值content: '连接线自定义属性',};},],},layout: {nodeId: (d) => d.id,nodeAlign: 'center',nodePadding: 0.03,iterations: 25,},style: {labelSpacing: 3,labelFontWeight: 'bold',linkFillOpacity: 0.2,linkFill: '#3F96FF',},interaction: {tooltip: {render: (e, { items, title }) => {return `<div>${items[0].content}</div>`;},},},});({data: {value: {nodes: [{ id: 'a', key: '首页', des: '节点自定义属性' },{ id: 'b', key: '页面1', des: '节点自定义属性' },{ id: 'b_1', key: '页面1', des: '节点自定义属性' },{ id: 'c', key: '页面2', des: '节点自定义属性' },{ id: 'c_1', key: '页面2', des: '节点自定义属性' },{ id: 'd', key: '页面3', des: '节点自定义属性' },{ id: 'd_1', key: '页面3', des: '节点自定义属性' },],links: [{ source: 'a', target: 'b', value: 100 },{ source: 'b', target: 'c', value: 80 },{ source: 'b', target: 'd', value: 20 },{ source: 'c', target: 'b_1', value: 80 },{ source: 'b_1', target: 'c_1', value: 40 },{ source: 'b_1', target: 'd_1', value: 40 },],},transform: [{callback: (data) => ({nodes: data.nodes,links: data.links,}),},],},tooltip: {nodeItems: [(datum, index, data, column) => {return {content: d.des,};z;},],linkItems: [(datum, index, data, column) => {return {color: 'red', // 指定 item 的颜色name: '连接线', // 指定 item 的名字value: `${d.source.key}-${d.target.key}`, // 使用 y 通道的值content: '连接线自定义属性',};},],},layout: {nodeId: (d) => d.id,nodeAlign: 'center',nodePadding: 0.03,iterations: 25,},style: {labelSpacing: 3,labelFontWeight: 'bold',linkFillOpacity: 0.2,linkFill: '#3F96FF',},interaction: {tooltip: {render: (e, { items, title }) => {return `<div>${items[0].content}</div>`;},},},});
chart.on() 方法将指定的监听器注册到 chart 上,当该对象触发指定的事件时,指定的回调函数就会被执行。
chart.on('tooltip:show', (event) => {console.log(event.data.data);});chart.on('tooltip:hide', () => {console.log('hide');});
尝试一下
{"tooltip": {"items": [{}]}}
null;
{"tooltip": {"items": [{"title": "a","items": [{"channel": "x"},{"channel": "y"}]}]}}
对于 Interval、Point 等非系列 Mark,控制展示的方式如下:
{"call": {}}
对于 Line、Area 等系列 Mark,控制展示的方式如下:
隐藏的方式如下:
chart.emit('tooltip:hide');
chart.emit('tooltip:disable');chart.emit('tooltip:enable');
默认情况下,crossharisY
是开启的,crosshairsX
是关闭的,所以如果要开启十字辅助线,有以下两种方式。
crosshairs
为true
。{"interaction": {"tooltip": {"crosshairs": true,"crosshairsXStroke": "red","crosshairsYStroke": "blue"}}}
crosshairsX
为true
。{"interaction": {"tooltip": {"crosshairsX": true,"crosshairsXStroke": "red","crosshairsYStroke": "blue"}}}
crosshairsX
的优先级大于crosshairs
的优先级。
{"interaction": {"tooltip": {"markerType": "hollow"}}}