重要文件版本
在 Vue 项目中使用 ECharts 只需要在 Vue 组件的
mounted
生命周期中 初始化 ECharts,然后在每次配置项有变更时调用setOption()
方法更新配置即可项目模板源码
封装图表组件<template>
<div class="default-chart" :style="{width, height}">div>
template>
<script>
import * as echarts from 'echarts/lib/echarts';
import 'zrender/lib/svg/svg';
// 引入提示框和标题组件
import throttle from '../../utils/throttle';
export default {
name: 'basic-echarts',
props: { // 规范传入参数格式,以及默认值
renderer: {
type: String,
required: false
},
option: {
type: Object,
default: () => ({})
},
notMerge: {
type: Boolean,
default: false
},
lazyUpdate: {
type: Boolean,
default: false
}
},
data() {
return {
chart: null,
width: '100%',
height: '100%'
};
},
methods: {
// 初始化图表
initChart(el) {
// renderer 用于配置渲染方式 可以是 svg 或者 canvas
const renderer = this.renderer || 'canvas';
console.log(renderer);
this.chart = echarts.init(el, null, {
renderer,
width: 'auto',
height: 'auto'
});
},
// 设置配置项
setOption(option) {
if (!this.chart) {
return;
}
const notMerge = this.notMerge;
const lazyUpdate = this.lazyUpdate;
this.chart.setOption(option, notMerge, lazyUpdate);
},
// 销毁
dispose() {
if (!this.chart) {
return;
}
this.chart.dispose();
this.chart = null;
},
// 重新渲染
resize() {
this.chart && this.chart.resize();
},
getInstance() {
return this.chart;
}
},
mounted() {
this.$nextTick(function() {
console.log('did mount');
this.initChart(this.$el);
this.setOption(this.option);
window.addEventListener('resize', throttle(this.resize, 100));
});
},
beforeDestroy() {
this.dispose();
},
watch: {
// 监视传入的 option 参数,如果有变化则重新设置配置项
option(newOpt) {
console.log('update config');
this.setOption(newOpt);
}
}
};
script>
<style lang="scss" scoped>
@import '../../scss/_common.scss';
style>
<template>
<Chart :renderer="renderer" :option="option"/>
template>
<script>
import { mapActions, mapState } from 'vuex';
// 引入当前图表配置需要用到的图表、组件
import 'echarts/lib/component/tooltip';
import 'echarts/lib/component/title';
import 'echarts/lib/component/grid';
import 'echarts/lib/component/legend';
import 'echarts/lib/chart/radar';
import 'echarts/map/js/china';
import Chart from '../components/Charts/index';
const colors = [
'#bcd3bb',
'#e88f70',
'#edc1a5',
'#9dc5c8',
'#e1e8c8',
'#7b7c68',
'#e5b5b5',
'#f0b489',
'#928ea8',
'#bda29a'
];
export default {
name: 'echarts-radar',
data() {
return { renderer: 'canvas' };
},
computed: {
...mapState('charts', { currentData: 'radar' }),
provinces() {
const currentData = this.currentData || [];
return currentData.map(data => data.province);
},
// option 合并传入的数据,返回一个 echarts 的 配置项
option() {
return {
backgroundColor: '#161627',
title: {
text: 'AQI - 雷达图',
left: 'center',
textStyle: {
color: '#eee'
}
},
legend: {
bottom: 5,
data: this.provinces,
itemGap: 20,
textStyle: {
color: '#fff',
fontSize: 14
},
selectedMode: 'single'
},
radar: {
indicator: [
// 雷达图指示器
{ name: 'AQI', max: 200 },
{ name: 'PM2.5', max: 250 },
{ name: 'PM10', max: 250 },
{ name: 'CO', max: 5 },
{ name: 'NO2', max: 150 },
{ name: 'SO2', max: 120 }
],
shape: 'circle', // 形状
splitNumber: 5, // 分割段数
splitLine: {
// 分隔线
lineStyle: {
color: [
'rgba(238, 197, 102, 0.1)',
'rgba(238, 197, 102, 0.2)',
'rgba(238, 197, 102, 0.4)',
'rgba(238, 197, 102, 0.6)',
'rgba(238, 197, 102, 0.8)',
'rgba(238, 197, 102, 1)'
].reverse()
}
},
splitArea: {
// 分割区域
show: false
},
axisLine: {
// 坐标轴轴线
lineStyle: {
color: 'rgba(238, 197, 102, 0.5)'
}
}
},
series: this.provinces.map((province, idx) => {
return {
name: province,
type: 'radar',
lineStyle: {
width: 1,
opacity: 0.5
},
data: this.currentData[idx].data,
symbol: 'none',
itemStyle: {
color: colors[idx % colors.length]
},
areaStyle: {
opacity: 0.05
}
};
})
};
}
},
methods: {
...mapActions('charts', ['changeData'])
},
// 组件装载前请求数据
async beforeMount() {
const path = '/radar';
const key = 'radar';
await this.changeData({ path, key });
},
components: { Chart }
};
script>
<style lang="scss" scoped>
@import '../scss/_common.scss';
style>