目录
1、图表全屏放大
2、dialog弹窗,传值放大
3、dialog弹窗,引入echarts组件放大
前置条件:基于v-scale-screen大屏适配插件,全局使用的单位为px,echarts属性对应的值为Number时,默认为px。
需求:因页面会拆分成n个子组件,每个子组件里内容的组合都不相同,我需要点击子组件时,对整个圈红的子组件放大显示。(类似下图,参考图为网图)
1、图表全屏放大
操作原理:利用echarts的.resize(),改变容器大小实现全屏变大。
优势:如果仅放大echarts,通用性蛮强的,因为api只是做的放大效果,所以当前页配置的属性全都生效。而且因为【点击放大】按钮是写在插件外的部分,不是用toolbox工具栏自定义事件,都不需要额外考虑“在全屏后如何隐藏掉放大按钮”。(不过就算考虑也没关系,操作方式可以参考【2dialog弹窗传值放大】)
具体实现参考这位大神的代码:
封装了一个echarts图全屏放大的功能_echarts怎么做到把图放大_外围前端吴彦祖的博客-CSDN博客
说几个局限性。
1)因为我是用v-scale-screen第三方插件做的适配,所以需要将插件内的tootip、legend属性中涉及到的size做处理,要做的改动有点多。(下图,图很大,字没变)
不过要是有大神已经做了css和js的全局适配,并且放大的要求的【全屏显示】,那很推荐,因为真的很省事。
2)如果是在同一个子组件有n个不同的图表、n个遍历显示的echarts、或者还带有其他一些自定义的信息,是不适合使用的。(比如下图,图片来自网络。内容太多,封装的全屏无法使整个子组件全屏)
3)当使用echarts自定义的鼠标事件,比如绘制地图,点击【下图1】的区域【放大】,显示区域内详细内容(下图2)时,大屏后不支持切换整体地图和区域地图互相切换,只能整体地图放大(下图1)or区域地图放大(下图2)。
不过其实大神的标题已经写得很明确了,是为echarts图做的放大效果,只不过不符合我们的需求而已。
2、dialog弹窗,传值放大
和【1全屏放大】相似,封装的弹窗组件。
优势:自定义的放大事件是写在toolbox工具栏中的,如果是单一的echarts,统一在封装弹窗内将事件赋值为false,很方便。
具体实现参考这位大神的代码:
echarts自定义全屏弹窗_echarts点击弹出窗口_禾子逸的博客-CSDN博客
但也存在局限性。
比如【1全屏放大__3)绘制地图】时,自定义的toolbox放大/返回事件在切换整体地图和局部地图不同图标的显示时,就不是那么友好了。
其余局限性和【1全屏放大】也是差不多的。
3、dialog弹窗,引入echarts组件放大
以上两种方式都不太符合前置需求,但是通过前两个链接,可以总结出一些使用经验:
1)封装共通组件;
2)需要支持子组件内所有内容一同显示在共通组件内,且样式正常;
3)需要支持共通组件内所有放大后的size自适应大小;
4)需要支持所有已定义的鼠标事件,例如 mapCharts.on('click',()={});
5)需要支持自定义【放大】、【返回】按钮在页面变化时的动态显示。
以上需求对应的实现思路:
1)封装仅做css处理的共通弹窗组件,背景色、图案等都处理好,引入圈红子组件。
2)圈红子组件被引入时,所有内容都会被显示出来,此时大概率在弹窗内左上的位置。(大概是下图这样)
3)不做任何处理时,因v-scale-screen的作用,在屏幕没有变化时,共通组件内所有的size都不会变化,和圈红子组件一致。不过可以给引入的子组件绑定ref,通过ref找到dom元素,做ref.style.transform = 'scale(2)'的倍数显示,就会所有内容都被放大且符合放大前的比例。
但也有些许缺陷,清晰度会有所降低……
4)因为是引入的子组件,鼠标事件都是生效的。
5)因为是引入的子组件,唯一需要注意的是,不要在toolbox工具栏中写自定义事件了,把它拿出来单独放子组件的页面里吧。方便在弹窗中做隐藏。(下图是写在toolbox中,【放大】子组件的显示,反向举例。)
弹窗参考代码:
<template> <!-- 区域整体+弹窗 --> <div class="all"> <div class="center"> <div class="title"> <span class="text">{{ titleOne }}</span> <span class="close" @click="close">×</span> </div> <div class="log" ref="log"> // :num=0 传值给echarts,因echarts注册时只允许存在1个id,可以做区分 <Contrast :num="'0'" v-if="title === '第一工場'"></Contrast> <FactoryListTwo :num="'0'" v-if="title === '第二工場'"></FactoryListTwo> <StoreCharts :num="'0'" v-show="title === 'japan'"></StoreCharts> </div> </div> </div> </template> <script> // 引入echasrts组件 import Contrast from '@/views/components/Contrast' import FactoryListTwo from '@/views/components/FactoryListTwo' import StoreCharts from '@/views/components/storeCharts.vue' export default { props: { show: { type: Boolean, default: false }, title: { type: String, default: 'dialog测试' }, id: { type: String, default: '' }, val: { type: Object, default: null } }, components: { Contrast, FactoryListTwo, StoreCharts }, data() { return { // 标题 titleOne: this.title } }, mounted() { // 前期规划的不太好,所以不同的echarts子组件做放大效果时分开处理了。 switch (this.title) { case '第一工場': this.contrastFun() case '第二工場': this.factoryListFun() } }, methods: { // 第一工場时的css处理--多个echarts和其他标签组成的子组件 contrastFun() { let divList = this.$refs.log.children[0].children // 图标+横向柱状图 let div0 = divList[0] div0.style.transform = 'scale(2)' // 环形图 let div1 = divList[1] div1.style.transform = 'scale(2)' div1.style.width = div0.offsetWidth + 'px' // 环形图循环 span div1.children[0].style.display = 'none' }, // 调用第二工場的css处理--多个环状图组成的echarts子组件 factoryListFun() { let factoryList = this.$refs.log.children[0] // 标题放大 factoryList.children[0].style.transform = 'scale(2)' // 表格放大 // 因echarts使用series创建多环形,绝对定位需要加一个top: 80px; factoryList.children[1].children[0].style.top = '80px' factoryList.children[1].style.transform = 'scale(2)' }, // 关闭 close() { this.$emit('close') } } } </script> <style lang="scss" scoped> .all { position: fixed; top: 0; left: 0; width: 100%; height: 100%; // display: none; background-color: rgba(0, 0, 0, 0.5); .center { width: 1500px; height: 900px; margin: 100px auto; .title { height: 50px; display: flex; justify-content: space-between; flex-direction: row; align-items: center; background: #ffffff; font-size: 25px; .text { margin-left: 20px; } .close { width: 40px; height: 40px; margin-right: 20px; } } .log { width: 100%; padding: 2% 15%; height: 750px; background-image: radial-gradient( circle at 50% 100%, $color134186, $color0850 ); background: -webkit-radial-gradient(bottom, $color134186, $color0850); } } } </style>
复制