You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
308 lines
9.4 KiB
308 lines
9.4 KiB
<template>
|
|
<div :id="idName" :style="{ height: height, width: width }" />
|
|
</template>
|
|
<script>
|
|
export default {
|
|
props: {
|
|
idName: { type: String, default: 'chart' },
|
|
width: { type: String, default: '100%' },
|
|
height: { type: String, default: '183px' },
|
|
chartData: { type: Array, default: () => [] },
|
|
desc: { type: String, default: '' }
|
|
},
|
|
data() {
|
|
return {
|
|
dataX: [],
|
|
dataY: [],
|
|
maxData: [],
|
|
disabled: false
|
|
}
|
|
},
|
|
watch: {
|
|
chartData: {
|
|
handler(val, olVal) {
|
|
this.initFun()
|
|
},
|
|
deep: true
|
|
}
|
|
},
|
|
mounted() {
|
|
this.initFun()
|
|
},
|
|
methods: {
|
|
initFun() {
|
|
if (this.chartData && this.chartData.length > 0) {
|
|
this.dataX = []
|
|
this.dataY = []
|
|
this.chartData.forEach(item => {
|
|
this.dataX.unshift(item.value)
|
|
this.dataY.unshift(item.name)
|
|
})
|
|
}
|
|
|
|
this.$nextTick(() => {
|
|
this.chartData.forEach(item => {
|
|
this.maxData.unshift({
|
|
value: Math.max(...this.dataX),
|
|
name: item.name,
|
|
values: item.value
|
|
})
|
|
})
|
|
this.visionFun()
|
|
})
|
|
},
|
|
visionFun() {
|
|
// 基于准备好的dom,初始化echarts实例
|
|
const monthTopEcharts = this.$echarts.init(document.getElementById(this.idName))
|
|
// 定义图形
|
|
const CubeLeft = this.$echarts.graphic.extendShape({
|
|
shape: {
|
|
x: 0,
|
|
y: 0
|
|
},
|
|
buildPath: function(ctx, shape) {
|
|
// console.log(ctx, shape)
|
|
const yAxisPoint = shape.yAxisPoint
|
|
const c0 = [shape.x, shape.y]
|
|
const c1 = [shape.x + 4, shape.y - 4]
|
|
const c2 = [yAxisPoint[0] + 4, yAxisPoint[1] - 4]
|
|
const c3 = [yAxisPoint[0], yAxisPoint[1]]
|
|
ctx.moveTo(c0[0], c0[1]).lineTo(c1[0], c1[1]).lineTo(c2[0], c2[1]).lineTo(c3[0], c3[1]).closePath()
|
|
}
|
|
})
|
|
const CubeRight = this.$echarts.graphic.extendShape({
|
|
shape: {
|
|
x: 0,
|
|
y: 0
|
|
},
|
|
buildPath: function(ctx, shape) {
|
|
const yAxisPoint = shape.yAxisPoint
|
|
const c1 = [shape.x, shape.y]
|
|
const c2 = [yAxisPoint[0], yAxisPoint[1]]
|
|
const c3 = [yAxisPoint[0] + 4, yAxisPoint[1] + 8]
|
|
const c4 = [shape.x + 4, shape.y + 8]
|
|
ctx.moveTo(c1[0], c1[1]).lineTo(c2[0], c2[1]).lineTo(c3[0], c3[1]).lineTo(c4[0], c4[1]).closePath()
|
|
}
|
|
})
|
|
const CubeTop = this.$echarts.graphic.extendShape({
|
|
shape: {
|
|
x: 0,
|
|
y: 0
|
|
},
|
|
buildPath: function(ctx, shape) {
|
|
const c1 = [shape.x, shape.y]
|
|
const c2 = [shape.x + 4, shape.y + 8]
|
|
const c3 = [shape.x + 8, shape.y + 4]
|
|
const c4 = [shape.x + 4, shape.y - 4]
|
|
ctx.moveTo(c1[0], c1[1]).lineTo(c2[0], c2[1]).lineTo(c3[0], c3[1]).lineTo(c4[0], c4[1]).closePath()
|
|
}
|
|
})
|
|
this.$echarts.graphic.registerShape('CubeLeft', CubeLeft)
|
|
this.$echarts.graphic.registerShape('CubeRight', CubeRight)
|
|
this.$echarts.graphic.registerShape('CubeTop', CubeTop)
|
|
// 基于准备好的dom,初始化echarts实例
|
|
monthTopEcharts.setOption({
|
|
backgroundColor: 'transparent',
|
|
yAxis: {
|
|
type: 'category',
|
|
data: this.dataY,
|
|
axisLine: {
|
|
show: false,
|
|
lineStyle: {
|
|
color: 'white'
|
|
}
|
|
},
|
|
axisTick: {
|
|
show: false
|
|
},
|
|
offset: 5,
|
|
axisLabel: {
|
|
show: true,
|
|
margin: 6,
|
|
formatter: (params) => {
|
|
var val = ''
|
|
if (params.length > 5) {
|
|
val = params.substr(0, 5) + '...'
|
|
return val
|
|
} else {
|
|
return params
|
|
}
|
|
}
|
|
}
|
|
},
|
|
xAxis: {
|
|
type: 'value',
|
|
show: false
|
|
},
|
|
tooltip: {
|
|
show: true,
|
|
// backgroundColor: '#fff', // 通过设置rgba调节背景颜色与透明度
|
|
formatter: '{b}',
|
|
position: 'left'
|
|
// color: '#000'
|
|
},
|
|
grid: {
|
|
left: '20%',
|
|
right: '25%',
|
|
bottom: '2%',
|
|
top: '3%'
|
|
},
|
|
series: [
|
|
// 下面背景立体图
|
|
{
|
|
type: 'custom',
|
|
emphasis: {
|
|
scale: false
|
|
},
|
|
// 图形渲染的逻辑
|
|
renderItem: function(params, api) {
|
|
const location = api.coord([api.value(0), api.value(1)])
|
|
// 一组图形元素--每个图形元素是一个 object
|
|
return {
|
|
type: 'group', // 一组
|
|
children: [{
|
|
type: 'CubeLeft', // 上方自定义的图形
|
|
shape: {
|
|
api,
|
|
xValue: api.value(0),
|
|
yValue: api.value(1),
|
|
x: location[0],
|
|
y: location[1],
|
|
yAxisPoint: api.coord([0, api.value(1)])
|
|
},
|
|
style: {
|
|
fill: 'rgba(7,29,97,.6)'
|
|
}
|
|
}, {
|
|
type: 'CubeRight', // 上方自定义的图形
|
|
shape: {
|
|
api,
|
|
xValue: api.value(0),
|
|
yValue: api.value(1),
|
|
x: location[0],
|
|
y: location[1],
|
|
yAxisPoint: api.coord([0, api.value(1)])
|
|
},
|
|
style: {
|
|
fill: 'rgba(10,35,108,.7)'
|
|
}
|
|
}, {
|
|
type: 'CubeTop', // 上方自定义的图形
|
|
shape: {
|
|
api,
|
|
xValue: api.value(0),
|
|
yValue: api.value(1),
|
|
x: location[0],
|
|
y: location[1],
|
|
yAxisPoint: api.coord([0, api.value(1)])
|
|
},
|
|
style: {
|
|
fill: 'rgba(11,42,106,.8)'
|
|
}
|
|
}]
|
|
}
|
|
},
|
|
data: this.maxData
|
|
},
|
|
// 上面实际数据
|
|
{
|
|
type: 'custom',
|
|
renderItem: (params, api) => {
|
|
const location = api.coord([api.value(0), api.value(1)])
|
|
return {
|
|
type: 'group',
|
|
children: [{
|
|
type: 'CubeLeft',
|
|
shape: {
|
|
api,
|
|
xValue: api.value(0),
|
|
yValue: api.value(1),
|
|
x: location[0],
|
|
y: location[1],
|
|
yAxisPoint: api.coord([0, api.value(1)])
|
|
},
|
|
style: {
|
|
fill: new this.$echarts.graphic.LinearGradient(1, 0, 0, 0, [{
|
|
offset: 0,
|
|
color: '#00FFFF'
|
|
},
|
|
{
|
|
offset: 1,
|
|
color: '#49BDE5'
|
|
}
|
|
])
|
|
}
|
|
}, {
|
|
type: 'CubeRight',
|
|
shape: {
|
|
api,
|
|
xValue: api.value(0),
|
|
yValue: api.value(1),
|
|
x: location[0],
|
|
y: location[1],
|
|
yAxisPoint: api.coord([0, api.value(1)])
|
|
},
|
|
style: {
|
|
fill: new this.$echarts.graphic.LinearGradient(1, 0, 0, 0, [{
|
|
offset: 0,
|
|
color: '#00FFFF'
|
|
},
|
|
{
|
|
offset: 1,
|
|
color: ' #49BDE5'
|
|
}
|
|
])
|
|
}
|
|
}, {
|
|
type: 'CubeTop',
|
|
shape: {
|
|
api,
|
|
xValue: api.value(0),
|
|
yValue: api.value(1),
|
|
x: location[0],
|
|
y: location[1],
|
|
yAxisPoint: api.coord([0, api.value(1)])
|
|
},
|
|
style: {
|
|
fill: new this.$echarts.graphic.LinearGradient(1, 0, 0, 0, [{
|
|
offset: 0,
|
|
color: '#00FFFF'
|
|
},
|
|
{
|
|
offset: 1,
|
|
color: '#49BDE5'
|
|
}
|
|
])
|
|
}
|
|
}]
|
|
}
|
|
},
|
|
data: this.dataX
|
|
},
|
|
// 数值显示
|
|
{
|
|
type: 'bar',
|
|
label: {
|
|
show: true,
|
|
position: 'right',
|
|
offset: [20, 3],
|
|
fontSize: 16,
|
|
color: '#FFC700',
|
|
formatter: (params) => {
|
|
return params.data.values
|
|
}
|
|
},
|
|
itemStyle: {
|
|
color: 'transparent'
|
|
},
|
|
data: this.maxData
|
|
}]
|
|
})
|
|
window.addEventListener('resize', () => { monthTopEcharts.resize() })
|
|
}
|
|
}
|
|
}
|
|
|
|
</script>
|
|
<style style="scss" scoped>
|
|
</style>
|