数据大屏搭建与开发的秘诀

2,073 阅读4分钟

今天6月1号,希望大家怀有童心,赶走烦心,留住开心,祝愿每一个大朋友小朋友笑口常开,快乐常在。

前言

小半年没有更新文章了,最近时间比较充裕,开发了一个大屏项目,在这里系统的介绍一下自己的开发过程。

正文

2b53db9ff55d0d181bdddcfc1ccd2c8.png

一. 拆分组件

根据ui图,创建合适的目录结构,划分合理的组件,UI图分为左中右三部分,同时又有头部,所以我将组件这样拆分

image.png

index.vue 为父组件,左中右以及头部为子组件,enterprise 目录是中间地图上方的内容,由于和地图各自独立我也单独拆分为一个组件,用绝对定位放在地图上方,当中间地图区域有交互效果时只需要将上层元素加一段css代码 pointer-events: none,允许点击穿透即可。组件拆分完成,接下来针对每一部分组件单独开发。

二. 大屏适配

大屏适配方案比较多,因项目而异,我这个项目中UI是32:9的尺寸,以我的项目为例,如果屏幕尺寸固定和UI一致,直接写死宽高 如果屏幕大小不一,且仍需按照32:9的比例显示,我们做动态匹配 给外层div绑定ref

image.png

    import throttle from 'lodash.throttle';
    onMounted(() => {
      if (dataScreenRef.value) {
        dataScreenRef.value.style.transform = `scale(${getScale()}) translate(-50%, -50%) `;
        dataScreenRef.value.style.width = `${width}px`;
        dataScreenRef.value.style.height = `${height}px`;
      }
      window.addEventListener('resize', resize);
    });
    const dataScreenRef: any = ref(null);
    // 数据大屏自适应函数
    const width = 3840;
    const height = 1080;
    const getScale = (w = width, h = height) => {
      let ww = window.innerWidth / w;
      let wh = window.innerHeight / h;
      return ww < wh ? ww : wh;
    };
    /* 浏览器监听 resize 事件 */
    const resize = () => {
      if (dataScreenRef.value) {
        throttle(
          (dataScreenRef.value.style.transform = `scale(${getScale()}) translate(-50%, -50%) transform-origin: top left;`),
          200,
        );
      }
    };

三. 组件图表开发

布局和适配完成之后,进行内容开发,大屏技术栈主要应用Echarts,这里我用到了自己封装的 Echarts插件 base-echarts。

一. 使用base-echarts构建图表

用到base-echarts之后,开发效率大幅提升。

  1. 先搭完组件的整体框架,用空盒子实现区块划分

  2. 下载安装base-echarts之后,引入BaseEcharts

npm install base-echarts@latest
import { BaseEcharts } from 'base-echarts';

3. 使用

image.png 如果外层盒子,charts-box有自己的宽高,我们需要图表撑满charts-box这个盒子,BaseEcharts可以不传宽高,默认宽高100%

二. 将图表配置封装成hooks

由于一个组件中有大量图表,太多的options加上接口api,十分冗余,难以维护,为每一个组件创建一个hooks,把options集中存放

image.png

image.png

三. 接口调用

在绑定的的options函数中调用接口,将拿到的数据赋值给函数内的局部变量option,option用ref包裹,这样由于vue3响应式的特点,当接口的参数改变之后会触发函数重新赋值,省去了侦听这一步。 image.png

完成上述步骤之后,项目雏形基本实现,接下来就是根据更细致的需求做一些缝缝补补的工作。

四. 视觉动态效果

  1. 每隔5分钟图表重新渲染,目的就是要看渲染的动画效果,给人一种数据实时更新的感觉😂

思路:这么多数据不可能每隔五分钟调一遍接口,对option重新赋值,想到echarts的渲染动画应该是在setOptions这一步执行渲染的,那是不是重新执行myEcharts.setOptions(options)就可以了呢。

实现:使用base-echarts的同时执行setOptions方法,需要给BaseEcharts组件绑定ref,通过ref调用setOptions

<BaseEcharts
  :height="'167px'"
  :options="options"
  ref="opt"
  :istool="true"
  :interval="6000"
/>
<script setup>
    import {ref, onMounted}
    const opt = ref(null)
    onMounted(()=>{
        setInterval(() => {
            opt.value.setOptions(options.value)
        }, 300000)
    })
</script>

这样实现,图表一动不动。因为echarts只有在数据改变的时候才会重新渲染,而我们执行setOptions时,数据没有发生改变。 在不改变原始数据的前提下要实现我们的目的,我们可以将echarts图表清空或者将图表销毁再执行。

使用BaseEcharts清空图表需要通过 echartInstance()方法 获取图表echartInstance实例调用他上面的clear()方法,echartInstance上的具体方法可查看官网

opt.value.echartInstance().clear(); // 清空图表
opt.value.echartInstance().dispose(); // 销毁实例

这里我们使用clear即可,销毁实例还是轻易不要尝试

image.png

image.png

  1. 让 图表的 tooltip悬浮框自动播放 😎

直接配置 BaseEcharts,:istool='true' 开启轮播,“什么?速度太快”,直接配置 BaseEcharts,:interval='6000'

  1. 数字滚动效果也加一个吧 😐

推荐使用用插件,vue3-count-to

  1. antd样式自定义

自定义?真懒得动弹,翻出之前封装的一个调调的antd ui库,拿来直接用吧(这里我不推荐大家使用了,局限性很大)

npm install dw-dark-ui

import 'dw-dark-ui/dw-dark-ui/style.css';

image.png

最终呈现

20230602_170852 (1).gif

希望这篇文章能给用到的人带来帮助。