基于vue 封装echarts 全局组件,柱状图,饼图,折线图

 1.使用npm安装echarts

npm install echarts --save

2.main.js文件下添加

import echarts from 'echarts'
Vue.prototype.$echarts = echarts

3.定义全局公用组件

<template>
  <div ref="chart" />
</template>

<script>
// 自行引入echarts
import echarts from "echarts";
export default {
  name: "EchartsLine",
  // 接收从父组件传回的值
  props: {
    getData: {
      type: Object,
      required: true,
    },
    iShow: {
      //折线,柱图,数据显隐
      type: Boolean,
      default: true,
    },
    iSxAxis: {
      //x轴显隐
      type: Boolean,
      default: true,
    },
  },
  data() {
    return {};
  },
  // 实时监听父组件传过来的值,进而执行drawBar方法,重绘图
  watch: {
    getData: {
      handler(value) {
        this.drawBar(value);
      },
      deep: true,
    },
  },
  mounted() {
    this.drawBar();
  },
  methods: {
    drawBar({
      legendData = this.getData.seriesData.map((r) => r.name), //图例数据
      textTitle = this.getData.textTitle, //主标题
      xName = this.getData.xname, //Y轴标注
      yName = this.getData.yname, //X轴标注
      subtext = this.getData.subtext, //副标题
      nameArray = this.getData.nameArray, //X轴数据
      colorArray = this.getData.colorArray, //自定义颜
      formatter = this.getData.formatter, //自定义提示内容显示格式
      radius = this.getData.radius, //如果是饼图,就传该属性,控制饼图大小
      center = this.getData.center, //如果是饼图,就传该属性,控制饼图位置
      roseType = this.getData.roseType, //如果是饼图,就传该属性,控制饼图样式
      tooltip = {
        trigger: "axis",
        axisPointer: {
          type: "cross",
          label: {
            backgroundColor: "#6a7985",
          },
        },
        // padding: [
        //   5, // 上
        //   30, // 右
        //   5, // 下
        //   30, // 左
        // ],
        textStyle: {
          fontStyle: "oblique",
        },
        formatter: formatter,
      },
      xAxis = [
        {
          show: this.iSxAxis,
          name: xName,
          type: "category",
          data: nameArray,
          nameLocation: "end",
          axisTick: {
            show: false,
          },
          splitLine: {
            show: false, // 去除网格线
          },
          axisLabel: {
            formatter: function (value) {
              let str = "";
              let num = 7; // 每行显示字数
              let valLength = value.length; // 该项x轴字数
              let rowNum = Math.ceil(valLength / num); // 行数
              if (rowNum > 1) {
                for (let i = 0; i < rowNum; i++) {
                  let temp = "";
                  let start = i * num;
                  let end = start + num;
                  temp = value.substring(start, end) + "\n";
                  str += temp;
                }
                return str;
              } else {
                return value;
              }
            },
          },
          nameTextStyle: {
            padding: [30, 0, 0, -30],
          },
        },
      ],
      dataZoom = [],
      grid = {
        left: 20,
        right: 20,
        bottom: 20,
        top: 80,
        containLabel: true,
      },
    } = {}) {
      const barBox = this.$echarts.init(this.$refs.chart); //初始化容器
      //定义series
      var series = this.getData.seriesData.map((r) => {
        return {
          name: r.name,
          type: r.type,
          // stack: 'Total',
          data: r.data,
          areaStyle: {}, //折线图,面积阴影
          label: {
            show: this.iShow, //开启显示
            position: "top", //在上方显示
            textStyle: {
              //数值样式
              color: "black",
              fontSize: 10,
              fontWeight: 600,
            },
          },
        };
      });
      //定义legendData
      let seriesData = this.getData.seriesData;
      if (seriesData.length > 0) {
        for (let i = 0; i < seriesData.length; i++) {
          if (seriesData[i].type === "pie") {
            //如果传递的type是pie 走这里面
            (tooltip = {
              trigger: "item",
              formatter: formatter,
            }),
              (legendData = []);
            const Data = this.getData.seriesData.map((r) => r.data);
            for (let j = 0; j < Data.length; j++) {
              for (let k = 0; k < Data[j].length; k++) {
                legendData.push(Data[j][k].name);
              }
              legendData.push(Data[j].name);
            }
            series = this.getData.seriesData.map((r) => {
              return {
                name: r.name,
                type: r.type,
                radius: radius, //饼图大小 //饼图大小
                data: r.data,
                center: center,
                roseType: roseType,
                label: {
                  show: true, //开启显示
                  position: "top", //在上方显示
                  textStyle: {
                    //数值样式
                    color: "black",
                    fontSize: 10,
                    fontWeight: 600,
                  },
                },
              };
            });
          }
        }
      }
      let option = {
        color: colorArray,
        legend: {
          data: legendData,
          bottom: "0",
        },
        title: {
          text: textTitle,
          left: "center",
          subtext: subtext,
          top: 17,
          textStyle: {
            color: "#333",
            fontSize: "18",
            fontWeight: "bolder",
          },
        },
        grid: grid,
        tooltip: tooltip,
        dataZoom: dataZoom,
        xAxis: xAxis,
        yAxis: [
          {
            axisLine: { show: false },
            name: yName,
            type: "value",
          },
        ],
        series,
      };
      const _this = this;
      barBox.setOption(option, true);
      barBox.off("click"); //事件多点触发
      barBox.on("click", function (data) {
        //柱子点击事件
        _this.$emit("onClick", data);
      });
    },
  },
};
</script>

 

 

4.组件调用Demo

//HeapTest.vue

<template>
  <div>
    <caet-echarts
        @onClick="onClick"
        :iShow="false"
      :getData="objectData"
      style="height: 400px; width: 800px"
    ></caet-echarts>
  </div>
</template>
<script>
import { getDateline } from "./api";
export default {
  name: "HeapTest",
  data() {
    return {
      objectData: {
        radius:['35%','75%'],//自定义饼图样式
        subtext: "",//副标题
        xname: "(日期)",
        yname: "单位/套",
        formatter:'{a}:<br>{b}: {c} (人)',
        textTitle: "某楼盘销售情况",
        nameArray: [], //后端传数据x轴
        seriesData: [], //后端传数据
        colorArray: ["#d91414", "#d5750e", "#4cabce", "#14ea4d","#364781"], //自定义颜色
      },
    };
  },
  mounted() {
    this.init();
  },
  methods: {
    onClick(data){//点击事件
      console.log(2222,data)
    },
    init() {
      getDateline().then((res) => {
        this.objectData.nameArray = res.result.nameArray;
        this.objectData.seriesData = res.result.seriesData;
      });
    },
  },
};
</script>
5.后台数据
export function getDateline() {//获取数据
  mockData.result = {
    nameArray: ['周一', '周二', '周三', '周四', '周五', '周六', '周天'],
    seriesData: [
      {
        type:'bar',
        name: '潜在客户',
        data: [
          { value: 2048, name: "周一" },
          { value: 735, name: "周二" },
          { value: 530, name: "周三" },
          { value: 484, name: "周四" },
          { value: 300, name: "周五" },
          { value: 300, name: "周六" },
          { value: 300, name: "周天" },
        ]
      },
      {
        type: 'line',
        name: '意向客户',
        data: [
          { value: 201, name: "周一" },
          { value: 711, name: "周二" },
          { value: 536, name: "周三" },
          { value: 124, name: "周四" },
          { value: 360, name: "周五" },
          { value: 314, name: "周六" },
          { value: 236, name: "周天" },
        ]
      },
      {
        type: 'bar',
        name: '预购客户',
        data: [
          { value: 150, name: "周一" },
          { value: 232, name: "周二" },
          { value: 201, name: "周三" },
          { value: 154, name: "周四" },
          { value: 190, name: "周五" },
          { value: 250, name: "周六" },
          { value: 410, name: "周天" },
        ]
      },
      {
        type: 'line',
        name: '成交客户',
        data: [
          { value: 320, name: "周一" },
          { value: 332, name: "周二" },
          { value: 301, name: "周三" },
          { value: 334, name: "周四" },
          { value: 390, name: "周五" },
          { value: 330, name: "周六" },
          { value: 320, name: "周天" },
        ]
      },
      {
        type: 'bar',
        name: '维护客户',
        data: [
          { value: 820, name: "周一" },
          { value: 932, name: "周二" },
          { value: 901, name: "周三" },
          { value: 934, name: "周四" },
          { value: 1290, name: "周五" },
          { value: 1330, name: "周六" },
          { value: 1320, name: "周天" },
        ]
      },
    ],
  }
  return new Promise(resolve => {
    resolve(mockData)
  })
}

6.效果展示

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值