2020.09.07 上周调试还是好的,这周就报错了
场景:用户点击按钮,弹出地理位置授权,用户拒绝。然后用户再次点击按钮,调动wx.openSetting弹出设置页面授权。如果这个接口不能调起设置页面的话
一开始在程序中Promise 的来处理回调,报错:openSetting:fail can only be invoked by user TAP gesture. (官方回答:不能使用promise的方式去处理回调,需要改成直接普通的回调方式, promise是异步的,“点击行为允许调用”这个机制要求是同步的)
open-type:
bindopensetting eventhandle 否 在打开授权设置页后回调,open-type=openSetting时有效
现在这个回调已经不能openSetting了
以下方式是以前的写法,直接在 uni.showModal中调起 uni.openSetting,已无效,需要废弃
export function getAuth(options) {
options = Object.assign({
auth: '',
title: '',
content: '',
showModal: true
}, options);
return new Promise((resolve, reject) => {
uni.getSetting({
success: res => {
console.log('1-sucess', res);
if (typeof res.authSetting[options.auth] === 'undefined') {
// 首次授权
resolve();
} else if (!res.authSetting[options.auth]) {
if (options.showModal) {
uni.showModal({
title: options.title,
content: options.content,
success: res => {
if (res.confirm) {
uni.openSetting({
success: res => {
if (res.authSetting[options.auth]) {
// 同意授权成功
resolve();
} else {
console.log('1-3');
reject();
}
},
fail: res => {
console.log('openSetting-fail', res);
}
});
} else {
console.log('2-3');
reject();
}
},
fail: reject
});
} else {
console.log('3-3');
reject();
}
} else {
// 已授权过
console.log('已授权过');
resolve();
}
},
fail: reject
});
});
}
解决:
需要自己写一个showModal的组件,进行判断
LmModalAlert自定义showModal组件
<template>
<u-modal v-model="show"
:title="title"
:title-style="titleStyle"
:show-confirm-button="isShowConfirmbtn"
:show-cancel-button="isShowCancelbtn"
:confirm-text="confirmText"
:confirm-color="confirmColor"
:cancel-text="cancelText"
:cancel-color="cancelColor"
@confirm="confirm"
@cancel="cancel"
>
<view class="modal_slot_content">
<rich-text :nodes="content"></rich-text>
<slot name='login_slot_btn'></slot>
</view>
</u-modal>
</template>
<script>
export default {
name:'LmModalAlert',
props:{
isShow:{
type:Boolean,
default:false
},
title:{
type:String,
default:''
},
titleStyle:{
type:Object,
default:{
color: '#000000',
fontSize:'18px',
padding: '56rpx 48rpx 0 48rpx',
overflow: 'initial',
whiteSpace: 'normal'
}
},
content:{ //传入的只必须是div
type:[String,Array],
default:``
},
isShowCancelbtn:{
type:Boolean,
default:true
},
cancelText:{
type:String,
default:'取消'
},
cancelColor:{
type:String,
default:'#000000'
},
isShowConfirmbtn:{
type:Boolean,
default:true
},
confirmText:{
type:String,
default:'确定'
},
confirmColor:{
type:String,
default:'#3F98FF'
},
},
computed: {
show:{
get: function () {
return this.isShow
},
set:function (val) {
this.$emit('cancel')
},
},
},
methods: {
confirm() {
console.log('confirm');
this.$emit('confirm')
},
cancel(){
console.log('cancel');
this.$emit('cancel')
}
}
}
</script>
<style lang="scss">
.modal_slot_content{
color: $text_color8;
@include fontSize(36);
text-align: center;
}
.m_slot_center{
padding: 26rpx 48rpx 48rpx 48rpx;
}
.modal_record_conent{
color: $black_color;
margin: 0 auto;
padding: 26rpx 48rpx 48rpx 48rpx;
text-align: left;
}
</style>
LmOpenSettingAlert自定义OpenSetting组件
<template>
<LmModalAlert :is-show="isShow"
:title="title"
:isShowCancelbtn="false"
:isShowConfirmbtn="false"
:content="content" @cancel="handleCancel">
<template v-slot:login_slot_btn>
<view class="open_setting_btn">
<button class="cancle_btn" hover-class="none" @click="handleCancel">取消</button>
<view class="line"></view>
<button class="confirm_btn" hover-class="none" open-type="openSetting" @opensetting="handleOpenSetting"> 确定 </button>
</view>
</template>
</LmModalAlert>
</template>
<script>
import LmModalAlert from '@/ownComponents/lm-modal-alert/index.vue'
export default {
name:'LmOpenSettingAlert',
components: {
LmModalAlert,
},
props:['isShow','title','content'],
methods: {
handleCancel(){
this.$emit('cancel')
},
handleOpenSetting(e){
this.$emit('opensetting',e)
}
}
}
</script>
页面中调用组件
//引用组件
<lm-opensetting-alert
:isShow="openSetting"
:title="grantSetting.title"
:content="grantSetting.content"
@cancel="openSetting=false"
@opensetting="handleOpenSetting"
></lm-opensetting-alert>
//组件逻辑处理
export default {
data() {
return {
openSetting: false,
}
},
methods:{
//获取微信运动
handleWeRunLogin() {
let self = this;
if ( this.weRunSetting ) {
uni.navigateTo( {
url: '/pages/sport/index'
} );
} else {
this.$getAuth.authIsSetting( { auth: 'scope.werun' } ).then( ( res ) => {
if ( res.code == 1 || res.code == 2 ) {
self.getWeRun( '需要loading' );
} else {
self.openSetting = true
self.grantSetting = {
auth: 'scope.werun',
title: "\"打卡小助手\"需要获取您的微信运动步数",
content: '<div class="m_slot_center">将用于小程序每日运动的效果展示</div>',
}
}
} );
}
},
//调起OpenSetting
handleOpenSetting( e ) {
let self = this;
let { auth } = self.grantSetting
if ( e.detail.authSetting[ auth ] ) {
console.log( '同意授权成功' );
if ( auth == "scope.userLocation" ) {
self.getLocation()
} else if ( auth == "scope.werun" ) {
self.getWeRun( '需要loading' )
}
this.openSetting = false;
} else {
console.log( '不同意授权' );
if ( auth == "scope.werun" ) {
self.setIsWeRun( false )
}
}
},
}
}
uni.getSetting方法
/*
* 校验是否开启了授权获取权限
* alertAuthoried 如果是用户禁止了定位,是否弹出进入设置页面的弹框
* callback 授权完成状态 1 授权成功 2未声明是否允许 3拒绝授权
*/
export function authIsSetting(options) {
options = Object.assign({
auth: '',
}, options);
return new Promise((resolve, reject)=>{
uni.getSetting({
success: res => {
// console.log('1-sucess', res, res.authSetting[options.auth]);
if (typeof res.authSetting[options.auth] === 'undefined') {
// 首次授权
console.log('首次授权');
resolve({ code: 1, auth: res.authSetting[options.auth] });
} else if(!res.authSetting[options.auth]) {
console.log('未授权');
resolve({ code: 3, auth: res.authSetting[options.auth] });
} else {
// 已授权过
console.log('已授权过');
resolve({ code: 2, auth: res.authSetting[options.auth] });
}
},
fail: (reject)=>{
// console.log('reject', reject);
},
complete:(res)=>{
// console.log('complete', res);
}
});
})
}