requestPermissionsFromUser后通过requestPermissionOnSetting拉起系统设置页半模态二次授权。
实践方案(以ohos.permission.CAMERA二次授权为例)
{
"name": "ohos.permission.CAMERA",
"reason": "$string:permission_reason_camera",
"usedScene": {
"abilities": [
"EntryAbility"
],
"when": "always"
}
} import { abilityAccessCtrl, Permissions } from '@kit.AbilityKit';
import { BusinessError } from '@kit.BasicServicesKit';
@Entry
@Component
struct CheckPermission {
build() {
RelativeContainer() {
Text('申请相机权限')
.fontSize($r('app.float.page_text_font_size'))
.fontWeight(FontWeight.Bold)
.alignRules({
center: { anchor: '__container__', align: VerticalAlign.Center },
middle: { anchor: '__container__', align: HorizontalAlign.Center }
})
.onClick(() => {
checkPermission(this.getUIContext().getHostContext()!);
})
}
.height('100%')
.width('100%')
}
}
export function checkPermission(context: Context) {
const PERMISSION_ARRAY: Permissions[] = ['ohos.permission.CAMERA'];
const atManager: abilityAccessCtrl.AtManager = abilityAccessCtrl.createAtManager();
atManager.requestPermissionsFromUser(context, PERMISSION_ARRAY).then((data) => {
if (data.authResults[0] === 0) {
// 已授权
console.info('request permission success.');
return;
}
if (data.dialogShownResults && data.dialogShownResults.length > 0 && data.dialogShownResults[0]) {
// 首次权限申请
console.info('request permission first.');
} else {
// 如果是未授权状态,可通过requestPermissionOnSetting拉起系统设置半模态二次授权。
atManager.requestPermissionOnSetting(context, PERMISSION_ARRAY)
.then((data: Array<abilityAccessCtrl.GrantStatus>) => {
console.info(`data: ${JSON.stringify(data)}`);
})
.catch((err: BusinessError) => {
console.error(`code: ${err.code}, message: ${err.message}`);
});
}
})
.catch((err: BusinessError) => {
console.error(`code: ${err.code}, message: ${err.message}`);
});
} Q:在某些情况下,需要引导用户跳转到指定应用的权限授权页面进行手动授权,但是官网指南中没有说明每种权限的URI,官网指南是否可以添加权限设置页面的URI列表?
A:由于系统设置应用中的URI涉及到内部实现,同时为了保证用户体验,设置提供了单独的接口,拉起申请权限申请弹窗,详见:支持跳转系统应用的能力清单。
Q:通知权限被拒绝后,如何再次拉起授权弹窗?
A:使用接口:openNotificationSettings拉起应用的通知设置界面,该页面以半模态形式呈现,可用于设置通知开关、通知提醒方式等。使用Promise异步回调。示例代码如下:
function reqNotification(context: common.UIAbilityContext) {
notificationManager.isNotificationEnabled().then((data: boolean) => {
console.info(`isNotificationEnabled success, data: ${JSON.stringify(data)}`);
if (!data) {
notificationManager.requestEnableNotification(context).then(() => {
console.info(`[ANS] requestEnableNotification success`);
}).catch((err: BusinessError) => {
if (1600004 == err.code) {
console.error(`[ANS] requestEnableNotification refused, code is ${err.code}, message is ${err.message}`);
notificationManager.openNotificationSettings(context); // 使用openNotificationSettings拉起应用通知设置的半模态页面。
} else {
console.error(`[ANS] requestEnableNotification failed, code is ${err.code}, message is ${err.message}`);
}
});
}
}).catch((err: BusinessError) => {
console.error(`isNotificationEnabled fail, code is ${err.code}, message is ${err.message}`);
});
}; 
Q:因为首次申请和二次申请权限调用方法不同,那么如何区分是否首次申请权限?
A:有以下两种方式:
Q:如何区分用户拒绝授权的三种状态(首次拒绝、二次拒绝、永久拒绝)?
A:区分三种拒绝状态需结合atManager.requestPermissionsFromUser返回的PermissionRequestResult中的authResults和dialogShownResults字段综合判断:
atManager.checkAccessToken仅能查询当前权限是否已授予,无法单独区分拒绝类型,需配合弹窗结果综合判断。