【踩坑记录】app嵌h5相关

需求:在正式与客户对接之前,老板要求先自己写一个demo来熟练流程

选型:以前没做过app,工作中使用uniapp写小程序和h5较多。故使用uniapp来写

a.app中

1.主页面

这里没有使用webview标签,用的是plus.webview.create方法(webview标签遇到问题,具体什么问题已经想不起来了,一两周前的事了)

//onload中
let _this = this
wv=plus.webview.create(`https:/xxxxxxxx.com/#channel=App&invite=${this.invite}&token=${this.token}`,"webview-1",{top:uni.getSystemInfoSync().statusBarHeight, //放置在titleNView下方。如果还想在webview上方加个地址栏的什么的,可以继续降低TOP值
	height: uni.getSystemInfoSync().windowHeight -uni.getSystemInfoSync().statusBarHeight
})
var currentWebview = this.$scope.$getAppWebview(); //此对象相当于html5plus里的plus.webview.currentWebview()。在uni-app里vue页面直接使用plus.webview.currentWebview()无效
currentWebview.append(wv);//一定要append到当前的页面里!!!才能跟随当前页面一起做动画,一起关闭

plus.globalEvent.addEventListener('plusMessage', function(msg) {
	let data = msg.data.args.data.arg
	console.log('--收到h5的消息-:',JSON.stringify(data));
	if(data){
		switch(data.type) {
			case 'outApp':
			// 此时是需求是退出app
            //app监听页面返回事件通知h5返回,h5中在首页时还返回就通知app退出
				_this.back()
				break;
			case 'toService':
			// 此时需求是从h5界面进入一个新的webview
			console.log('h5界面进入一个新的webview')
				uni.navigateTo({
					url:'/subpages/onLine_service/onLine_service'
				})
				reak;
			case 'toPayMiniProgram':
			// 从app跳入支付小程序
			console.log('跳往支付小程序',JSON.stringify(data.orderInfo))
			try{
                //sweixin的获取在下面
				_this.sweixin.launchMiniProgram({
					id: 'gh_xxxxxxxxxx',//原始id(不是appid),在微信公众平台-设置-基本设置
					path: 'subpages/pay/pay?order=' + data.orderInfo,
					type: 2//0:正式版,1:测试版,2:体验版
				})
			}catch(err){
				console.log(JSON.stringify('err',err));
			}
		    break;
		}
	}
});
this.getPlus()

此时在app中返回时直接显示的是再划一次退出app,而不是h5返回上一级页面。需要监听页面返回,通知h5返回上一个页面

//与onload同级
onBackPress(e) {
    console.log('app监听到页面返回')
    var pages = getCurrentPages()
    var page = pages[pages.length - 1]
    var currentWebview = page.$getAppWebview()
    currentWebview.children()[0].evalJS('window.myHistory()')//调用h5的页面返回函数
    return true; // 返回true 表示不执行返回键默认操作
},

methods中定义的一些方法

getPlus() {
//获取当前显示的webview
var pages = getCurrentPages()
var page = pages[pages.length - 1]
var currentWebview = page.$getAppWebview()
//调用H5+APP的扩展API
var shares=null;
let that = this
var pusher = plus.share.getServices(function(s){
    shares={};
    for(var i in s){
        var t=s[i];
        shares[t.id]=t;
    }
    that.sweixin=shares['weixin'];
}, function(e){
    console.log("获取分享服务列表失败:"+e.message);
});
//放入当前的webview
currentWebview.append(pusher);
},
//.................................................
// 退出app。demo到这里改退出app了,如果只是退出webview的话调各自的关闭webview的方法
back() {
	if(this.startTime == 0){
		plus.nativeUI.toast('再按一次退出应用',2000)
		this.startTime = new Date().getTime()
		setTimeout(()=>{
			this.startTime = 0
		},2000)
	}else if(new Date().getTime() - this.startTime < 2000){
		// 两次返回间隔小于2000毫秒,退出应用
		plus.runtime.quit();
	}
},

2.副webview入口

h5中打开一个新的网页,如果有端的webview支持webview嵌套的话,就不需要了

代码和主webview差不多,只是不用监听plusMessage事件获得h5传递的消息和监听页面返回事件通知h5返回

3.小程序中支付完成后,返回app,给h5传参

//app的app.vue中的onshow中
let params = plus.runtime.arguments
	if(params != ''){
		try{
			// 获取小程序支付完成后退回app时传递的参数
			let type = params.split('&')[0].split('=')[1]
			let data = params.split('&')[1].split('=')[1]
			// console.log(JSON.stringify(type + '---' + data));
			let pages = getCurrentPages()
			let page = pages[pages.length - 1]
			let currentWebview = page.$getAppWebview()
			if(type == 'payBack'){
				// 支付完成返回
				// uni.setStorageSync('payBackData',data)
                //调用h5中的一个方法来通知h5支付完成返回,可传参
				currentWebview.children()[0].evalJS(`window.myPayBackData(${JSON.stringify(data)})`)
			}else if(type == 'nopayBack'){
				// 未支付返回
                //调用h5中的一个方法来通知h5未支付返回,可传参
				currentWebview.children()[0].evalJS(`window.myNopayBackData(${JSON.stringify(data)})`)
			}
			// 清除数据
			plus.runtime.arguments = ''
		}catch(e){}
	}

b.h5中

支付时通知app跳转的方法

uni.webView.postMessage({
	data:{
		type:'toPayMiniProgram',
		orderInfo:JSON.stringify(data)
	}
})

收到app通知返回上一页的方法

//h5的app.vue的mounted里
//
window.myHistory = () => {
	console.log('h5中的myHistory方法执行');
	var path = this.$route.path//当前页面
	if(path.indexOf('/pages/index/index') != -1 || path.indexOf('/pages/first/first') != -1 || path.indexOf('/pages/movie/movie') != -1){
             window.AndroidView.getWaPiaoMessage(JSON.stringify({type:'outApp',dataName:'',data:'',}))
		console.log('此时在首页,点击退出两次就退出app');
	}else{
		// 此时不在首页,点击物理按键的返回时,h5返回一级
		uni.navigateBack({delta:1})
	}
}

接受支付成功返回和未支付返回的方法页上面一样,只需把方法名和app调的方法名一致即可

c.实际对接时

和客户实际对接时才发现客户app用的是安卓原生还有ios端。上面的通信方法他收不到QAQ

可我app这也是第一次写啊,用uniapp写的时候还是一步一坑、一坑就得网上疯狂找解决方法。找安卓原生怎么和webview通信出来的全是安卓原生的写法,看不懂啊啊啊啊!

最后老板花了300大洋找人问,给的代码如下:

window.AndroidView.xxxxxxxMessage()

xxxxxxxMessage是需要安卓app暴露出来的方法。我们来调

不过这钱没白花,别看代码少。对接的时候客户的安卓开发人员不知道怎么写,又给了一个demo。

客户的人还不成功,问我AndroidView是什么。这我也不懂,就问300大洋,给回了一个是标签。又把他也拉到对接群里面作为我方的安卓技术支持,教客户的人

我听起来AndroidView和xxxxxxxMessage都是需要app来定义的

ios的代码是客户的ios开发人员给的

window.webkit.messageHandlers.xxxxxxxMessage.postMessag()

xxxxxxxMessage是需要iosapp暴露出来的方法。我们来调

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值