小程序页面onLoad时redirectTo其它页面,如何优雅的阻止onShow执行?
携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第27天,点击查看活动详情。
背景
有时候,我们需要在小程序的onLoad
生命周期做一些校验,若校验不通过,则wx.redirectTo
其它页面。
但是,如果直接在onLoad
里面执行wx.redirectTo
,那么小程序还是会执行完本页面的onShow
和onUnload
,才会关闭本页面。
其实大部分时候,如果你马上要切走页面了,onShow
和onUnload
没必要执行,执行太多只会影响你页面切换的速度,而且一些场景下还会引入Bug。
所以,我们需要一种优雅的方式,阻止onShow
和onUnload
执行。
一种解决方案
在本页面设置一个变量:preventOnShow
,默认为false,如果需要阻止onShow
,就设置为true。在onShow
逻辑中,优先判断preventOnShow
,如果为true,就直接return。注意preventOnShow
不要放在data里面,因为它不需要渲染,更新它时不影响wxml。
代码如下:
Page(
data: {},
preventOnShow: false,
onLoad(options) {
// 如果发生特殊情况,就直接redirectTo其它页面
if (...) {
this.preventOnShow = true;
wx.redirectTo({ url: '...' });
return;
}
// ... 其它onLoad逻辑
},
onShow() {
if (this.preventOnShow) return;
// ... 其它onShow逻辑
},
);
更优雅的解决方案
为什么需要更优雅的解决方案?
因为上面的解决方案还不够好。我们需要在每个页面都加这样的重复逻辑:
Page(
preventOnShow: false,
onShow() {
if (this.preventOnShow) return;
// ... 其它onShow逻辑
},
);
一旦某个页面忘记加,那么preventOnShow
就失效了。
因此,我们最好通过某种方式一次性全局加上这种逻辑,避免开发者新建某页面时忘记,减少了出错率。这体现了工程化的思想。
具体怎么做?参考文章:《如何全局重写小程序 Page函数 wx对象?》。
function onShowProxy(onShow) {
return function newOnShow() {
if (this.preventOnShow) return;
if (onShow) {
return onShow.call(this);
}
};
}
function pageProxy(Page: WechatMiniprogram.Page.Constructor): WechatMiniprogram.Page.Constructor {
return function newPage(options) {
Page({
...options,
preventOnShow: false,
onShow: onShowProxy(options.onShow),
});
};
}
Page = pageProxy(Page);
以上逻辑,在app.js
中引入即可。
这样,我们就一次性给所有页面加上了preventOnShow
属性,通过给它赋值true,即可跳过执行onShow
。
写在最后
我是HullQin,公众号线下聚会游戏的作者(欢迎关注公众号,联系我,交个朋友),转发本文前需获得作者HullQin授权。我独立开发了《联机桌游合集》,是个网页,可以很方便的跟朋友联机玩斗地主、五子棋等游戏,不收费无广告。还独立开发了《合成大西瓜重制版》。还开发了《Dice Crush》参加Game Jam 2022。喜欢可以关注我噢~我有空了会分享做游戏的相关技术,会在这2个专栏里分享:《教你做小游戏》、《极致用户体验》。
转载自:https://juejin.cn/post/7136586065086775309