首先附上v-chart官网地址:https://v-charts.js.org/#/
安装方式:
//注意:得安装echarts,因为v-charts是对echarts的封装
yarn add v-charts echarts
全局引入:
// main.js
import Vue from 'vue'
import VCharts from 'v-charts'
import App from './App.vue'
Vue.use(VCharts)
new Vue({
el: '#app',
render: h => h(App)
})
以柱状图为例:
<ve-histogram :data="chartData" :extend="dataExtend" :settings="dataSettings" width="100px"></ve-histogram>
- 三大基本要素
-
:data
表示要加载的图表数据 -
:settings
表示对图表的基础配置,比如指定纵坐标和横坐标的参数名,这个参数名是对应data数据的。但是在echarts中,是不叫横坐标,纵坐标这么low的名称的,横坐标通常称为维度
,对应纵坐标的不同数据被称为指标
-
:extend
表示额外配置,比如一些echarts里面的参数都可以写在extend里面,例如改变柱子颜色(color),柱子宽度(series),x轴(xAxis)或者y轴(yAxis)的字体大小和颜色,对图例的显示配置(legend)
-
下面逐个说明每个属性该如何配置:
- :settings
export default {
data () {
this.dataSettings= {
metrics: ['访问用户'], //定义指标名称,也就是以chartData里面的'访问用户'为key来取数据
dimension: ['日期'] //定维度名称,以chartData里面的'日期'为key来取数据
}
return {
chartData: {
columns: ['日期', '访问用户'], //第一个元素表示维度,第二个元素以及以后的种种元素都表示指标,后面有几个元素就会在统计图上显示几条柱,这里其实可以省略,因为metrics和dimension已经配置过来
rows: [ //从后台接口请求到的数据放在rows里面
{ '日期': '1/1', '访问用户': 1393 },
{ '日期': '1/2', '访问用户': 3530},
{ '日期': '1/3', '访问用户': 2923},
{ '日期': '1/4', '访问用户': 1723},
{ '日期': '1/5', '访问用户': 3792},
{ '日期': '1/6', '访问用户': 4593}
]
}
}
}
}
好了,来看一下基础配置生成的图表:

这是一个最简单的案例,意在理解metrics和dimension代表什么。但是我们实际请求接口返回的数据一定不是这样以中文名来作为key的,那么也就会用到别名。
this.dataSettings= {
// 地域配置
labelMap: {
percentage: "所占比例", // 点击柱子时显示的文字
},
dimension: ["talkDuration"], // 维度别名
metrics: ["percentage"], // 指标别名
itemStyle: {
normal: { //这个是显示在每条柱子上的数字
label: { show: true, position: "top", formatter: "{c}%" },
},
},
max: [100, 100], //这是刻度的最大值
};
注意:v-charts
更新到v-charts-v2
以后,labelMap需要替换成labelAlias
它所对应的数据是:
chartData: {
columns: ["talkDuration", "percentage"],
rows: [
{ 'talkDuration': '1/1', 'percentage': 1393 },
{ 'talkDuration': '1/2', 'percentage': 3530},
{ 'talkDuration': '1/3', 'percentage': 2923},
{ 'talkDuration': '1/4', 'percentage': 1723},
{ 'talkDuration': '1/5', 'percentage': 3792},
{ 'talkDuration': '1/6', 'percentage': 4593}
]
}
至于extend,它能配置的东西太多了,所有eharts setOption里面的参数都可以在这里面配置,这样也就打破了v-chart的局限性,实现任何UI需求上所需要的样式。
下面将对ve-histogram
柱形图,ve-ring
环形图,ve-bar
条形图,分别举具体的实例,来帮助大家理解extend里面的参数配置,来实现特殊需求的UI样式
在举例之前,罗嗦一下。有一些基础属性在做之前最好先阅读v-chart的开发文档,比如图表的宽度,高度配置,如果把图表装在外部容器中,宽度就是容器的宽度,高度也会自适应,不需要额外设置,但是会出现有一部分被遮挡的情况,比如y轴可能被挡住一些。
莫慌,这时候可以使用:grid
这个参数(在这里要特别说明一下,v-chart是对echarts进行的封装,方便我们在vue中进行使用,但是它的文档并不是很全面,制作简易的图表没有问题,但是要满足设计图上的UI,光靠v-chart文档是完全不行的,还是得我们去echarts官网查找相关参数,依靠:extend
额外配置属性回到熟悉的echarts配置上。这样就能满足echarts的所有功能。附上echarts各大参数地址:https://echarts.apache.org/zh/option.html#yAxis
):grid
就是echarts的参数,在v-chart官网里是没有说明的,它可以理解为图表区域,使用方式如下:
<ve-histogram :grid="{ containLabel: true, right: 40}"
:data="ageData" :settings="dataSettings" :extend="dataExtend" />
-
containLabel
表示是否显示刻度 -
right
表示图表区域距离父视图容器右侧的距离
这样就能让图表往左侧偏移一些,解决了遮挡问题,同理,top,left,bottom也能灵活使用
``
言归正传,接下来举三个具体实例:

<ve-bar class="barStyle"
:data="areaData"
:legend-visible="false" //是否显示图例
:colors="colors" //柱子颜色,是一个数组
:settings="areaSettings"
:extend="areaExtend"
:grid="{ containLabel: true, right: 40, top: 30, left: 60 }"
/>
export default {
name: "Personas",
data() {
this.areaSettings = {
// 地域配置
labelMap: {
percentage:
},
dimension: ["talkDuration"],
metrics: ["percentage"],
dataOrder: { //按照由大到小进行排序
label: "percentage",
order: "desc",
},
itemStyle: {
normal: { //这里没有使用百分数的单位,所以%是自己加上去的
label: { show: true, position: "right", formatter: "{c}%" },
},
},
max: [100, 100],
};
this.areaExtend = {
"yAxis.0.splitLine.show": false, // y轴表格线不显示
"xAxis.0.splitLine.show": false, // x轴标签不显示
"xAxis.0.axisLabel.show": false, // x轴标签不显示
yAxis: {
axisLabel: {
textStyle: {
color: "#9B9B9B", // y轴字体颜色
padding: [3, 15, 5, 6], // 上右下左
},
},
},
// 每个柱子
series(v) {
// console.log("v", v);
// 设置柱子的样式
v.forEach((i) => {
i.barWidth = 45; //柱子高度
});
return v;
},
};
return{
colors: ["rgba(45, 103, 235, 0.5)"],
areaData: {
rows: [
{ 'talkDuration': '1.广东', 'percentage': 20 },
{ 'talkDuration': '2.北京', 'percentage': 20 },
{ 'talkDuration': '3.上海', 'percentage': 18 },
{ 'talkDuration': '4.江苏', 'percentage': 8 },
{ 'talkDuration': '5.浙江', 'percentage': 6 },
{ 'talkDuration': '6.山东', 'percentage': 4 }
],
},
}
}

<ve-ring
:legend-visible="true"
:extend="sexExtend"
:resizeable="true"
:settings="sexSettings"
:data="sexData"
/>
this.sexSettings = {
dimension: "talkDuration",
metrics: "percentage",
// radius: ["60px", "100px"], //圆环内径和外径,可以用px单位
radius: ["40%", "65%"], //之所以注释掉换成百分比,是为了做屏幕适配,使图表在大屏小屏电脑上能自动变大和变小
};
this.sexExtend = {
legend: {
show: true, //显示图例
orient: "vertical", //使图例竖向排列
icon: "circle", //图例的标识改成圆点
bottom: 0, //距离底部0
itemGap: 20, //图例各个元素之间的距离为20
formatter: (name) => { //自定义图例上的文字格式
let param = "";
if (this.sexData) {
param = this.sexData.rows.find((item) => {
return item["talkDuration"] === name;
})["percentage"];
}
return name + " " + param + " " + param + "%";
},
},
series: {
center: ["50%", "35%"], //图表在容器的位置
label: {
normal: {
show: false,
},
},
},
color: ["#5253FD", "#FA6090", "#05C8D6"], //改变环形每个区域的颜色
};
return{
sexData: {
rows: [
{ 'talkDuration': '男', 'percentage': 30 },
{ 'talkDuration': '女', 'percentage': 48 },
{ 'talkDuration': '未知', 'percentage': 22 }
],
},
}

因为v-chart提供的双轴案例是需要至少两条柱子才能实现双轴,但UI要求只显示一根柱子,但是需要同时标名人数和百分比。所以,这里的思路是把两条柱子完全重叠在一起。
<ve-histogram
:extend="systemExtend"
:legend-visible="true"
:grid="{ containLabel: true, right: 40, top: 80,bottom:10 }"
:data="systemData"
:settings="dataSettings"
/>
this.dataSettings = {
labelMap: {
percentage: "人数(万人)",
per2: "百分比",
},
dimension: ["talkDuration"], // 维度-横坐标
axisSite: { right: ["per2"] }, //百分比对应的数据是per2
metrics: ["percentage", "per2"], // 指标
yAxisType: ["KMB", "percent"],
yAxisName: ["人数(万)", "百分比"],
itemStyle: {
normal: { //因为柱子重叠,文字也会重叠,这里是取出文字,把顶层柱子的文字加上换行符
label: { show: true, position: "top", formatter: (params)=>{
if(params.seriesIndex===0){
return params.data+"万\n"
}
return "("+ Number(params.data*100).toFixed()+"%)"
} },
},
},
max: [100, 1], //左侧最大值为100,右侧为1,注意:百分比的最大值是1哦,数据需要除以100,改成小数
};
this.systemExtend = {
xAxis: {
axisLabel: {
textStyle: {
color: "grey", // y轴字体颜色
fontSize: 11,
},
},
},
yAxis: {
type: "value",
splitNumber: 10, //这里是刻度间隔,默认是20哦
},
// 每个柱子
series(v) {
// console.log("v", v);
// 设置柱子的样式
v.forEach((i) => {
(i.barWidth = "40%"), (i.barGap = "-100%"); //重头戏在这里,barGap = "-100%",可以使两根柱子完全重合,否则就是叠加
});
return v;
},
color: ["#8592F2","#8CC9FF"], //两条柱子颜色
};
return{
systemData: {
rows: [
{ 'talkDuration': 'Android', 'percentage': 73,'per2': 0.73 },
{ 'talkDuration': 'IOS', 'percentage': 7,'per2': 0.07 },
{ 'talkDuration': '未知', 'percentage': 20,'per2': 0.2 }],
},
}
如果大家有其他好的案例,欢迎留言,共同学习!
网友评论