最初想着怎么给echarts设置vw单位或者rem,echart中怎么把legend的单位设置为vw或者rem来使表格自适应,后面发现行不通。
项目中使用px-to-vw包,将所有px转为对应的vw,所有可以根据相同比例进行缩放,做到自适应效果。但是使用了echarts图表,图表中的fontSize和legend的大小等默认都是px单位。当屏宽为4K屏时,其他地方元素字体等都能适应,但是echarts就会显得很小,还是之前1920的大小。
第一个想法当然是也使用vw或者rem单位就可以做到和页面自适应相同的效果,但是传入vw,rem单位是没有用的。
查看echarts的官方文档试图寻找解决办法:echarts移动端自适应
看到文档中说可以使用百分比,相对于父元素的比例。
于是满心欢喜的把所有数值都换算成了百分比,但是结果却不正确(这里不上例子了,结果就是不正确),自己还是太嫩没有认真审题,文档中给的是定位方式,而不是大小尺寸。
还有一种官方提供的Media Query方式,当然可以按照这种媒体查询的方式来写,这里不讨论这种方式。
出现问题:他的fontSize是相对于根元素(html)的百分比,于是把所有的fontSize也换算成根元素的百分比,但是结果还是有问题:比如legend中的itemWidth,itemHeight,itemGap,柱状图中的barWidth,坐标系中的axisLine的width都会出问题。。。
顿时整个人就不好了。
解决方案:将实际窗口的大小与设计图窗口大小做比得到要给相对的比率,每个单位数值和这个比率相乘即可。即:按比例缩放字体。比如设计图是1920*1080的,某个数值是fontSize:12,当前显示器是3840的大屏,那么你现在的字体大小应该是:12*(3840/1920)= 24。
所以我们的换算函数:
//当前视口宽度
let nowClientWidth = document.documentElement.clientWidth;
换算方法
function nowSize(val,initWidth=1920){
return val * (nowClientWidth/initWidth);
}
然后将配置项中所有的跟大小相关的数值调用这个方法:
const barOption = {
backgroundColor: 'transparent',
tooltip: {
trigger: 'axis',
axisPointer: {
type: 'shadow'
}
},
legend: {
data: ['门禁进入', '门禁外出'],
align: 'left',
top: nowSize(18),
right: nowSize(20),
textStyle: {
color: "#c1c5cd",
fontSize:nowSize(13)
},
itemWidth: nowSize(10),
itemHeight: nowSize(10),
itemGap: nowSize(12)
},
grid: {
top: '24%',
left: '3%',
right: '3%',
bottom: '3%',
containLabel: true
},
xAxis: [{
type: 'category',
data: [
'1号楼',
'2号楼',
'3号楼',
'4号楼',
'5号楼',
'6号楼',
'7号楼',
'8号楼',
],
axisLine: {
show: true,
lineStyle: {
color: "#45647f",
width: nowSize(1),
type: "solid"
}
},
axisTick: {
show: false,
},
axisLabel: {
show: true,
textStyle: {
color: "#a1d8f1",
fontSize:nowSize(12)
}
},
}],
yAxis: [{
type: 'value',
axisTick: {
show: false,
},
axisLine: {
show: true,
lineStyle: {
color: "#45647f",
width: nowSize(1),
type: "solid"
},
},
splitLine: {
show: false
},
axisLabel: {
show: true,
textStyle: {
color: '#a1d8f1',
fontSize: nowSize(12)
}
}
}],
series: [{
name: '门禁进入',
type: 'bar',
data: [20, 50, 80, 58, 83, 68, 57, 100],
barWidth: nowSize(8), //柱子宽度
// barGap: 1, //柱子之间间距
itemStyle: {
color: '#14e3cc'
}
}, {
name: '门禁外出',
type: 'bar',
data: [50, 70, 60, 61, 75, 87, 60, 62],
barWidth: nowSize(8),
// barGap: 1,
itemStyle: {
color: '#f84f55'
}
}]
}
使用比例换算后1920下的效果图:
使用比例换算后3840下的效果图:
由于这里使用的开发者模式的responsive来模拟效果,所以和实际效果有偏差(模糊)。上面两张图没有明显的差别,是因为这就是我们要的效果,相应的字体,宽度等都放大了。
为了展示差别这里放一张不使用比例的效果图: