ECharts 实现同一个X轴多个Y轴分区展示不同值域数据

需求是展示11个指标数据的折线图,也就是11条折线,但是其实这是3组数据,值域的分布差别有点大,一组数据值域是0到0.1,一组数据的值域达到了10万,如果强行在同一个坐标系,导致数据趋势不能在图表上展示,于是,就有了显示的要求,要求三组数据分组显示,但是要在同一个X轴,也就是Y轴分组。我选择了EChart来实现。
最终实现的思路是 xAxis、yAxis和grid生成三组,xAxis和yAxis引用gridIndex,其中X轴的数据是相同的,grid设置到不同的区域,纵向排布,series设置时把相应的yAxisIndex、xAxisIndex分别设置到对应的区域,还有一个关键的交互,要求在鼠标移动时三个坐标系要同步显示标线并且tooltip展示所有的数据,代码如下

 // 过滤掉 fma he sma 为 0 的数据
    data = data.filter((item: any) => item['fma'] !== 0 && item['sma'] !== 0)

    // 获取日期数组
    const dates = data.map((item: any) => dayjs(item.timestamp).utc().format('MM-DD HH:mm:ss'));

    // 获取三组数据
    const group1 = ['market_price_ask', 'market_price_bid', 'market_price_mid', 'sma', 'fma'];
    const group2 = ['most_of_vol', 'realtime_vol'];
    const group3 = ['rs', 'rsa', 'rsd', 'rsm'];

    const series = [
      ...group1.map(symbol => ({
        name: symbol,
        type: 'line',
        showSymbol: false,
        color: getColor(symbol),
        data: data.map((item: any) => item[symbol]),
        yAxisIndex: 0,
        xAxisIndex: 0,
        lineStyle: {
          width: 1
        },
      })),
      ...group2.map(symbol => ({
        name: symbol,
        type: 'line',
        showSymbol: false,
        color: getColor(symbol),
        data: data.map((item: any) => item[symbol]),
        yAxisIndex: 1,
        xAxisIndex: 1,
        lineStyle: {
          width: 1
        },
      })),
      ...group3.map(symbol => ({
        name: symbol,
        type: 'line',
        showSymbol: false,
        color: getColor(symbol),
        data: data.map((item: any) => item[symbol]),
        yAxisIndex: 2,
        xAxisIndex: 2,
        lineStyle: {
          width: 1
        },
      })),
    ];

    if (data.length > 0) {
      chartRef.current?.setOption({
        title: {
          text: 'Price Analysis',
        },
        // 核心配置:强制所有坐标系联动
        axisPointer: {
          type: 'line', // 显示纵向指示线
          link: [{ xAxisIndex: [0, 1, 2] }], // 联动所有 x 轴
          label: { show: false } // 隐藏默认标签
        },
        tooltip: {
          trigger: 'axis',
          // 自定义 Tooltip 内容
          formatter: (params: any) => {
            const date = params[0].axisValue; // 获取当前时间点
            const allValues = data.find((d: any) => dayjs(d.timestamp).utc().format('MM-DD HH:mm:ss') === date); // 找到完整数据

            // 按分组组织内容
            return `
              
${date}
Market Data:
${['market_price_ask', 'market_price_bid', 'market_price_mid', 'sma', 'fma'] .map(symbol => `
${symbol}: ${allValues[symbol].toFixed(4)}
`).join('')}
Volatility:
${['most_of_vol', 'realtime_vol'] .map(symbol => `
${symbol}: ${allValues[symbol].toFixed(4)}
`).join('')}
PDS:
${['rs', 'rsa', 'rsd', 'rsm'] .map(symbol => `
${symbol}: ${allValues[symbol].toFixed(4)}
`).join('')}
`; } }, grid: [ { // 第一组坐标系 top: '5%', height: '30%', left: '10%', right: '10%' }, { // 第二组坐标系 top: '40%', height: '25%', left: '10%', right: '10%' }, { // 第三组坐标系 top: '70%', height: '20%', left: '10%', right: '10%' } ], legend: { data: [...group1, ...group2, ...group3], }, xAxis: [ { // 主 X 轴(共享) type: 'category', data: dates, gridIndex: 0, // 关联第一个 grid show: false, }, { // 隐藏的副 X 轴(用于对齐) type: 'category', gridIndex: 1, show: false, data: dates, axisPointer: { show: true } }, { // 隐藏的副 X 轴(用于对齐) type: 'category', gridIndex: 2, axisLabel: { show: true }, data: dates, axisPointer: { show: true } } ], yAxis: [ { type: 'value', name: 'Market Data', position: 'left', scale: true, gridIndex: 0, }, { type: 'value', name: 'Volatility', position: 'left', scale: true, gridIndex: 1, }, { type: 'value', name: 'PDS', position: 'left', scale: true, gridIndex: 2, } ], series: series, }, true) }

你可能感兴趣的:(ECharts 实现同一个X轴多个Y轴分区展示不同值域数据)