遇到的一些比较新的Echarts图表

383 阅读2分钟

前言

遇到了两个之前没写过的echarts图形,图形比较接近(来自产品的连续改需求),想着起一个系列,把以后遇到的比较新的echarts图形补充进来。

图一、堆叠柱形图+鼠标移入获取信息

还需要移动每个堆叠的块,显示该小块的信息,而不是整块的信息。

1.首先实现一个堆叠柱形图

主要根据series里的stack属性,见如下代码

const chart = this.$refs.chart//获取元素
const myChart = this.$echarts.init(chart)
const BarMap = {
  1: '设备故障',
  2: '校调维护',
  3: '停电',
  4: '无人放假',
  6: '待料',
}
const xData = [
  'T6',
  'T7',
  'B4',
  'T8',
  'L1',
  'L2',
  'T5',
  'B3',
  'T9',
  'L3',
  'T4',
  'M3',
]
const series = [
  {
    type: 'bar',
    stack: '总量', //stack一样的会堆叠在一起
    data: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
  },
  {
    name: '设备故障',
    type: 'bar',
    stack: '总量',//stack一样的会堆叠在一起
    data: [0.02, 2, 72, 0, 2.03, 0, 0, 47.98, 0, 0, 0, 48.02],
  },
  {
    name: '校调维护',
    type: 'bar',
    stack: '总量',
    data: [0, 0, 74.04, 0, 2.02, 0, 0, 0, 0, 0, 0, 0],
  },
  {
    name: '停电',
    type: 'bar',
    stack: '总量',
    data: [119.95, 0, 0, 288, 0, 0, 0, 0, 0.95, 0, 0, 263.99],
  },
  {
    name: '无人放假',
    type: 'bar',
    stack: '总量',
    data: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 72.02],
  },
  {
    type: 'bar',
    stack: '总量',
    data: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
  },
  {
    name: '待料',
    type: 'bar',
    stack: '总量',
    data: [72, 0, 0, 0, 0, 0, 143, 0, 0, 0, 0, 0],
  },
  {
    type: 'bar',
    stack: '总量',
    data: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
  },
  {
    type: 'bar',
    stack: '总量',
    data: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
  },
  {
    type: 'bar',
    stack: '总量',
    data: [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
  },
]
const option = {
  legend: {
    data: Object.values(BarMap),
    width: 0,
    right: -5,
  },
  yAxis: {
    type: 'value',
  },
  xAxis: [
    {
      data: xData,
      axisLine: { onZero: true },
      splitLine: { show: false },
      splitArea: { show: false },
      axisTick: {
        length: 20,
      },
    },
  ],
  series,
}
myChart.setOption(option)

堆叠柱形图如图下:
$0RXA8Z6M7@Q09P`C%V{~O6.png

2.获取鼠标移入的某个分块的信息

现在还差个鼠标移入的提示信息,我们知道是去配置tooltip,分析下需求,他需要显示鼠标移入的某个分块的信息,我们需要知道他现在在哪个位置。tooltip里的axisPointer可以获取在坐标轴里的信息,我们打印看下。

1662644555842-8305f3c1-70b0-43af-a4c6-dc1ab645d9df.png
可以看到鼠标移入后的打印信息,会返回在当前图表里的x,y,而y值正是我们需要的,在当前列的什么高度信息。

tooltip: {
  axisPointer: {
    type: 'cross',
    lineStyle: {
      color: '#ffffff00',
    },
    label: {
      formatter: function (params) {
        if (params.axisDimension === 'y') {
          window.mouseCurValue = params.value//在当前列的什么高度信息。
        }
      },
      show: false,
    },
  },
  formatter: function (params) {
    let res = '',
      sum = 0
    for (let i = 0; i < params.length; i++) {
      let series = params[i]
      sum += Number(series.data)
      if (sum >= window.mouseCurValue) {
        res = `系列"${series.seriesName}"点"${series.axisValue}"<br>值:${series.data}`

        break
      }
    }
    return res
  },
  trigger: 'axis',
}

而高度正是由当前列的value从下往上累计而成的,所以我们逐一叠在,如果和超过当前鼠标的值,则表示,处在这一列的第几快信息里了。效果如下图。

F@$_PX1W0RCZ07JCBIP}U5.png](https://cdn.nlark.com/yuque/0/2022/png/2968124/1662644082802-049d5c2d-390c-4d33-94bf-9147181bf1b7.png#clientId=uef5e2c69-70e1-4&crop=0&crop=0&crop=1&crop=1&from=drop&id=uac70ba26&margin=%5Bobject%20Object%5D&name=F%40%24_PX1W0RCZ0%607JCBIP%7DU5.png&originHeight=405&originWidth=932&originalType=binary&ratio=1&rotation=0&showTitle=false&size=18333&status=done&style=none&taskId=u4cc35052-1762-4ab7-85e6-4984ff7340a&title=)![W2[L[7%HVT2L{X9H3)3IHG.png

图二、双Y轴+堆叠柱形图+折线图+鼠标移入获取信息

惨无人道,但好在有第一个图的基础,入手就比较快了。

1.部分堆叠柱形图部分折线图

series里区分type即可

const series = [
  {
    name: '设备故障',
    type: 'line',//折线图
    data: [
      0, 0.0153, 0.0173, 0.0303, 0.0153, 0, 0, 0, 0.0153, 0.0103, 0,
      0.0353,
    ],
  },
  {
    name: '校调维护',
    type: 'bar',//柱状图
    stack: '总量',//堆叠
    data: [0, 0.0023, 0, 0, 0.0153, 0, 0, 0, 0.0078, 0, 0, 0.0023],
  },
  {
    name: '停电',
    type: 'bar',
    stack: '总量',
    data: [0, 0.1293, 0, 0, 0.0091, 0, 0, 0.0064, 0.0023, 0, 0, 0.1293],
  },
  {
    name: '无人放假',
    type: 'bar',
    stack: '总量',
    data: [0, 0.0091, 0, 0, 0, 0, 0, 0, 0.0091, 0, 0, 0.0091],
  },
  {
    name: '其他',
    type: 'bar',
    yAxisIndex: 0,
    stack: '总量',
    data: [0, 0.0153, 0, 0, 0.1293, 0, 0, 0, 0.0153, 0, 0, 0.053],
  },
  {
    name: '待料',
    type: 'bar',
    yAxisIndex: 0,
    stack: '总量',
    data: [0, 0.0078, 0, 0, 0.0078, 0, 0, 0.0353, 0.1293, 0, 0, 0.0178],
  },
]

可以得到如下图_V6YIP58%DOTQMKJ0X4I~RT.png

2.双Y轴

其中折线图使用右边的y轴,柱状图使用左边的

yAxis: [//传入两个y轴,标明位置
  {
    position: 'left',
    type: 'value',
    axisLine: {
      show: true,
    },
    axisTick: {
      show: true,
    },
    splitLine: {
      show: false,
    },
  },
  {
    position: 'right',
    type: 'value',
    axisTick: {
      show: true,
    },
    axisLine: {
      show: true,
    },
    splitLine: {
      show: false,
    },
  },
]

//利用yAxisIndex来区分是使用左边的Y轴还是右边的Y轴
const series = [
  {
    name: '设备故障',
    type: 'line',
    yAxisIndex: 1,
    data: [
      0, 0.0153, 0.0173, 0.0303, 0.0153, 0, 0, 0, 0.0153, 0.0103, 0,
      0.0353,
    ],
  },
  {
    name: '校调维护',
    type: 'bar',
    yAxisIndex: 0,
    stack: '总量',
    data: [0, 0.0023, 0, 0, 0.0153, 0, 0, 0, 0.0078, 0, 0, 0.0023],
  },
  {
    name: '停电',
    type: 'bar',
    yAxisIndex: 0,
    stack: '总量',
    data: [0, 0.1293, 0, 0, 0.0091, 0, 0, 0.0064, 0.0023, 0, 0, 0.1293],
  },
  {
    name: '无人放假',
    type: 'bar',
    yAxisIndex: 0,
    stack: '总量',
    data: [0, 0.0091, 0, 0, 0, 0, 0, 0, 0.0091, 0, 0, 0.0091],
  },
  {
    name: '其他',
    type: 'bar',
    yAxisIndex: 0,
    stack: '总量',
    data: [0, 0.0153, 0, 0, 0.1293, 0, 0, 0, 0.0153, 0, 0, 0.053],
  },
  {
    name: '待料',
    type: 'bar',
    yAxisIndex: 0,
    stack: '总量',
    data: [0, 0.0078, 0, 0, 0.0078, 0, 0, 0.0353, 0.1293, 0, 0, 0.0178],
  },
]

如图所示

QQ图片20220909103641.png

3.鼠标移入显示对应内容

跟图一类似,但是多了个折线图,且有双y轴。先打印下参数研究下
2N%ZRI}OG(J4EJI2LIX(`%D.png
因为双Y轴,所以返回了两个Y轴信息
接下来就是记录鼠标所在Y轴信息

tooltip: {
  axisPointer: {
    type: 'cross',
    lineStyle: {
      color: '#ffffff00',
    },
    label: {
      formatter: function (params) {
        if (params.axisDimension == 'y' && params.axisIndex == 0) {
          window.mouseCurValue = params.value//存储左边Y轴的信息
        } else if (
          params.axisDimension == 'y' &&params.axisIndex == 1
        ) {
          window.mouseCurValue2 = params.value //存储右边Y轴的信息
        }
      },
      show: false,
    },
  },
  trigger: 'axis',
}

先处理鼠标移入堆叠柱状图的提示,跟图一差不多,但要注意,图一是整列从下往上累加比较,因为图一全是堆叠数据,而当前这个多了个折线图,所以累计堆叠柱状图高度时需要去掉折线图数据。
然后折线图需要注意,折线图是移到线上这个点才会提示,不像柱形图,只要在这个块区间就会显示,所以应该是这个数据完全等于window.mouseCurValue2时才会显示,根据数据做一些处理,增大些范围。
完整代码如下:(xData,series等不再罗列)

const option = {
  tooltip: {
    axisPointer: {
      type: 'cross',
      lineStyle: {
        color: '#ffffff00',
      },
      label: {
        formatter: function (params) {
          if (params.axisDimension == 'y' && params.axisIndex == 0) {
            window.mouseCurValue = params.value
          } else if (
            params.axisDimension == 'y' &&
            params.axisIndex == 1
          ) {
            window.mouseCurValue2 = params.value
          }
        },
        show: false,
      },
    },
    formatter: function (params) {
      let res = '',
        sum = 0
      for (let i = 0; i < params.length; i++) {
        let series = params[i]
        if (BarMap[i] !== '设备故障') {//不是折线图数据才累加
          sum += Number(series.data)
        } else {//是折线图,需要判断数据和鼠标所在y轴的值是否接近
          if (//折线图上下增加了0.0002触发范围
            window.mouseCurValue2 <= series.data + 0.0002 &&
            window.mouseCurValue2 >= series.data - 0.0002
          ) {
            res = `系列"${series.seriesName}"点"${series.axisValue}"<br>值:${series.data}`
            break
          }
        }
        if (!res && sum >= window.mouseCurValue) {
          res = `系列"${series.seriesName}"点"${series.axisValue}"<br>值:${series.data}`
          break
        }
      }
      return res
    },
    trigger: 'axis'
  },
  legend: {
    data: Object.values(BarMap),
    right: 'center',
    bottom: 0
  },
  yAxis: [
    {
      position: 'left',
      type: 'value',
      axisLine: {
        show: true
      },
      axisTick: {
        show: true
      },
      splitLine: {
        show: false
      },
    },
    {
      position: 'right',
      type: 'value',
      axisTick: {
        show: true
      },
      axisLine: {
        show: true
      },
      splitLine: {
        show: false
      }
    }
  ],
  xAxis: [
    {
      data: xData,
      axisLine: { onZero: true },
      splitLine: { show: false },
      splitArea: { show: false },
      axisTick: {
        length: 20
      }
    }
  ],
  series
}

效果图如下所示

QQ图片20220909103544.png

1662690781638-c0c78574-f980-4dfb-8fba-b918f2d4bd11.png