解决问题:app弹出popup框弹出后 用户使用全面屏手势/虚拟按键返回 关闭弹窗阻止页面跳转 可以跨越层级进行关闭弹窗
优点:监听页面返回 如果有弹窗则先关闭弹窗阻止页面返回 可跨越层级进行监听 只需要定义在路由页面即可
缺点:1.监听页面必须是路由页面(目前试下来是这样 封装的组件是无法使用 onBackPress 来监听的);2.如果当前路由没办法进行返回了 则监听失效 将会进入 再按一次退出应用
区分是父组件 还是子组件还是孙组件
如果定义在父组件(路由页面)中 可以直接使用 如果是子组件或孙组件以上 需要加入vuex来进行动态记录数据(避免页面改动过大所以采用此方案)
data() {
...
},
onBackPress() {
if (this.hidepop()) {
return true; // 此处返回 true 表示阻止页面跳转或关闭
}
},
mounted() {
....
},
methods: {
hidepop() {
const store = this.$store;
if (store.getters.getPoint) { // 记录的vuex的数据 如果获取的是 true 也就是当前子组件/孙组件 弹窗出于打开状态
store.commit("setPoint", false); // 关闭弹窗页面
} else if (this.showPdf) { // 如果是父组件(当前路由页面) 可以直接进行判断
this.showPdf = false;
} else {
return false;
}
return true;
},
}
const routerPop = {
state: {
showPoint: false, // 子组件/孙组件控制弹窗显示变量
},
mutations: {
setPoint(state, payload) {
state.showPoint = payload;
},
},
getters: {
getPoint(state) {
return state.showPoint;
},
},
actions: {},
};
export default routerPop;
孙组件页面
data() {
...
},
computed: {
showPoint() { // 这个可以当做 data里面的值使用
return this.$store.getters.getPoint; // 此处使用 computed 方法进行定义变量 目的是因为变动后会有响应式
},
},
// 打开弹窗
handleOpen() {
this.$store.commit("setPoint", true);
},
// 关闭弹窗
handleClose() {
this.$store.commit("setPoint", false);
},
// TIPS:注意 如果子组件/孙组件是进行循环渲染或弹窗需要唯一 则只需要监听一个变量即可 避免进行多个弹窗进行同时展开
watch: {
showPoint(newValue) {
this.showPopup = newValue
}
}
注:如果使用了 uni-simple-router
需要在配置文件更改以下:
如不更改会导致 第一次监听使用成功 第二次无法返回问题
const backInfo = {
number: 1,
};
const router = createRouter({
platform: process.env.VUE_APP_PLATFORM,
detectBeforeLock: () => {
router.$lockStatus = false; // 需要更改此处 防止出现第一次使用成功 第二次无法返回问题
},
routerErrorEach: (error, router) => {
if (error.type === 3) {
// #ifdef APP-PLUS
if (backInfo.number > 1) {
plus.runtime.quit();
} else {
// 这里可以进行判断 vuex里面的变量 是否为关闭状态 进行关闭 可以不提醒再按一次退出应用
backInfo.number += 1;
plus.nativeUI.toast("再按一次退出应用");
}
setTimeout(function () {
backInfo.number = 1;
}, 1000);
// #endif
}
},
routes: [...modules],
});