ECharts 的 Tooltip 组件是数据可视化交互中非常重要的一部分。用户将鼠标移动到图表中的柱形、折线、散点或其他数据元素上时,Tooltip 可以动态展示对应的数据详情。合理配置 Tooltip,不仅能够让图表信息更加直观,还可以提升复杂数据场景下的阅读效率。
ECharts 默认 Tooltip 已经能够满足基础的数据提示需求,但在实际项目中,经常需要调整显示位置、触发方式、内容格式、背景样式,甚至根据不同数据动态生成 HTML 内容。这些需求都可以通过 Tooltip 的高级配置实现。
Tooltip的基本配置
最简单的 Tooltip 配置如下:
const option = {
tooltip: {
show: true
},
xAxis: {
type: 'category',
data: ['周一', '周二', '周三', '周四', '周五']
},
yAxis: {
type: 'value'
},
series: [
{
type: 'line',
data: [120, 200, 150, 80, 170]
}
]
};show: true 表示显示 Tooltip。实际上 ECharts 中 Tooltip 默认就是开启状态,因此通常不需要单独配置。
如果希望关闭鼠标悬浮提示,可以设置:
tooltip: {
show: false
}对于需要交互查看数据的统计图表,不建议轻易关闭 Tooltip,因为它能够补充坐标轴标签无法完整表达的数据细节。
trigger:控制Tooltip触发方式
trigger 是 Tooltip 定制中最常使用的配置之一,它决定 Tooltip 是针对单个数据项显示,还是针对整个坐标轴显示。
常见配置包括:
tooltip: {
trigger: 'item'
}item 表示数据项触发。鼠标移动到某个柱子、折线节点或散点时,只显示当前数据项的信息。
例如柱状图:
tooltip: {
trigger: 'item'
}如果希望鼠标移动到某个类目后,同时查看该类目下多个系列的数据,可以使用:
tooltip: {
trigger: 'axis'
}例如多折线图:
const option = {
tooltip: {
trigger: 'axis'
},
xAxis: {
type: 'category',
data: ['1月', '2月', '3月', '4月']
},
yAxis: {
type: 'value'
},
series: [
{
name: '销售额',
type: 'line',
data: [120, 180, 160, 230]
},
{
name: '订单量',
type: 'line',
data: [80, 120, 110, 150]
}
]
};此时鼠标移动到某一个月份时,Tooltip 可以同时展示销售额和订单量。
一般来说,单系列图表可以考虑 item,多系列折线图、柱状图等场景通常更适合 axis。
formatter:自定义Tooltip内容
如果说 trigger 决定 Tooltip 什么时候显示,那么 formatter 则决定 Tooltip 显示什么内容。
例如:
tooltip: {
trigger: 'item',
formatter: '{b}
数值:{c}'
}这里使用了 ECharts 提供的字符串模板。
常见变量包括:
{a}:系列名称{b}:数据项名称{c}:数据值{d}:饼图等特定图表中的百分比等数据{@xxx}:数据集维度相关值
如果需要更复杂的内容,可以直接使用 JavaScript 函数:
tooltip: {
trigger: 'item',
formatter: function(params) {
return `
${params.name}
销售额:${params.value} 元
`;
}
}箭头函数写法也很常见:
tooltip: {
formatter: (params) => {
return `${params.name}
销售额:${params.value} 元`;
}
}这种方式适合需要添加单位、业务说明、计算结果或自定义 HTML 结构的场景。
trigger为axis时如何处理formatter参数
使用:
tooltip: {
trigger: 'axis'
}时,formatter 接收到的参数通常是一个数组,因为同一个坐标轴位置可能对应多个系列。
例如:
tooltip: {
trigger: 'axis',
formatter: function(params) {
let html = `${params[0].axisValue}
`;
params.forEach(item => {
html += `${item.marker}${item.seriesName}:${item.value}
`;
});
return html;
}
}最终效果类似:
3月
● 销售额:160
● 订单量:110这里的 params[0].axisValue 可以获得当前坐标轴对应的类目,而 item.seriesName 和 item.value 分别对应系列名称和数据值。
实际开发时需要特别注意 item 和 axis 两种触发方式的参数结构不同,否则很容易出现 params.seriesName 获取不到值的问题。
自定义Tooltip中的单位
数据可视化项目中,经常需要给数值添加单位,例如人民币、件、%、℃ 等。
可以直接在 formatter 中处理:
tooltip: {
formatter: function(params) {
return `
${params.name}
销售额:${params.value} 万元
`;
}
}如果数据本身是百分比:
tooltip: {
formatter: function(params) {
return `${params.name}
占比:${params.value}%`;
}
}对于数值格式化,还可以结合 JavaScript 的 toLocaleString():
tooltip: {
formatter: function(params) {
const value = Number(params.value);
return `${params.name}
金额:${value.toLocaleString()} 元`;
}
}这样可以将较大的数字转换成带千位分隔符的形式,例如 1234567 显示为 1,234,567。
自定义Tooltip样式
Tooltip 的外观可以通过多个配置项调整。
例如:
tooltip: {
backgroundColor: 'rgba(0, 0, 0, 0.75)',
borderColor: '#666',
borderWidth: 1,
textStyle: {
color: '#fff',
fontSize: 14
}
}其中:
backgroundColor:Tooltip 背景颜色borderColor:边框颜色borderWidth:边框宽度textStyle:文字样式
还可以设置圆角:
tooltip: {
borderRadius: 6
}如果希望控制内边距,可以使用:
tooltip: {
padding: [10, 15]
}也可以使用单个数字:
tooltip: {
padding: 10
}这对于统一后台管理系统的图表视觉风格非常实用。
使用extraCssText增强Tooltip样式
当内置样式配置无法满足需求时,可以使用 extraCssText 添加额外 CSS。
例如:
tooltip: {
extraCssText: `
box-shadow: 0 4px 12px rgba(0, 0, 0, 0.2);
border-radius: 8px;
`
}也可以控制最大宽度:
tooltip: {
extraCssText: `
max-width: 300px;
white-space: normal;
`
}这种方式适合对 Tooltip 进行更细致的视觉定制。
自定义Tooltip位置
默认情况下,ECharts 会根据鼠标位置自动计算 Tooltip 的显示位置。如果希望固定位置,可以使用 position。
例如:
tooltip: {
position: 'top'
}也可以指定具体坐标:
tooltip: {
position: [20, 20]
}更灵活的方式是使用函数:
tooltip: {
position: function(point, params, dom, rect, size) {
return [point[0] + 10, point[1] - 20];
}
}其中 point 是鼠标位置,可以根据鼠标坐标动态调整 Tooltip。
例如希望 Tooltip 始终位于鼠标右侧:
tooltip: {
position: function(point) {
return [point[0] + 15, point[1]];
}
}对于大屏、仪表盘等复杂布局,合理设置 Tooltip 位置可以减少遮挡图表数据的问题。
confine:限制Tooltip不超出图表区域
如果 Tooltip 内容比较长,或者图表靠近页面边缘,默认情况下 Tooltip 可能出现部分超出容器的情况。
可以设置:
tooltip: {
confine: true
}启用后,ECharts 会尽量将 Tooltip 限制在图表容器范围内。
对于后台系统中的固定尺寸图表、数据大屏和嵌入式图表,这个参数尤其值得关注。
axisPointer:自定义坐标轴指示器
当使用:
tooltip: {
trigger: 'axis'
}时,通常还会出现坐标轴指示器。通过 axisPointer 可以控制它的样式和类型。
例如十字准星:
tooltip: {
trigger: 'axis',
axisPointer: {
type: 'cross'
}
}常见类型包括:
axisPointer: {
type: 'line'
}以及:
axisPointer: {
type: 'shadow'
}其中:
line:显示直线指示器shadow:显示阴影区域cross:显示十字准星
柱状图经常使用 shadow,折线图则可以使用 line 或 cross。
还可以调整指示器标签:
tooltip: {
trigger: 'axis',
axisPointer: {
type: 'cross',
label: {
show: true
}
}
}Tooltip显示多个系列数据
多系列图表是 Tooltip 定制中非常典型的应用场景。
例如:
tooltip: {
trigger: 'axis',
formatter: function(params) {
let result = `${params[0].axisValue}
`;
params.forEach(item => {
result += `
${item.marker}
${item.seriesName}:
${item.value}
`;
});
return result;
}
}item.marker 可以保留 ECharts 自动生成的系列标记,使 Tooltip 与图表中的系列颜色对应起来。
如果需要按照业务规则重新排序,也可以先对参数进行处理:
formatter: function(params) {
params.sort((a, b) => b.value - a.value);
let result = `${params[0].axisValue}
`;
params.forEach(item => {
result += `${item.marker}${item.seriesName}:${item.value}
`;
});
return result;
}这样就可以根据数值大小调整 Tooltip 中的数据排列顺序。
Tooltip中使用图片或图标
formatter 返回的是 HTML 字符串,因此可以加入图片、图标等元素。
例如:
tooltip: {
formatter: function(params) {
return `
${params.name}
数值:${params.value}
`;
}
}如果项目中使用图标字体,也可以直接嵌入对应的 HTML 标签。
不过需要注意,Tooltip 中引用外部图片时,应确保资源路径正确,同时考虑图片加载失败、跨域以及页面性能等问题。
根据数据动态改变Tooltip内容
业务项目中经常存在这样的需求:普通数据展示基础信息,异常数据需要额外显示警告信息。
可以在 formatter 中判断:
tooltip: {
formatter: function(params) {
let result = `${params.name}
数值:${params.value}`;
if (Number(params.value) > 1000) {
result += '
数据超过预警阈值';
}
return result;
}
}如果数据结构更加复杂,可以将额外字段放进 series 的 data 中:
series: [
{
type: 'bar',
data: [
{
value: 120,
status: '正常'
},
{
value: 1500,
status: '预警'
}
]
}
]然后通过 formatter 获取:
tooltip: {
formatter: function(params) {
const data = params.data;
return `
${params.name}
数值:${params.value}
状态:${data.status}
`;
}
}这种方式能够让图表数据和业务状态保持关联,非常适合监控平台和运营分析系统。
使用renderMode控制Tooltip渲染方式
Tooltip 支持不同的渲染模式,可以通过 renderMode 进行设置:
tooltip: {
renderMode: 'html'
}常见场景下使用 HTML Tooltip,可以方便地实现复杂内容和 CSS 样式。
如果项目对渲染性能、兼容性或图表整体渲染方式有特殊要求,则需要结合具体 ECharts 版本和运行环境选择合适的渲染方式。
对于普通 Web 管理系统,HTML Tooltip 通常更方便进行深度定制。
Tooltip内容过长的处理方法
当 Tooltip 中需要展示大量信息时,如果不加限制,很容易造成弹窗过大,甚至遮挡主要图表。
可以通过 CSS 控制:
tooltip: {
extraCssText: `
max-width: 360px;
white-space: normal;
word-break: break-word;
`
}同时建议从内容层面控制信息密度,不要把数据库中的所有字段全部塞进 Tooltip。
比较合理的结构通常是:
时间
核心指标
同比变化
环比变化
业务状态对于更详细的信息,可以考虑点击图表后打开详情面板,而不是全部放在鼠标悬浮提示中。
Tooltip与数据格式化结合
如果后端返回的是原始数据,例如金额单位为分,可以在 Tooltip 中转换成元:
tooltip: {
formatter: function(params) {
const amount = Number(params.value) / 100;
return `
${params.name}
金额:${amount.toFixed(2)} 元
`;
}
}对于百分比数据:
tooltip: {
formatter: function(params) {
const value = Number(params.value);
return `
${params.name}
完成率:${value.toFixed(2)}%
`;
}
}如果多个地方都需要相同格式化逻辑,可以将格式化函数单独封装,避免在多个 Tooltip formatter 中重复编写代码。
一个完整的Tooltip高级配置示例
下面将触发方式、内容格式、样式和坐标轴指示器结合起来:
const option = {
tooltip: {
trigger: 'axis',
confine: true,
backgroundColor: 'rgba(30, 30, 30, 0.9)',
borderWidth: 0,
borderRadius: 6,
padding: [10, 14],
textStyle: {
color: '#fff',
fontSize: 13
},
axisPointer: {
type: 'cross',
label: {
show: true
}
},
formatter: function(params) {
let html = `${params[0].axisValue}`;
params.forEach(item => {
const value = Number(item.value);
html += `
${item.marker}
${item.seriesName}:
${value.toLocaleString()}
`;
});
return html;
}
},
xAxis: {
type: 'category',
data: ['一季度', '二季度', '三季度', '四季度']
},
yAxis: {
type: 'value'
},
series: [
{
name: '销售额',
type: 'line',
data: [120000, 180000, 165000, 230000]
},
{
name: '订单量',
type: 'line',
data: [1200, 1680, 1540, 2100]
}
]
};这个配置适合常见的经营数据分析场景。Tooltip 不再只是简单显示一个数值,而是成为图表和业务数据之间的交互入口。
Tooltip配置中的常见问题
formatter没有获取到正确的数据
首先检查 trigger 类型。如果使用 trigger: 'axis',formatter 的参数通常是数组;如果使用 trigger: 'item',则通常直接对应当前数据项。
因此不要把两种写法混用。
HTML没有按照预期显示
formatter 返回 HTML 时,应注意标签闭合以及特殊字符处理。例如:
return `
${params.name}
`;如果内容来自用户输入或不可信的外部数据,还需要进行适当的 HTML 转义,避免将未经处理的数据直接拼接到 HTML 中。
Tooltip遮挡图表
可以综合使用:
confine: true以及动态 position。
如果图表本身空间有限,还应该减少 Tooltip 内容,而不是单纯扩大弹窗。
多系列数据显示混乱
建议使用:
trigger: 'axis'然后遍历 params:
params.forEach(item => {
// 处理每个系列
});不要假设系列数量固定,更不要写死 params[0]、params[1] 等多个数据项。
数据单位重复
如果数据已经包含单位,例如后端返回 "100万元",formatter 又追加 "万元",最终就可能变成 "100万元万元"。
更合理的方式是让数据保持结构化,例如数值和单位分别管理:
{
value: 100,
unit: '万元'