vue ecahrts组件开发

为满足特定需求,本文档记录了使用 Vue 和 Echarts 开发组件的过程。在第一版组件中,父组件需要传递大量数据,不利于维护。因此,开发了第二版组件,通过 bardata 仅传递接口数据,简化了使用,但限制了图例的通用性,适用于饼图和线图的封装,仍有改进空间。

开发背景

新需求需要使用echarts和vue开发,在开发的过程中,发现网上已有的组件不符合自己的需求,所以准备自己开发一个。
经历了两版,第一版的写完之后每次传递给子组件的时候需要一堆数据,所以今天在第一版的基础上开发了第二版。

第一版

ecahrts组件

<template>
  <div :id="id" :style="style" class="chartcom"></div>
</template>
<script>
export default {
  name: 'chart',
  data () {
    return {
      chart: ''
    }
  },
  props: {
    id: {
      type: String
    },
    width: {
      type: String,
      default: '100%'
    },
    height: {
      type: String,
      default: '400px'
    },
    margin: {
      type: String,
      default: '0 auto'
    },
    option: {
      type: Object,
      default () {
        return {
          title: {
            text: 'vue-Echarts'
          },
          legend: {
            data: ['销量']
          },
          xAxis: {
            data: ['衬衫', '羊毛衫', '雪纺衫', '裤子', '高跟鞋', '袜子', 'tuoxie']
          },
          series: [
            {
              name: '销量',
              type: 'line',
              data: [5, 20, 36, 10, 10, 70]
            }
          ]
        }
      }
    }
  },
  // 在Chart.vue中加入watch
  watch: {
    // 观察option的变化
    option: {
      handler (newVal, oldVal) {
        debugger
        if (this.chart) {
          if (newVal) {
            this.chart.setOption(newVal)
          } else {
            this.chart.setOption(oldVal)
          }
        } else {
          this.init()
        }
      },
      deep: true // 对象内部属性的监听,关键。
    }
  },
  computed: {
    style () {
      return {
        height: this.height,
        width: this.width,
        margin: this.margin
      }
    }
  },
  mounted () {
    this.init()
  },
  methods: {
    init () {
      this.chart = null
      if (this.chart && this.chart.dispose) {
        this.chart.dispose()
      }
      this.chart = this.$echarts.init(document.getElementById(this.id))
      this.chart.setOption(this.option, true)
    }
  }
}
</script>
<style>
  .chartcom {
    background: #fff;
    border-radius: 3px;
  }
</style>

父组件使用

 <chart id="test" :option="option" :height="height" :width="width"></chart>

option ,width,height是父组件传递给子组件的数据
option每次需要传很多数据,如果我需要在同一个父组件里使用好多个子组件,代码量就上来了,不好维护。
但是好处是,各种图例都适合。

第二版

组件代码

<template>
  <div ref="chartline" class="chartcom"></div>
</template>
<script>
export default {
  name: 'chart',
  data () {
    return {
      chart: '',
      normaloption: {
        title: {
          text: 'linechart'
        },
        tooltip: {
          trigger: 'axis'
        },
        grid: {
          left: '3%',
          right: '4%',
          bottom: '3%',
          containLabel: true
        },
        yAxis: [
          {
            show: true,
            type: 'value'
          }
        ],
        legend: {
          data: this.option.ldata
        },
        xAxis: {
          data: this.option.xdata
        },
        series: this.option.sdata
      }
    }
  },
  props: {
    option: {
      type: Object,
      default () {
        return {
          ldata: [1, 2, 3],
          xdata: [],
          sdata: []
        }
      }
    }
  },
  // 在Chart.vue中加入watch
  watch: {
    // 观察option的变化
    option: {
      handler (newVal, oldVal) {
        if (newVal) {
          this.normaloption.legend.data = newVal.ldata
          this.normaloption.xAxis.data = newVal.xdata
          this.normaloption.series = newVal.sdata
          this.init()
          // this.chart.setOption(this.normaloption)
        } else {
          this.normaloption.legend.data = oldVal.ldata
          this.normaloption.xAxis.data = oldVal.xdata
          this.normaloption.series = oldVal.sdata
          this.init()
          // this.chart.setOption(this.normaloption)
        }
      },
      deep: true // 对象内部属性的监听,关键。
    }
  },
  computed: {
  },
  mounted () {
    // this.init()
  },
  methods: {
    init () {
      this.chart = this.$echarts.init(this.$refs.chartline)
      this.chart.setOption(this.normaloption, true)
    }
  }
}
</script>
<style>
  .chartcom {
    background: #fff;
    border-radius: 3px;
    height: 400px;
  }
</style>

子组件使用

<chart :option='bardata'></chart>

bardata 里面只要传接口拿到的数据就好,不需要传一些多余的东西。
但是缺点是,针对饼图和线图,需要单独封装,不能共用。

仍然遗留了一个问题,

window.addEventListener('resize',function() {
this.chart.resize()
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值