vue3之echarts柱状图-圆锥加自动轮播
vue3之echarts柱状图-圆锥加自动轮播
效果:
版本
"echarts": "5.4.2"
核心代码:
<template>
<div ref="echartRef" class="chart"></div>
<svg>
<linearGradient v-for="(item, i) in colors" :id="`lab${i}`" :key="i" x1="0" y1="0" x2="0" y2="1">
<stop offset="38%" stop-color="#ffffff"></stop>
<stop offset="100%" :stop-color="item"></stop>
</linearGradient>
<linearGradient v-for="(item, i) in colors" :id="`area${i}`" :key="`area${i}`" x1="0" y1="1" x2="0" y2="0">
<stop offset="0%" stop-color="transparent"></stop>
<stop offset="30%" :stop-color="item"></stop>
</linearGradient>
</svg>
</template>
<script setup lang="ts">
import { onMounted, reactive, onUnmounted, ref, nextTick } from 'vue';
import * as echarts from 'echarts';
// 颜色配置
const colors = ['rgba(255, 145, 56, 1)', 'rgba(252, 219, 31, 1)', 'rgba(91, 251, 223, 1)', 'rgba(16, 178, 255, 1)'];
const info = reactive({
curData: [
{
name: '渝',
value: '5978',
},
{
name: '豫',
value: '5806',
},
{
name: '冀',
value: '4947',
},
{
name: '苏',
value: '2942',
},
{
name: '鲁',
value: '2678',
},
{
name: '晋',
value: '2621',
},
{
name: '陕',
value: '1944',
},
{
name: '鄂',
value: '1551',
},
{
name: '皖',
value: '1387',
},
],
});
let timer: any = null;
let myEchart: any = null;
const echartRef = ref(null);
const dataZoomEndValue = 4;
const option = ref(null);
onMounted(() => {
initChart();
});
onUnmounted(() => {
clearInterval(timer);
timer = null;
});
const initChart = () => {
if (echartRef.value && !myEchart) {
myEchart = echarts.init(echartRef.value, '', { renderer: 'svg' });
myEchart.on('mouseover', () => {
endRoll();
});
myEchart.on('mouseout', () => {
startRoll();
});
}
getChartOptions();
};
// 结束滚动
const endRoll = () => {
clearInterval(timer);
timer = null;
};
// 开启滚动
const startRoll = () => {
nextTick(() => {
// 自动滚动
if (info.curData.length > 5) {
timer = setInterval(() => {
if (option.value.dataZoom[0].endValue === info.curData.length) {
option.value.dataZoom[0].startValue = 0;
option.value.dataZoom[0].endValue = dataZoomEndValue;
} else {
option.value.dataZoom[0].startValue += 1;
option.value.dataZoom[0].endValue += 1;
}
myEchart.setOption(option.value);
}, window.config.chartRollTime);
}
});
};
const getChartOptions = () => {
endRoll();
const sortData = info.curData.sort((a: any, b: any) => b.value - a.value);
const xData = sortData.map((item: { name: string }) => item.name);
const fontSize = 14;
const topFontSize = 12;
const symbolSizeW = 60;
const laboff = -20;
option.value = {
tooltip: {
trigger: 'axis',
axisPointer: {
type: 'none',
},
formatter: (par: any) => {
return `${par[0].name}:${par[0].value}`;
},
textStyle: {
fontSize,
},
},
xAxis: {
data: xData,
show: true,
type: 'category',
axisLabel: {
fontFamily: 'HONOR Sans CN',
color: 'rgba(238, 246, 255, 1)',
fontSize,
padding: [0, 0, 0, 0],
},
axisLine: {
show: true,
lineStyle: {
color: 'rgba(186, 215, 255, 1)',
opacity: 0.5,
},
},
axisTick: {
show: false,
},
splitLine: {
show: false,
},
},
yAxis: {
type: 'value',
show: true,
splitNumber: 5,
min: 0,
axisLine: {
show: false,
},
splitLine: {
show: true,
lineStyle: {
color: '#BAD7FF',
opacity: 0.1,
},
},
axisLabel: {
color: '#EEF6FF',
fontSize,
padding: [0, 0, 0, 0],
},
},
grid: {
left: 0,
right: 10,
top: 20,
bottom: 30,
containLabel: true,
},
series: [
{
type: 'pictorialBar',
symbol: 'path://M0,10 L10,10 C5.5,10 5.5,5 5,0 C4.5,5 4.5,10 0,10 z',
data: sortData.map((item: { value: string }, index: number) => {
const curColor = index < 4 ? colors[index] : colors[3];
const num = index < 4 ? index : 3;
return {
value: item.value,
symbolSize: [symbolSizeW, '100%'],
symbolPatternSize: 100,
symbolOffset: [0, 2],
itemStyle: {
color: `url(#area${num})`,
opacity: 0.5,
borderColor: curColor,
borderWidth: 3,
},
emphasis: {
itemStyle: {
color: `url(#area${num})`,
},
},
label: {
show: true,
position: 'top',
offset: [0, 0],
textStyle: {
color: '#FFFFFF',
fontSize,
fontWeight: '500',
fontFamily: 'DINPro',
},
},
};
}),
},
{
type: 'pictorialBar',
symbol: 'rect',
symbolRepeat: false,
symbolSize: [0, 0],
symbolMargin: 1,
data: sortData.map((item: any, i: number) => {
const num = i < 4 ? i : 3;
return {
value: item.value,
label: {
show: true,
position: 'bottom',
offset: [0, laboff],
formatter: (par: any) => {
return `TOP${par.dataIndex + 1}`;
},
fontSize: topFontSize,
fontFamily: 'DINPro',
color: `url(#lab${num})`,
fontStyle: 'italic',
fontWeight: '600',
},
};
}),
},
],
dataZoom: [
{
show: false,
xAxisIndex: 0,
startValue: 0,
endValue: dataZoomEndValue,
},
{
type: 'inside',
show: true,
xAxisIndex: [0],
start: 0, // 默认为1
end: 50,
},
],
};
myEchart.setOption(option.value);
startRoll();
};
</script>
<style scoped lang="scss">
.chart {
width: 380px;
height: 180px;
}
</style>