• 具体项目下解决Echarts多端同步开发和维护的问题


    具体问题场景

            PC端和移动端需要同时上线图表功能(没有多余工时)

            之后的版本迭代(功能、样式、配置等)默认双端同步,开发人员只希望维护一套代码

            Echarts在移动端有部分功能不兼容不支持

             

    Echarts在移动端的坑

            ① 移动端页面使用echarts4 中的地图组件,并添加省份的点击事件,响应click无效,eharts也不支持tap事件。

            解决方法:自己代理echarts组件实例的click事件。或更新到echarts5版本

            ②地图组件有数据的省份高亮状态点击后消失。

            解决方法:劫持点击事件做判断

            ③dataZoom失效

    1. dataZoom:{
    2. type: 'inside',
    3. start: 0,
    4. end: 50,
    5. },

            解决方法:把传入的对象参数改成数组

    1. dataZoom:[
    2. {
    3. type: 'inside',
    4. start: 0,
    5. end: 50,
    6. }
    7. ],

            ④ 图表组件的datazoom会阻碍页面的原生滑动事件,导致页面没办法正确上下滑。

            解决方法:添加preventDefaultMouseMove属性为false

            ⑤datazoom为inside时,多个图表在移动端上滑动失效

            解决方法:更新到最新版本echarts,但是还是会有部分机型存在这个问题

    多端合一是比较理想的解决方案

            我们可以看到Echarts在移动端上还是存在很多不兼容的地方。而且Echarts官网时挂着的example都是PC端上的。为了避免各种坑爹问题,我在项目中还是选择了多端为一端的开发方案。

            核心思想就是通过Iframe让移动端的页面直接渲染PC的网页,同时微调一些样式以适配移动端的小屏。

    图表部分

            这部分不是重点,因为页面用的还是PC端的页面。只需要调整部分样式大小就好。主要解决一个留存问题就是Iframe里面图表的内部滑动会影响移动端的页面滑动。

    1. <mobileTouchView @touchInfo="updateTouchInfo" :touchRecord="true">
    2. <...>
    3. <m-dashboard-runtime-item
    4. v-for="item in layout"
    5. :key="item.pkId"
    6. :layout="item"
    7. :field="fieldMap[item.pkId]"
    8. />
    9. mobileTouchView>

            解决方法是套了个自定义的滑动层,并监听会出问题的几个操作

    1. <template>
    2. <div
    3. :class="$style.mobileTouchView"
    4. @touchstart="proxyStart"
    5. @touchmove="proxyMove"
    6. @touchend="proxyEnd"
    7. @touchcancel="proxyCancel"
    8. >
    9. <slot>slot>
    10. div>
    11. template>

            核心思想是计算touch起点和终点的screenY/screenX的偏离来确定用户手势。具体可以看我的另外一篇推文。

    通讯部分  

            代码分为两部分

     移动端部分

            主体

    1. class="dashboard-page">
    2. ....
    3. <view class="content" :class="{ showFilter: filterFields.length > 0 }">
    4. <iframe
    5. v-if="iframeUrl"
    6. ref="iframe"
    7. class="webview"
    8. :src="iframeUrl"
    9. >iframe>
    10. <x-abnormal v-else :text="tips" class="tips" />
    11. view>

            很简单的一个移动端页面中间嵌套了一个iframe页面

            监听加载

    1. async getFormData() {
    2. ....
    3. await this.$nextTick();
    4. this.$refs.iframe &&
    5. this.$refs.iframe.addEventListener('load', e => this.handleIframeLoad(e));
    6. }

            发送讯息

            同时监听PC端发过来的讯息

    1. // iframe加载完成
    2. handleIframeLoad(e) {
    3. // 先打开对PC讯息的监听器
    4. window.addEventListener('message', this.messageGateway);
    5. // 对PC建立握手
    6. this.handShake(5);
    7. }

            这里为什么要握手五次?其实这里可以填大一点。因为单方无法知道连接是否成功。 所以每500毫秒重新握手一次,直到收到回复。

            握手

    1. handShake(t = 0) {
    2. if (this.connected || t < 1) {
    3. return;
    4. }
    5. // console.log('mobile: 开始建立握手');
    6. this.$refs.iframe.contentWindow.postMessage({
    7. type: 'ping',
    8. data: {timeStamp:this.currentTime},
    9. }, '*');
    10. setTimeout(() => {
    11. this.handShake((t -= 1));
    12. }, 500);
    13. }

           收到回复后把this.connected改成true就好了

             

     Pc部分

            Iframe通讯

             PC上通过监听message来捕抓移动端发送过来的讯息

    1. created() {
    2. window.addEventListener('message', e => this.messageGateway(e));
    3. }

            这里可以过滤一下域名:

    1. get allowOrigin() {
    2. return ['localhost:8080', 'm.xxx.com', 'mobile.xxx.com'];
    3. }
    4. messageGateway(e) {
    5. const findIndex = this.allowOrigin.findIndex(item =>
    6. e.origin.includes(item),
    7. );
    8. if (findIndex > -1) {
    9. ...
    10. }
    11. }

    用户权限问题

            在移动端打开PC端的Iframe页面,需要传入token来验证登录状态和身份权限。

    1. get iframeUrl() {
    2. return `${createModuleUrl('app')}/m-dashboard/${this.formId}?token=${
    3. this.token
    4. }`;
    5. }

            iframe页面验证token后通过路由跳转到页面

    1. const routes = [
    2. ...,
    3. {
    4. path: '/m-dashboard/:formId',
    5. component: () => import('@/views/dashboard/mobile')
    6. },
    7. ]

     

  • 相关阅读:
    微服务架构的外部 API 集成模式
    全球产业链:智能驾驶产业链
    吴恩达《机器学习》8-7:多元分类
    R语言使用table1包绘制(生成)三线表、使用双变量分列构建三线表、双变量分列三线表、自定义调换双变量的顺序从不同角度分析查看
    IMAGEBIND: One Embedding Space To Bind Them All论文笔记
    window 7 安装VC-redist.x64.exe的问题
    华为obs上传下载-Java版 2023-11-23
    【等保资料】等级保护定级指南及网络安全解读(ppt原件)
    Briefings in bioinformatics2022 | Knowledge-based BERT+:像计算化学家一样提取分子性质的方法
    shell_56.Linux永久重定向
  • 原文地址:https://blog.csdn.net/weixin_42274805/article/details/132942239