在混合开发中,如果原生app没有提供监听app回滚事件的方法,那么H5并不知道app已经回滚了,但是有时候我们需要监听页面的回滚,并做相应的处理。比如在产品支付页面,输入支付密码就是类似微信支付的弹窗。打开弹窗后,用户准备输入支付密码,但此时用户不想支付,用户会触发应用返回并关闭。这个弹窗,如下视频所示:如果H5不监听屏蔽,那么用户的动作就变成返回上一页1.实现原理实现原理:监听历史的变化。history.state增加了一个新的状态实现步骤:在页面初始化后监听popstate事件,并在该事件中进行业务处理letoriginState=history.state.current;//存储原始状态letonPopstate=function(e){console.log('监听页面上的动作',e.state,originState);if(e.state&&(e.state.current===originState||e.state.target===originState)){//这里可以进行业务处理,比如关闭弹窗,提示userforunprocessedthings,etc.}};//监听popstate事件window.addEventListener("popstate",onPopstate,false);注意:这里需要存储页面进来时的history.state,当页面回滚时,可以知道当前页面回滚,弹窗打开时,在hostory.state中添加一个新的state让changeHistoryState=function(){//这里只需要添加一个原始状态,之前添加的`popstate`事件处理函数就可以正确处理window.history.pushState({target:originState,random:Math.random()},"",location.href);};H5主动关闭弹窗h5在主动关闭弹窗时需要调用window.history.back()回到之前的状态。否则,当用户想要返回上一页时,需要触发两次应用才能返回上一页。2.代码实现useListenerAppBack.jsimport{onUnmounted}from'vue';/***监听原生app返回事件,防止返回上一页*/exportfunctionuseListenerAppBack(onAppBack){letappBack=function(){window.history.back();};让appForward=function(){window.history.forward();};让appGo=function(delta){window.history.go(delta);};if(!window.history.pushState){return{appBack,appForward,appGo,changeHistoryState(){console.warn('浏览器不支持pushState!');}};}让originState=history.state.current;//存储原始状态//letstatePushed=false;letchangeHistoryState=function(){//只需要在这里添加另一个原始状态window.history.pushState({target:originState,random:Math.random()},"",location.href);};letonPopstate=function(e){console.log('监听页面上的动作',e.state,originState);如果(e.state&&(e.state.current===originState||e.state.target===originState)){onAppBack(e.state);}};//监听popstate事件window.addEventListener("popstate",onPopstate,false);onUnmounted(function(){console.log('shiftRemovepopstateeventlistener');//移除popstate事件监听window.removeEventListener("popstate",onPopstate,false);});返回{appBack,appForward,appGo,changeHistoryState};};用于业务代码,支付。vue:
