<template>
|
<div class="e-chart-root" @dblclick="fullScreen" :class="{'full-screen': fullScreenState}">
|
<div class="e-chart-container">
|
<div class="e-chart" :id="id" :ref="id"></div>
|
</div>
|
<slot></slot>
|
</div>
|
</template>
|
|
<script>
|
// 引入 ECharts 主模块
|
import ECharts from "echarts/lib/echarts";
|
//引入折线图
|
import "echarts/lib/chart/line";
|
//引入提示框
|
import "echarts/lib/component/tooltip";
|
//引入标题
|
import "echarts/lib/component/title";
|
//引入图例标志
|
import "echarts/lib/component/legend";
|
//区域缩放
|
import "echarts/lib/component/dataZoom";
|
|
//markeline
|
import "echarts/lib/component/markLine"
|
|
// 引入自定义主题
|
import "./theme/transparent"
|
//监听div变化改变chart图大小
|
//import EleResize from "./theme/EleResize.js";
|
|
export default {
|
props: {
|
id: {
|
type: String,
|
required: true,
|
},
|
unit: {
|
type: String,
|
default: '',
|
},
|
noFull: {
|
type: Boolean,
|
default: false
|
},
|
startZero: {
|
type: Boolean,
|
default: false
|
},
|
},
|
data() {
|
return {
|
fullScreenState: false,
|
}
|
},
|
methods: {
|
getOption(opt) {
|
let unit = this.unit;
|
// 整体配置项
|
let option = {
|
animation: false,
|
color: this.getColor(opt),
|
title: this.getTitle(opt),
|
tooltip: this.getTooltip(opt),
|
grid: this.getGrid(opt),
|
legend: this.getLegend(opt),
|
toolbox: {
|
show: true,
|
feature: {
|
dataZoom: {
|
yAxisIndex: 'none'
|
},
|
restore: {},
|
}
|
},
|
dataZoom: [{
|
type: 'inside',
|
start: 0,
|
end: 100
|
}],
|
xAxis: this.getXAxis(opt),
|
yAxis: this.getYAxis(opt),
|
series: this.getSeries(opt),
|
};
|
return option;
|
},
|
setOption(opt) {
|
let option = this.getOption(opt);
|
// 清理画布
|
this.$G.chartManage.get(this.id).clear();
|
// 设置配置项
|
this.$G.chartManage.get(this.id).setOption(option);
|
},
|
getGrid(opt) { // 配置边距
|
// 未配置自定义颜色
|
if (!opt || !opt.grid) {
|
return {
|
left: '1%',
|
right: '5%',
|
bottom: '2%',
|
containLabel: true
|
}
|
}
|
// 返回
|
return opt.grid;
|
},
|
getColor(opt) { // 配置自定义颜色
|
// 未配置自定义颜色
|
if (!opt || !opt.color) {
|
return []
|
}
|
|
// 返回颜色
|
return opt.color;
|
},
|
getTitle(opt) { // 配置标题
|
// 未配置标题
|
if (!opt || !opt.title) {
|
return {
|
show: false,
|
};
|
}
|
|
// 返回标题
|
return opt.title;
|
},
|
getTooltip(opt) { // 配置标题
|
let unit = this.unit;
|
// 未配置标题
|
if (!opt || !opt.tooltip) {
|
return {
|
trigger: 'axis',
|
axisPointer: { // 坐标轴指示器,坐标轴触发有效
|
type: 'line' // 默认为直线,可选为:'line' | 'shadow'
|
},
|
appendToBody: true,
|
formatter(params) {
|
let res = params[0].name + '<br/>';
|
params.forEach(item => {
|
res += item.marker;
|
res += item.seriesName;
|
res += ' : ' + item.data[1] + unit + '</br>';
|
});
|
return res;
|
}
|
};
|
}
|
|
// 返回标题
|
return opt.tooltip;
|
},
|
getLegend(opt) {
|
// 未配置legend
|
if (!opt || !opt.legend) {
|
return {
|
show: false,
|
}
|
}
|
|
return opt.legend;
|
},
|
getXAxis(opt) {
|
// 未配置x轴
|
if (!opt || !opt.xAxis) {
|
return [{
|
type: 'category',
|
boundaryGap: 0,
|
axisLine: {
|
onZero: false
|
}
|
}]
|
}
|
|
return opt.xAxis;
|
},
|
getYAxis(opt) {
|
let startZero = this.startZero;
|
// 未配置x轴
|
if (!opt || !opt.yAxis) {
|
return [{
|
type: 'value',
|
splitLine: {
|
show: true,
|
},
|
min: function (data) {
|
let min = data.min;
|
if (min == Infinity) {
|
return 0;
|
}
|
// 重0开始
|
if (startZero && (data.min > 0 && data.max > 0)) {
|
return 0;
|
}
|
if (min > 0) {
|
return Math.floor(min * 0.9);
|
} else {
|
return Math.floor(min * 1.01);
|
}
|
|
},
|
max: function (data) {
|
let max = data.max;
|
if (max == -Infinity) {
|
return 1;
|
}
|
// 重0开始
|
if (startZero && (data.min < 0 && data.max < 0)) {
|
return 0;
|
}
|
return Math.ceil(max * 1.01);
|
}
|
}];
|
}
|
return opt.yAxis;
|
},
|
getSeries(opt) { // 设置series
|
// 未配置series
|
if (!opt || !opt.series) {
|
return [];
|
}
|
// 设置配置项
|
let series = opt.series.map(item => {
|
// 设置类型
|
item.type = "line";
|
// 设置平滑的线条,关闭圆圈,设置采样点
|
item.smooth = item.smooth == undefined ? true : item.smooth;
|
item.symbolSize = item.symbolSize == undefined ? 0 : item.symbolSize;
|
item.sampling = 'average';
|
return item;
|
});
|
// 返回
|
return series;
|
},
|
getMax(list) {
|
let arr = list.map(item => {
|
return item[1];
|
});
|
return Math.max.apply(null, arr);
|
},
|
getMin(list) {
|
let arr = list.map(item => {
|
return item[1];
|
});
|
return Math.min.apply(null, arr);
|
},
|
fullScreen() {
|
// 判断是否可以全屏
|
if (this.noFull) {
|
return;
|
}
|
this.fullScreenState = this.fullScreenState ? false : true;
|
this.$nextTick(() => {
|
// 重置大小
|
this.$G.chartManage.get(this.id).resize();
|
});
|
},
|
resize() {
|
// 重置大小
|
this.$G.chartManage.get(this.id).resize();
|
},
|
},
|
mounted() {
|
// 基于准备好的dom,初始化echarts实例
|
let chart = ECharts.init(this.$refs[this.id], 'transparent');
|
// 将图表添加到图表管理
|
this.$G.chartManage.set(this.id, chart);
|
// 设置配置项
|
this.setOption();
|
|
let resizeDiv = document.getElementById(this.id)
|
//监听拖拽和改变大小时echart自适应
|
let listener = () => {
|
chart.resize()
|
}
|
//EleResize.on(resizeDiv, listener)
|
|
// // 容器大小发生变化
|
// this.$refs.resizeBox.contentDocument.defaultView.addEventListener('resize', () => {
|
// chart.resize();
|
// });
|
}
|
}
|
</script>
|
|
<style scoped>
|
.e-chart-root,
|
.e-chart-container,
|
.e-chart {
|
height: 100%;
|
box-sizing: border-box;
|
}
|
|
.e-chart-root.full-screen .e-chart-container {
|
position: fixed;
|
top: 0;
|
left: 0;
|
right: 0;
|
bottom: 0;
|
background-size: 100% 100%;
|
z-index: 9999;
|
}
|
|
.resize-box {
|
display: block;
|
position: absolute;
|
top: 0px;
|
left: 0px;
|
width: 100%;
|
height: 100%;
|
border: none;
|
padding: 0px;
|
margin: 0px;
|
opacity: 0;
|
z-index: -1000;
|
pointer-events: none
|
}
|
</style>
|