公司的uniapp项目有一个专门打开网页的功能,uniapp通过webview去打开对应的url,然后通过监听webview网页发送过来的事件,在uniapp手机端打开手机的扫码功能,然后将扫码识别到的结果传回给网页。
思路
1.网页引入uni.webview.js文件
2.网页在某个时机或者某个事件发送事件
3.uniapp端监听处理事件,调用手机摄像头
4.uniapp将扫码结果传回
5.网页接收处理数据
1.网页引入uni.webview.js文件
因为网页端需要向app发送事件,所以需要引入对应的webview.js文件。这是基础。
如果项目会运行在内网环境,最好是引用已经下载好了的。
假如使用的是vue项目,则可以在index.html文件中去引入。
2.网页在某个时机或者某个事件发送事件
如果需要在网页打开的时候就去调用,则需要监听uni是否可以安全调用
如果是通过点击事件去触发,一般来说按钮加载出来到可以交互,已经加载完成了。
直接使用uni.postMessage方法就好。最主要就是定义type事件的类型,这样在uniapp中可以根据对应的type值进行不同的处理逻辑。
3.uniapp端监听处理事件,调用手机摄像头
添加web-view组件,定义方法接收传递过来的信息。@message处理信息。
然后根据type类型处理不同的逻辑,示例中专门处理type值为scanCode时候,就打开摄像头。
4.uniapp将扫码结果传回
这个是比较重要的,原理就是:通过拿到webview的内部对象,去调用系统的evalJS方法,将该方法内部的字符串当做代码去执行。示例中qrCodeWv是在初始化的时候拿到的。
webview网页内容里面的话,要定义一个全局的appScanCodeResult方法 。如果没有定义,webview网页会报错找不到这个方法。evalJS方法会把里面的内容当做代码来处理,所以方法的参数如果是对象要使用JSON.stringify处理一下,然后引号包裹起来。
5.网页接收处理数据
网页是vue框架的话,最重要的就是如何将app执行的全局方法告诉对应的页面或者组件。所以要使用window的自定义事件CustomEvent。
本来CustomEvent方法是可以传递参数的,但是监听这个事件的时候,接收到的是一个event没有带值。所以干脆就当一个触发,将app传过来的值存储在全局的window上。
vue3的写法,注册监听,离开的时候注销就好。
拿到扫描结果