微信小程序webview与h5通过postMessage实现实时通讯的实现
文章转自:https://www.jb51.net/article/167957.htm
这篇文章主要介绍了微信小程序webview与h5通过postMessage实现实时通讯的实现,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
在做 React Native 应用时,如果需要在 App 里面内嵌 H5 页面,那么 H5 与 App 之间可以通过 Webview 的 PostMessage 功能实现实时的通讯,但是在小程序里面,虽然也提供了一个 webview 组件,但是,在进行 postMessage 通讯时,官方文档里面给出了一条很变态的说明:
网页向小程序 postMessage 时,会在特定时机(小程序后退、组件销毁、分享)触发并收到消息。e.detail = { data },data 是多次 postMessage 的参数组成的数组
这里面已经说的很明白了,不管我们从 H5 页面里面 postMessage 多少次,小程序都是收不到的,除非:
- 用户做了回退到上一页的操作
- 组件销毁
- 用户点击了分享
这里面其实我没有完全说对,官方其实说的是 小程序后退,并没有说是用户做回退操作,经过我的实测,确实人家表达得很清楚了,我们通过微信官方的SDK调起的回退也是完全可行的:
1 |
|
大体思路
从上面的分析和实测中我们可以知道,要实现无需要用户操作即可完成的通讯,第三种情况我们是完全不需要考虑了的,那么来仔细考虑第 1 和第 2 种场景。
第 1 种方式:回退
当我们想通过网页向小程序发送数据,同时还可以回退到上一个页面时,我们可以在 wx.miniProgram.postMessage 之后,立马调用一次 wx.miniProgram.navigateBack(),此时小程序的操作是:
- 处理 postMessage 信息
- 回退到上一页
我们在处理 postMessage 的时候做一些特殊操作,可以将这些数据保存下来
第 2 种方式:组件销毁
这是我感觉最合适的一种方式,可以让小程序拿到数据,同时还保留在当前页面,只需要销毁一次 webview 即可,大概的流程就是:
- 小程序 postMessage
- 小程序 navigateTo 将小程序页面导向一个特殊的页面
- 小程序的那个特殊页面立马回退到 webview 所在的页面
- webview 所在的页面的 onShow 里面,做一次处理,将 webview 销毁,然后再次打开
- 触发 onMessage 拿到数据
- H5 页面再次被打开
这种方式虽然变态,但是至少可以做到实时拿到数据,同时还保留在当前 H5 页面,唯一需要解决的是,在做这整套操作前,H5 页面需要做好状态的缓存,要不然,再次打开之后,H5 的数据就清空了。
第 1 种方式:通过回退,将数据提交给小程序之后传递给 webview 的上一页面
这种方式实现起来其实是很简单的,我们现在新建两个页面:
sandbox/canvas-by-webapp/index.js
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 |
|
上面的代码中,核心点,就在于 wx.navigateTo 调用时,里面的 events 参数,这是用来进行与 /apps/browser/index 页面通讯,接收数据用的。
apps/browser/index.js
我省略了绝大多数与本文无关的代码,保存最主要的三个:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 |
|
其实,onLoad 方法中,我们使用了自微信 SDK 2.7.3 版本开始提供的 getOpenerEventChannel 方法,它可以创建一个与上一个页面的事件通讯通道,这个我们会在 handleMessage 中使用。
handlePostMessage 就是被 bindmessage 至 webview 上面的方法,它用于处理从 H5 页面中 postMessage 过来的消息,由于小程序是将多次 postMessage 的消息放在一起发送过来的,所以,与其它的Webview不同点在于,我们拿到的是一个数组: e.detail.data, handlePostMessage 的作用就是遍历这个数组,取出每一条消息,然后交由 handleMessage 处理。
handleMessage 在拿到 message 对象之后,将 message.action 与 message.data 取出来(*这里需要注意,这是我们在 H5 里面的设计的一种数据结构,你完全可以在自己的项目中设计自己的结构),根据 action 作不同的操作,我在这里面的处理是,当 action === 'postData' 时,就通过 getOpenerEventChannel 得到的消息通道 this.eventChannel 将数据推送给上一级页面,也就是 /sandbox/canvas-by-webapp,但是不需要自己执行 navigateBack ,因为这个需要交由 H5 页面去执行。
H5 页面的实现
我的 H5 主要就是使用 html2canvas 库生成 Canvas 图(没办法,自己在小程序里面画太麻烦了),但是这个不在本文讨论过程中,我们就当是已经生成了 canvas 图片了,将其转为 base64 文本了,然后像下面这样做:
1 2 3 4 5 6 7 8 |
|
将数据 postMessage 之后,立即 navigateBack() ,来触发一次回退,也就触发了 bindmessage 事件。
使用销毁 webview 实现实时通讯
接下来,咱就开始本文的重点了,比较变态的方式,但是也没想到更好的办法,所以,大家将就着交流吧。
H5 页面的改变
1 2 3 4 5 6 7 8 |
|
H5 页面只是将 wx.miniProgram.navigateBack() 改成了 wx.miniProgram.navigateTo('/apps/browser/placeholder') ,其它的事情就先都交由小程序处理了。
/apps/browser/placeholder
这个页面的功能其实很简单,当打开它了之后,做一点点小操作,立马回退到上一个页面(就是 webview 所在的页面。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
|
我们一行一行来看:
1 |
|
这个可以拿到当前整个小程序的页面栈,由于这个页面我们只允许从小程序的 Webview 页面过来,所以,它的上一个页面一定是 webview 所在的页面:
1 |
|
拿到 webviewPage 这个页面对象之后,调用它的方法 setData 更新一个值:
1 2 3 4 5 6 7 8 |
|
shouldReattachWebview 这个值为 true 的时候,表示需要重新 attach 一次 webview,这个页面的事件现在已经做完了,回到 webview 所在的页面
apps/browser/index.js 页面
我同样只保留最核心的代码,具体的逻辑,我就直接写进代码里面了。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 |
|
对应的 index.wxml 文件内容如下:
1 |
|
流程回顾与总结
- 打开 webview 页面,打开 h5
- h5 页面生成 canvas 图,并转为 base64 字符
- 通过 wx.miniProgram.postMessage 将 base64 发送给小程序
- 调用 wx.miniProgram.navigateTo 将页面导向一个特殊页面
- 在特殊页面中,将 webview 所在页面的 shouldReattachWebview 设置为 true
- 在特殊页面中回退至 webview 所在页面
- webview 所在页面的 onShow 事件被触发
- 在 onShow 事件检测 shouldReattachWebview 是否为 true,若为 true
- 将 hideWebview 设置为 true,引起 web-view 组件的销毁
- handlePostMessage 被触发,解析所有的 message 之后交给 handleMessage 逐条处理
- handleMessage 发现 action === 'saveCanvas' 的事件,拿到 data
- 根据 data 计算 checksum ,以 checksum 为 key 缓存下来数据,并将这个 checksum 保存到 canvasData 对象中
- 此时 hideWebview 被 onShow 里面 setData 的回调中的 setData 重新置为 false,web-view 重新加 attach,H5页面重新加载
- webview 重新 attach 之后, this.handleCanvasData 被触发,
- handleCanvasData 检测是否有需要保存的 canvas 数据,如果有,保存,修改 canvasData 状态
整个流程看旧去很繁琐,但是写起来其实还好,这里面最主要的是需要注意,数据去重,微信的 postMessage 里面拿到的永远 都是 H5 页面从被打开到关闭的所有数据。
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持脚本之家。
微信小程序webview与h5通过postMessage实现实时通讯的实现相关推荐
- 微信小程序web-view 外部引用h5页面调用摄像头录制视频 配有提示音
微信小程序web-view 外部引用h5页面调用摄像头录制视频 配有提示音 1.目前的需求是什么 2.都踩了那些坑 1.小程序 2.h5语音提示 3.语音合成声音录制不进去,ios有时候是麦克风,有时 ...
- 微信小程序web-view与H5之间交互(含支付)
第一章 了解web-view与H5的交互(含支付) 文章目录 第一章 了解web-view与H5的交互(含支付) 前言 一.web-view是什么? 二.使用步骤 三.业务场景 1.小程序带参数跳转链 ...
- 微信小程序web-view与H5 通信方式探索
本文作者为奇舞团前端开发工程师 小程序简介 小程序是一种全新的连接用户与服务的方式,它可以在微信内被便捷地获取和传播,同时具有出色的使用体验. 需求 微信小程序 H5 混合开发就是 在一个小程序中,采 ...
- 微信里嵌入html5页面,微信小程序web-view嵌套H5实现微信支付功能解决方案
一. 产品现状 首先,在接入微信支付功能以前,我们的产品情况是这样的: 1 有公众号和app的h5站点及相关配套功能 2 小程序已经有一些基础功能,这些功能没有使用web-view 3 小程序之前的服 ...
- 微信小程序web-view嵌入h5页面,分享当前页
① index.wxml 为web-view标签添加bindload事件 web-view bindload | 微信开放文档 <web-view src="{{webview_u ...
- 微信小程序web-view嵌入h5———微信名包含emoji表情,导致数据无法存入数据库
由于部分用户微信名包含emoji表情导致无法存入数据库. 报错为:[2019-08-27 16:21:12] [ERROR] [org.hibernate.engine.jdbc.spi.SqlExc ...
- [微信小程序]WebView内嵌H5实现本地文件上传
[官方文档] 小程序与H5如何互相跳转 小程序与H5交互以上传文件为例 微信小程序开放能力web-view使用之h5页面与小程序页面交互传值 快速小程序开发之微信小程序内嵌 H5 微信小程序web-v ...
- 微信小程序webview(H5页面)调用微信小程序支付
1.业务描述:微信小程序商城入口进入的页面是商城H5页面,在H5页面进行微信支付如何实现: 2.微信小程序(webview访问H5页面)必须使用微信小程序支付: 如何实现以及实现方式以及支付后页面返回 ...
- 实现微信小程序web-view内嵌H5中的下载功能(大文件切片下载)
实现微信小程序内嵌H5中的下载功能 一.项目场景: 难点 解决方案: 1.H5微信小程序: a.首先必不可少的是安装jweixin-module模块: b.在main.js中将依赖绑定: c.H5对应 ...
最新文章
- 计算机视觉与深度学习 | 基于边缘与形态学的细胞检测
- 七牛云存储:通过SDK上传图片
- php自定义能过滤器,过滤器与自定义过滤器的介绍
- HDU 1999 不可摸数
- MySQL查询多表定义实体类_自己设计一个 JAVA + MyBatis 解析实体类多表通用查询
- bool类型数组转换成一个整数_「PHP」常用的数组键值操作函数,面试重点
- springcloud config服务端配置(二)
- 面向小姐姐的编程——java面相对象之抽象
- 在mysql支持关系模型中_MySQL支持关系模型中、和三种不同的完整性约束
- linux http 访问限制,51CTO博客-专业IT技术博客创作平台-技术成就梦想
- 五分钟带你了解什么是PID模糊算法
- HTML5前端教程:jQuery项目实战
- shoppping collection
- 计算机主板 华硕 游戏用,华硕Z390-A大师主板,带你畅享极致游戏体验-华硕主板bios设置...
- Maya火球特效制作
- 外贸出口流程全图(转)
- Educational Codeforces Round 101 (Rated for Div. 2)
- 什么是支付通道,一篇文章了解支付通道理念
- unity 3d开发的大型网络游戏
- 中基鸿业工薪家庭理财方法