先解释一下我遇到的问题:我目前在实现一个项目,应该是会发布为微信小程序。在实现登录后获取到用户头像以及用户名信息后跳转回个人页面,该页面是一个tabbar页面。就会出现一个问题,只能使用
uni.switchTab({
    url: '/pages/mine/index'
});

不能像uni.reLaunch(OBJECT) 函数,关闭所有页面,打开到应用内的某个页面。会触发页面的全部生命周期,这个时候是可以拿到修改后的最新数据。
登录页面
登录后头像数据未拿到

一.解决办法

在你需要重新获取最新数据的页面使用:

	uni.$on('update',function(data){
		console.log('监听到事件来自 update ,携带参数 msg 为:' + data.msg);
		//在这里写你需要处理的逻辑
	})

在跳回到tabbar页面,完成需要的数据更新的时候使用:

	uni.$emit('update',{msg:'页面更新'})

这个原理就是在全局的事件总线上操作数据。所以解决办法的话还可以使用Vuex等全局状态管理器。

二.实际开发例子

我在我的login登录页面
getOpenid() {
	// 调用uni.login获取登录凭证code
	uni.login({
		success: (res) => {
			if (res.code) {
				// 将code发送到后台获取openid
				uni.request({
					url: 'https://api.weixin.qq.com/sns/jscode2session',
					method: 'GET',
					data: {
						appid: config.appId,
						secret: config.secret,
						js_code: res.code,
						grant_type: 'authorization_code'
					},
					success: (response) => {
						let url = this.avatar;
						uni.showToast({
							title: '请稍等~',
							icon: 'loading',
						});
						uni.setStorage({
							key: 'userInfo',
							data: {
								openId: response.data.openid,
								avatar: this.avatar,
								name: this.nickname,
							},
							success: function() {
								uni.hideToast();
								uni.$emit('login', {
									avatar: url
								})
								uni.switchTab({
									url: '/pages/mine/index'
								});
								// goPage("/pages/mine/index",true)
							}
						});
						// 此处可以将openid存储在本地或者全局变量中
					}
				});
			} else {
				console.log('登录失败!' + res.errMsg);
			}
		}
	});
},
在需要更新用户头像数据的tabbar页面
mounted() {
	if (uni.getStorageSync('userInfo')) {
		this.avatar = uni.getStorageSync('userInfo').avatar
	}
	let this_=this; //this大坑,这里面有个坑,可能跟我的这个页面是使用了组件的影响吧,
	//在uni.$on('',fun)中fun的this指向是全局的一个VUe实例,不是指向该页面,故此给一个没有该数据的
	//data属性,会获取不到,也就无法绑定响应式数据更新。于是可以先存储一下this,然后在进行逻辑操作
	uni.$on('login', function(data) {
		//console.log(this.avatar);undefined
		this_.avatar = data.avatar
	})
	uni.$on('loginOut', function() {
		this_.avatar = ""
	})
},
//为了优化代码,可以加上移除事件,避免重复监听事件
onUnload() {
	// 移除监听事件  
	uni.$off('login');
	uni.$off('loginOut');
},
我的退出登录页面逻辑
Handle() {
	if (this.$props.url == "loginout") {
		uni.removeStorage({
			key: 'userInfo',
			success: function(res) {
				uni.$emit('loginOut')
				uni.switchTab({
					url: '/pages/mine/index'
				});
				// goPage("/pages/mine/index", true)
			}
		});
		return;
	}
}

以上就是全部的解决过程。

为啥要写这个文章呢,因为这个小小的bug改了我一个下午!!!最后是吃了一顿晚饭,然后小溜达了一会,问题解决办法突然从脑子里面崩出来,因为我打印了this.avatar发现是undefined,但是我明明在data中定义了,不应该没有值啊,所以我猜到这个this肯定有问题。于是我对每个this都进行了打印,然后查看他们身上的属性,发现this指向的果然是错了,我说我之前使用的定义全局响应式变量,或者使用vuex,mixin,或者自己定义了事件总线,然后进行操作都不好使。大概都是因为这个this指向的问题,呀,好气!!!写出这篇文章,记录一下。当然,如果能帮助到你就更好了,有用的话点一个免费的赞赞,谢谢。

Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐