Echarts面积图2.0(范围绘制)

代码:

// 以下代码可以直接粘贴在echarts官网的示例上
// 需求:范围随着原始折线图的颜色进行变化
// 原始图表的颜色绘制
let lineColor = ['#00a6ff', '#ff2e2e', '#00c228']
// 范围的颜色绘制
let areaColor = {
  '#00a6ff': 'rgba(0, 166, 255,0.05)',
  '#ff2e2e': 'rgba(255, 46, 46,0.09)',
  '#00c228': 'rgba(0, 194, 40,0.06)'
  // ...
}
// 范围区域 的数据
let normalValue = {
   '原始数据1': {
    type: '内部绘制',
    minValue: 200,
    maxValue: 700
  },
  '原始数据2': {
    // type: '内部绘制',
    type: '两边绘制',
    // type: '一条线',
    minValue: 200,
    maxValue: 700
  }
}
// 原始数据的图例名称
let legendName = ['原始数据1', '原始数据2']
// 获取当前折线图的y轴的最大值(用于两侧绘制) -- 在原本的绘图完成之后进行获取,然后进行重新配置和渲染
// getComponent参数:
// 参数一:轴名称 y轴 -- "yAxis"   x轴 -- "xAxis"
// 参数二:存在多个y轴时,求最值的对应轴的索引oneData
// _extent的索引:0代表求最小值,1代表求最大值 
// let yAxisMax = myChart.getModel().getComponent("yAxis",0).axis.scale._extent[1]
// let yAxisMaxData = Array.from({length: xData.length}, () => yAxisMax) 
let yAxisMaxData = [1330,1330,1330,1330,1330,1330,1330] // y轴最大的数值数组 -- 这个是假数据
let xData = ['Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'] // x轴数据

let legendSelect = {} // 图例是否显示
let legendData = [] // 图例的数据
if (legendName && legendName.length) {
  legendName.forEach((item,i) => {
  legendSelect[item] = item.indexOf('正常范围') === -1
  let obj = {
    name: item,
    itemStyle: {
      color: ''
    }
  }
  if(item.indexOf('正常范围') === -1) {
    obj.itemStyle.color = lineColor[i]
    legendData.push(obj)
  } 
  })
}

let seriseData = [{
  name: '原始数据1',
  data: [820, 932, 901, 934, 1290, 1330, 1320],
  type: 'line',
},
{
  name: '原始数据2',
  data: [80, 92, 91, 94, 190, 130, 120],
  type: 'line',
}]

let newLegend = JSON.parse(JSON.stringify(legendData))
for(let i in normalValue) {
	let item = normalValue[i]
	legendData.forEach(j => {
	  if (i === j.name) {
  		let legendObj = {
  		  name: `${i}正常范围`,
  		  itemStyle: {
  			  color: areaColor[j.itemStyle.color]
  		  }
  		}
  		newLegend.push(legendObj)
  	  legendSelect[`${i}正常范围`] = false
      let minData = Array.from({length: xData.length}, () => item.minValue) 
      let diffData = Array.from({length: xData.length}, () => Math.abs(item.maxValue - item.minValue)) 
      let maxData = Array.from({length: xData.length}, () => item.maxValue) 
  		if (item.type === '内部绘制') {
    		  seriseData.push({ // 最小值进行折线图的绘制
      			name: `${i}正常范围`,
      			data: minData,
      			type: 'line',
      			stack: `${i}内部绘制`,
      			symbol: 'none',
      			legendHoverLink: false,
      			triggerLineEvent: false,
      			emphasis: {
      			  disabled: true
      			},
      			lineStyle: {
        			color: j.itemStyle.color,
        			type: 'dashed'
      			}
    		  },{
    			name: `${i}正常范围`, // 最大值进行面积图的绘制
    			data: diffData,
    			type: 'line',
    			stack: `${i}内部绘制`,
    			triggerLineEvent: false,
    			legendHoverLink: false,
    			emphasis: {
    			  disabled: true
    			},
    			areaStyle: {
    			  color: areaColor[j.itemStyle.color]
    			},
    			symbol: 'none',
    			lineStyle: {
      			color: j.itemStyle.color,
      			type: 'dashed'
    			}
  		  })
  		} else if (item.type === '一条线') {
    		  seriseData.push({
      		  name: `${i}正常范围`,
      		  data: minData,
      		  type: 'line',
      		  symbol: 'none',
      		  legendHoverLink: false,
      		  triggerLineEvent: false,
      		  emphasis: {
      			  disabled: true
      		  },
      		  lineStyle: {
      			  color: areaColor[j.itemStyle.color]
      		  }
  		  })
  		} else if(item.type === '两边绘制') {
  		  seriseData.push({ // 最大值正常绘制折线图
    		  name: `${i}正常范围`,
    		  data: maxData,
    		  type: 'line',
    		  stack: `${i}两边绘制`,
    		  triggerLineEvent: false,
    		  legendHoverLink: false,
    		  emphasis: {
    			disabled: true
    		  },
    		  symbol: 'none',
    		  lineStyle: {
    			color: j.itemStyle.color,
    			type: 'dashed'
    		  }
  		  },
  		  { // y轴的最大值绘制面积图
    		  name: `${i}正常范围`,
    		  data: yAxisMaxData,
    		  type: 'line',
    		  stack: `${i}两边绘制`,
    		  triggerLineEvent: false,
    		  legendHoverLink: false,
    		  emphasis: {
    			disabled: true
    		  },
    		  areaStyle: {
    			color: areaColor[j.itemStyle.color]
    		  },
    		  symbol: 'none',
    		  lineStyle: {
    			color: j.itemStyle.color,
    			type: 'dashed'
    		  },
    		  itemStyle: {
    			borderColor: j.itemStyle.color
    		  }
  		  },
  		  { // 最小值正常绘制面积图
    		  name: `${i}正常范围`,
    		  data: minData,
    		  type: 'line',
    		  triggerLineEvent: false,
    		  legendHoverLink: false,
    		  emphasis: {
    			disabled: true
    		  },
    		  areaStyle: {
    			color: areaColor[j.itemStyle.color]
    		  },
    		  symbol: 'none',
    		  lineStyle: {
    			color: j.itemStyle.color,
    			type: 'dashed'
    		  },
    		  itemStyle: {
    			borderColor: j.itemStyle.color
    		  }
  		  })
  		}
  	}
	})
}

let colorArr = []
if(newLegend && newLegend.length) {
	newLegend.forEach(k => {
		colorArr.push(k.itemStyle.color)
	})
}
console.log('newLegend',newLegend)
option = {
  color: colorArr,
  xAxis: {
    type: 'category',
    boundaryGap: false,
    data: xData
  },
  tooltip: {
    show: true,
    trigger:  'axis',
    formatter: (params) => {
      let areaObj = {}
      let str = `<div><div>${params[0].name}</div>`
      params.forEach(item => {
        if(item.seriesName.indexOf('正常范围') === -1) {
          str += `<div>${item.marker}
            <span>${item.seriesName}:</span><span>${item.value}</span>
          </div>`
        } else {
          areaObj[item.seriesName] = true
        }
      })
      newLegend.forEach(item => {
        if(areaObj[item.name] && (item.name.indexOf('正常范围') != -1)) {
          let itemArr = item.name.split('正常范围')
          let obj = normalValue[itemArr[0]]
          if(obj.type ==='一条线') {
            str += `<div>
              <span style="display:inline-block;margin-right:5px;border-radius:10px;width:10px;height:10px;background-color:${item.itemStyle.color};"></span>
              <span>${item.name}:</span><span>${obj.minValue}</span>
            </div>`
            str += `</div>`
          }
          if(obj.type ==='两边绘制') {
            str += `<div>
              <span style="display:inline-block;margin-right:5px;border-radius:10px;width:10px;height:10px;background-color:${item.itemStyle.color};"></span>
              <span>${item.name}:</span>
              <span>-∞ ~ ${obj.minValue}  ${obj.maxValue} ~ +∞</span>
            </div>`
            str += `</div>`
          }
          if(obj.type ==='内部绘制') {
            str += `<div>
              <span style="display:inline-block;margin-right:5px;border-radius:10px;width:10px;height:10px;background-color:${item.itemStyle.color};"></span>
              <span>${item.name}:</span><span>${obj.minValue}~${obj.maxValue}</span>
            </div>`
            str += `</div>`
          }
        }
      })
      return str
    }
  },
  legend: {
    data: newLegend,
    selected: legendSelect
  },
  yAxis: {
    type: 'value',
    max: 'dataMax'
  },
  series: seriseData
};

效果:

① 内部绘制:
在这里插入图片描述

② 两边绘制:
在这里插入图片描述

③ 一条线:

在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值