本文主要是介绍echarts最新封装柱状图,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
- 父元素传入一次最多显示几个以及每次切换几个
- 超出没两秒向右切换一个
- 图表加载有动画效果
- 动态更新数据实时显示
- 屏幕尺寸改变自动适应
- 字体大小自适应
组件 BarChart.vue
<template><div class="w100 h100"><divref="chart"class="w100 h100"@mouseenter="stopTimer"@mouseleave="startTimer"></div></div>
</template><script>
import resize from "./mixins/resize";
let color = ["#FFF200", "#ff6200"];
let color1 = ["rgba(255, 225, 128,.6)", "rgba(245, 116, 116,.6)"];
export default {name: "BarChart",mixins: [resize],props: {/*** chartData 属性定义* 类型:Array* 是否必填:是* 描述:用于接收图表数据,是渲染图表的基础*/chartData: {type: Array,required: true,},/*** maxVisibleBars 属性定义* 类型:Number* 默认值:6* 描述:定义图表中最大可见的条形数量,用于限制图表的显示范围,以避免过多数据导致的视觉混乱*/maxVisibleBars: {type: Number,default: 6,},/*** barsPerStep 属性定义* 类型:Number* 默认值:1* 描述:定义每次滚动或更新时,图表显示的条形数量变化,用于控制图表更新的平滑度*/barsPerStep: {type: Number,default: 1,},},data() {return {chart: null,currentIndex: 0,timer: null,};},mounted() {this.initChart();this.startTimer();},beforeDestroy() {if (this.timer) {clearInterval(this.timer);}if (this.chart) {this.chart.dispose();}},watch: {chartData: {handler: "updateChart",deep: true,},},methods: {initChart() {this.chart = this.$echarts.init(this.$refs.chart);this.updateChart();},updateChart() {const visibleData = this.chartData.slice(this.currentIndex,this.currentIndex + this.maxVisibleBars);const option = {color: ["#FFF200", "#ff6200"], //柱状图颜色// backgroundColor: "#000", //背景色animation: true, //开启动画(页面一进来柱状图升起动画)animationDuration: 1000, //动画时长animationEasing: "cubicInOut", //动画缓动效果animationDurationUpdate: 500, //更新数据动画时长animationEasingUpdate: "cubicInOut", //更新动画缓动效果title: {//标题text: "动态柱图",textStyle: {color: "#fff",fontSize: this.fontSize(0.2),},left: "center",top: "2%",},tooltip: {//提示框组件show: true,trigger: "item", //提示框触发的条件,默认为鼠标悬浮formatter: "{b}{a}: {c}", //提示框内容格式 a 为系列名称,b 为数据项名称,c 为数据项值,d 为百分比,e 为数据项所在系列索引值backgroundColor: "#f9f9f9",borderColor: "#ccc",borderWidth: 1,padding: [5, 10],textStyle: {color: "#333",fontSize: 14,},},grid: {top: "20%",left: "6%",right: "1%",bottom: "4%",containLabel: true,},legend: {itemHeight: this.fontSize(0.12), //图例图标的高度itemWidth: this.fontSize(0.2), //图例图标的宽度itemGap: this.fontSize(0.23), //图例图标与文字间的间距textStyle: {color: "#fff",borderColor: "#fff",fontSize: this.fontSize(0.14),},top: 7,right: 20,},xAxis: {type: "category",data: visibleData.map((item) => item.name),boundaryGap: true,//坐标轴axisLine: {lineStyle: {color: "#2384B1", //横轴颜色width: this.fontSize(0.01), //横轴粗细},},axisLabel: {interval: 0, // 显示所有标签rotate: 30, // 倾斜标签以节省空间textStyle: {color: "#fff", // 横坐标颜色fontSize: this.fontSize(0.13),},},axisTick: {show: false, //不显示坐标轴刻度},},yAxis: {type: "value",min: 0,minInterval: 1,// 网格线splitLine: {show: true,lineStyle: {color: "#023052",type: "dotted",},},axisLine: {lineStyle: {color: "#2384B1", //横轴颜色width: this.fontSize(0.01), //横轴粗细},},//坐标值标注axisLabel: {textStyle: {color: "#fff",fontSize: this.fontSize(0.13),},},},series: [{name: "数量", // 图例名称data: visibleData.map((item) => item.value),type: "bar",barWidth: this.fontSize(0.2), // 柱状图宽度barMinHeight: 2, // 设置柱状图的最小高度(默认为0时显示一点)// 柱状图颜色渐变itemStyle: {normal: {show: true,color: new this.$echarts.graphic.LinearGradient(0, 0, 0, 1, [{offset: 0,color: color[0],},{offset: 1,color: color1[0],},]),barBorderRadius: [4, 4, 0, 0], // 设置柱形四个角的圆角半径,顺序为左上、右上、右下、左下shadowColor: color1[0],shadowBlur: 24,},},// 柱上面的数值label: {normal: {show: true,position: "top", //在上方显示textStyle: {color: "#fff",fontSize: this.fontSize(0.13),},},},},],};this.chart.setOption(option);},startTimer() {this.timer = setInterval(() => {this.currentIndex += this.barsPerStep;if (this.currentIndex + this.maxVisibleBars > this.chartData.length) {this.currentIndex = 0;}this.updateChart();}, 2000);},stopTimer() {clearInterval(this.timer);},},
};
</script><style scoped>
</style>
父组件
<template><div id="app" style="background: #000"><BarChart style="width: 500px; height: 400px" :chartData="data" /><button @click="updateData">更新数据</button></div>
</template><script>
import BarChart from "./components/BarChart.vue";
export default {components: {BarChart,},data() {return {data: [{ name: "项目1", value: 20 },{ name: "项目2", value: 30 },{ name: "项目3", value: 10 },{ name: "项目4", value: 40 },{ name: "项目5", value: 0 },{ name: "项目6", value: 0.5 },{ name: "项目7", value: 1 },{ name: "项目8", value: 45 },{ name: "项目9", value: 30 },{ name: "项目10", value: 20 },],};},methods: {updateData() {this.$set(this.data, 4, {name: "更新后的项目",value: Math.random() * 100,});},},
};
</script>
/mixins/resize.js
import { debounce } from "@/utils";export default {data() {return {$_sidebarElm: null,$_resizeHandler: null,};},mounted() {this.initListener();// console.log(888, this.fontSize(1));},activated() {if (!this.$_resizeHandler) {// avoid duplication initthis.initListener();}// when keep-alive chart activated, auto resizethis.resize();},beforeDestroy() {this.destroyListener();},deactivated() {this.destroyListener();},methods: {// 字体大小自适应fontSize(res) {let docEl = document.documentElement,clientWidth =window.innerWidth ||document.documentElement.clientWidth ||document.body.clientWidth;if (!clientWidth) return;let fontSize = 100 * (clientWidth / 1920);return res * fontSize;},// use $_ for mixins properties// https://vuejs.org/v2/style-guide/index.html#Private-property-names-essential$_sidebarResizeHandler(e) {if (e.propertyName === "width") {this.$_resizeHandler();}},initListener() {this.$_resizeHandler = debounce(() => {this.resize();}, 100);window.addEventListener("resize", this.$_resizeHandler);this.$_sidebarElm =document.getElementsByClassName("sidebar-container")[0];this.$_sidebarElm &&this.$_sidebarElm.addEventListener("transitionend",this.$_sidebarResizeHandler);},destroyListener() {window.removeEventListener("resize", this.$_resizeHandler);this.$_resizeHandler = null;this.$_sidebarElm &&this.$_sidebarElm.removeEventListener("transitionend",this.$_sidebarResizeHandler);},resize() {const { chart } = this;chart && chart.resize();},},
};
对比原来柱状图
<template><div class="w100 h100"><div class="flex-3 h100" ref="chart6" /></div>
</template><script>
import resize from "./mixins/resize";
let color = ["#FFF200", "#ff6200"];
let color1 = ["rgba(255, 225, 128,.6)", "rgba(245, 116, 116,.6)"];
export default {mixins: [resize],props: ["list"],watch: {list: {handler(val) {this.initChart();// 深度监听没有旧值let month = val.monthOrDayOrTimeList;let orderNum = val.administrativeDivisionList;// let month = val.map((item) => {// return item.date;// });// let orderNum = val.map((item) => {// return item.sugarAfterMeal;// });// let orderNum1 = val.map((item) => {// return 47 - item.sugarAfterMeal;// });let option = {xAxis: [{data: month,},],series: [{name: "火灾总量",data: orderNum, // 订单量},// {// name: "非轻微火灾",// data: orderNum1, // 订单量// },],};this.chart.setOption(option);if (this.timeId) {clearInterval(this.timeId);this.timeId = null;}if (month.length > this.maxNum) {let num = 0;this.timeId = setInterval(() => {if (num + this.maxNum == month.length) {num = 0;} else {num += 1;}let option = {dataZoom: [{startValue: num, // 从头开始。endValue: num + this.maxNum - 1, // 一次性展示几个},],};this.chart.setOption(option);}, 3000);}},// 这里是关键,代表递归监听的变化deep: true,},},data() {return {chart: null,maxNum: 12, // 一次性展示几个。timeId: null,};},mounted() {console.log("tab1Bar来了");this.$nextTick(() => {this.initChart();});},beforeDestroy() {console.log("tab1Bar走了");if (!this.chart) {return;}this.chart = null;clearInterval(this.timeId);this.timeId = null;},methods: {init() {},initChart() {this.chart = this.$echarts.init(this.$refs.chart6);let option = {grid: {top: "20%",left: "6%",right: "1%",bottom: "4%",containLabel: true,},tooltip: {show: true,trigger: "item",formatter: "{b}: {c}",},//滑动条dataZoom: [{xAxisIndex: 0, //这里是从X轴的0刻度开始show: false, //是否显示滑动条,不影响使用type: "inside", // 这个 dataZoom 组件是 slider 型 dataZoom 组件startValue: 0, // 从头开始。endValue: this.maxNum - 1, // 一次性展示几个},],// 横坐标设置xAxis: [{type: "category",boundaryGap: true,//坐标轴axisLine: {lineStyle: {color: "#2384B1", //横轴颜色width: this.fontSize(0.01), //横轴粗细},},axisLabel: {interval: 0, // 显示所有标签rotate: 30, // 倾斜标签以节省空间textStyle: {color: "#fff", // 横坐标颜色fontSize: this.fontSize(0.13),},},axisTick: {show: false, //不显示坐标轴刻度},// data: this.month,},],// Y轴设置yAxis: [{type: "value",min: 0,minInterval: 1,// 网格线splitLine: {show: true,lineStyle: {color: "#023052",type: "dotted",},},axisLine: {show: false,},//坐标值标注axisLabel: {textStyle: {color: "#fff",fontSize: this.fontSize(0.13),},},},],legend: {itemHeight: this.fontSize(0.12), //图例图标的高度itemWidth: this.fontSize(0.2), //图例图标的宽度itemGap: this.fontSize(0.23), //图例图标与文字间的间距textStyle: {color: "#fff",borderColor: "#fff",fontSize: this.fontSize(0.14),},top: 7,right: 20,},series: [{name: "",type: "bar",// barWidth: "30%",barWidth: this.fontSize(0.2),itemStyle: {normal: {show: true,color: new this.$echarts.graphic.LinearGradient(0, 0, 0, 1, [{offset: 0,color: color[0],},{offset: 1,color: color1[0],},]),barBorderRadius: [4, 4, 0, 0], // 设置柱形四个角的圆角半径,顺序为左上、右上、右下、左下shadowColor: color1[0],shadowBlur: 24,},},// data: this.orderNum, // 订单量label: {normal: {show: true,position: "top", //在上方显示textStyle: {//数值样式color: "#fff",fontSize: this.fontSize(0.13),// fontWeight: 700,},},},},// {// name: "",// type: "bar",// // barWidth: "30%",// barWidth: this.fontSize(0.2),// itemStyle: {// normal: {// show: true,// color: new this.$echarts.graphic.LinearGradient(0, 0, 0, 1, [// {// offset: 0,// color: color[1],// },// {// offset: 1,// color: color1[1],// },// ]),// barBorderRadius: [4, 4, 0, 0], // 设置柱形四个角的圆角半径,顺序为左上、右上、右下、左下// shadowColor: color1[1],// shadowBlur: 24,// },// },// // data: this.orderNum, // 订单量// label: {// normal: {// show: true,// position: "top", //在上方显示// textStyle: {// //数值样式// color: "#fff",// fontSize: this.fontSize(0.13),// // fontWeight: 700,// },// },// },// },],};this.chart.setOption(option);},},
};
</script>
<style lang="sass" scoped>
@import "./css/rem.scss"
</style>
这篇关于echarts最新封装柱状图的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!