美文网首页
vue中把echart封装为组件后多次引用,只有第一个可以res

vue中把echart封装为组件后多次引用,只有第一个可以res

作者: 3e2235c61b99 | 来源:发表于2022-01-05 16:59 被阅读0次

在项目中一个页面需要使用8、9个相似的echart图,大概可以分为两种:饼图和柱状图。本着不想多写代码的原则,我把饼图和柱状图分别封装了两个组件,然后多次引用。
引用之后效果实现了,但是在改变浏览器窗口大小的时候,多个饼图和柱状图的resize()方法分别只有第一个可以生效,其他的都不生效。
问题代码和效果图如下:

<el-row :gutter="10">
    <el-col :span="8"><pieCom chartId="AAA"></pieCom></el-col>
    <el-col :span="8"><pieCom chartId="BBB"></pieCom></el-col>
    <el-col :span="8"><pieCom chartId="CCC"></pieCom></el-col>
    <el-col :span="8"><barCom chartId="DDD"></barCom></el-col>
    <el-col :span="8"><barCom chartId="EEE"></barCom></el-col>
    <el-col :span="8"><barCom chartId="FFF"></barCom></el-col>
</el-row>
<!--封装的echart组件-->
<template>
    <div :id="chartId" class="echartsCase"></div>
</template>

<script>
    import echarts from 'echarts';
    import { throttle } from '@/utils/index.js';

    export default {
        props: {
            chartId: String
        },

        data() {
            return {
                chart: '',
                option: {}  // 根据需求自己定义
            }
        },

        mounted() {
            this.initChart();
            window.addEventListener('resize', this.resize);
        },

        beforeDestroy() {
            window.removeEventListener('resize', this.resize)
        },

        methods: {
            resize: throttle(function() {
                this.chart && this.chart.resize()
            }, 100),

            initChart() {
                this.chart = echarts.init(document.getElementById(this.chartId));
                this.chart.setOption(this.option)
            }
        }
    }
</script>
问题.gif
上面的代码是其中一个封装的echart组件,可以看到在浏览器窗口大小发生变化时,只有第一个饼图和第一个柱状图的大小发生了变化
问题原因:在一个页面中调用同一个封装了echart的组件多次之后,在resize时只能获取到第一个echart实例,其他的获取不到,所以只能使第一个echart实例尺寸发生变化
解决办法
<!--封装的echart组件-->
<template>
    <div :id="chartId" class="echartsCase"></div>
</template>

<script>
    import echarts from 'echarts';
    import {
        throttle
    } from '@/utils/index.js';

    export default {
        props: {
            chartId: String
        },

        data() {
            return {
                AAA: '',
                BBB: '',
                CCC: '',
                option: {}
            }
        },

        mounted() {
            this.initChart();
            window.addEventListener('resize', this.resize);
        },

        beforeDestroy() {
            window.removeEventListener('resize', this.resize)
        },

        methods: {
            resize: throttle(function() {
                // 此处重新获取调用当前组件的全部echart实例
                ['AAA', 'BBB', 'CCC'].forEach(item => {
                    this[item] = echarts.getInstanceByDom(document.getElementById(item));
                    this[item] && this[item].resize()
                })
            }, 100),

            initChart() {
                this[this.chartId] = echarts.init(document.getElementById(this.chartId));
                this[this.chartId].setOption(this.option)
            }
        }
    }
</script>
问题解决.gif

这样问题就解决啦

完美解决方案:
按评论区老哥的方法试了下,上述问题完美解决:

    mounted() {
      this.initChart();
      this.resize = throttle(() => {
        this.chart && this.chart.resize()
      }, 100);
      window.addEventListener('resize', this.resize);
    },

    methods: {
      // resize: throttle(function() {
      //   this.chart && this.chart.resize()
      // }, 100),

      initChart() {
        this.chart = echarts.init(document.getElementById(this.chartId));
        this.chart.setOption(this.option)
      }
    }

与之前相比,把resize方法写到了mounted中,完美解决

完美解决.gif

相关文章

网友评论

      本文标题:vue中把echart封装为组件后多次引用,只有第一个可以res

      本文链接:https://www.haomeiwen.com/subject/fgtkcrtx.html