iOS 10 plist配置
描述字符串一定要填写,不然会引发包无效的问题,导致构建版本不显示
<!-- 相册 -->
<key>NSPhotoLibraryUsageDescription</key>
<string>App需要您的同意,才能访问相册</string>
<!-- 相机 -->
<key>NSCameraUsageDescription</key>
<string>App需要您的同意,才能访问相机</string>
<!-- 麦克风 -->
<key>NSMicrophoneUsageDescription</key>
<string>App需要您的同意,才能访问麦克风</string>
<!-- 位置 -->
<key>NSLocationUsageDescription</key>
<string>App需要您的同意,才能访问位置</string>
<!-- 在使用期间访问位置 -->
<key>NSLocationWhenInUseUsageDescription</key>
<string>App需要您的同意,才能在使用期间访问位置</string>
<!-- 始终访问位置 -->
<key>NSLocationAlwaysUsageDescription</key>
<string>App需要您的同意,才能始终访问位置</string>
<!-- 日历 -->
<key>NSCalendarsUsageDescription</key>
<string>App需要您的同意,才能访问日历</string>
<!-- 提醒事项 -->
<key>NSRemindersUsageDescription</key>
<string>App需要您的同意,才能访问提醒事项</string>
<!-- 运动与健身 -->
<key>NSMotionUsageDescription</key>
<string>App需要您的同意,才能访问运动与健身</string>
<!-- 健康更新 -->
<key>NSHealthUpdateUsageDescription</key>
<string>App需要您的同意,才能访问健康更新</string>
<!-- 健康分享 -->
<key>NSHealthShareUsageDescription</key>
<string>App需要您的同意,才能访问健康分享</string>
<!-- 蓝牙 -->
<key>NSBluetoothPeripheralUsageDescription</key>
<string>App需要您的同意,才能访问蓝牙</string>
<!-- 媒体资料库 -->
<key>NSAppleMusicUsageDescription</key>
<string>App需要您的同意,才能访问媒体资料库</string>
如果不起作用,可以请求后台权限,类似于这样:
<key>UIBackgroundModes</key>
<array>
<!-- 在这里写上你在后台模式下要使用权限对应的key -->
<string>location</string>
...
</array>
鉴定权限
鉴定权限是很有必要的,防止用户关闭权限后出现crash
DDYAuthorityMaster.h
// Use : [DDYAuthorityMaster checkCameraAuthority]
#import <Foundation/Foundation.h>
typedef void (^AuthorizedFinishBlock)();
@interface DDYAuthorityMaster : NSObject
#pragma mark - 摄像头权限
+ (void)cameraAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail;
#pragma mark - 麦克风权限
+ (void)audioAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail;
#pragma mark - 相册权限
+ (void)albumAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail;
#pragma mark - 推送通知权限
+ (void)pushNotificationAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail;
#pragma mark - 推送通知权限
+ (void)locationAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail;
#pragma mark - 通讯录权限
+ (void)AddressBookAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail;
/** 麦克风权限 */
+ (void)audioAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show;
/** 摄像头权限 */
+ (void)cameraAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show;
/** 相册使用权限 */
+ (void)albumAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show;
/** 推送通知权限 */
+ (void)pushNotificationAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show;
/** 通讯录权限 */
+ (void)contactsAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show;
/** 定位权限 */
+ (void)locationAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show;
@end
DDYAuthorityMaster.m
/*
* 不弹出提示或需要在提示框增加详细描述的,需手动在info.plist加一些字段
* NSLocationWhenInUseUsageDescription 位置权限 使用期间 状态
* NSLocationAlwaysUsageDescription 位置权限 始终 状态
*
*/
#import "DDYAuthorityMaster.h"
#import "DDYAppDelegate.h"
#define kAPPName [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleName"]
#define CancelText NSLocalizedString(@"Cancel", nil)
#define OKText NSLocalizedString(@"OK", nil)
#define OpenText NSLocalizedString(@"Open Setting", nil)
#define CancelText NSLocalizedString(@"Cancel", nil)
#define CameraText NSLocalizedString(@"Camera", nil)
#define AudioText NSLocalizedString(@"Microphone", nil)
#define AlbumText NSLocalizedString(@"Album", nil)
#define LocationText NSLocalizedString(@"Location", nil)
#define ContactText NSLocalizedString(@"AddressBook", nil)
@import AVFoundation;
@import CoreLocation;
@import AddressBook; // 通讯录 iOS 9-
@import Contacts; // 通讯录 iOS 9+
@import AssetsLibrary; // 相册 iOS 6-9
@import Photos; // 相册 iOS 8+
@implementation DDYAuthorityMaster
#pragma mark 私有方法
+ (BOOL)checkAuthority:(AVAuthorizationStatus)status {
return (status == AVAuthorizationStatusAuthorized) || (status == AVAuthorizationStatusNotDetermined);
}
#pragma mark 弹窗提示无权限
+ (void)showAlertController:(AuthorizedFinishBlock)block device:(NSString *)device {
UIAlertController *alertC = [UIAlertController alertControllerWithTitle:@"没有权限" message:[NSString stringWithFormat:@"请开启‘%@’对 %@ 的使用权限",kAPPName,device] preferredStyle:UIAlertControllerStyleAlert];
[alertC addAction:[UIAlertAction actionWithTitle:CancelText style:UIAlertActionStyleCancel handler:nil]];
[alertC addAction:[UIAlertAction actionWithTitle:OKText style:UIAlertActionStyleDefault handler:^(UIAlertAction *action) {
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]];
}]];
[((DDYAppDelegate *)[UIApplication sharedApplication].delegate).window.rootViewController presentViewController:alertC animated:YES completion:block];
}
#pragma mark iOS10以下可以跳转系统设置
+ (void)showNotificationAlertController:(AuthorizedFinishBlock)block {
UIAlertController *alertC = [UIAlertController alertControllerWithTitle:@"Push Notification Are Off" message:[NSString stringWithFormat:@"Don't miss out on messages from friends.Go\"Setting->Notifications\"to open"] preferredStyle:UIAlertControllerStyleAlert];
[alertC addAction:[UIAlertAction actionWithTitle:CancelText style:UIAlertActionStyleCancel handler:nil]];
[alertC addAction:[UIAlertAction actionWithTitle:OpenText style:UIAlertActionStyleDefault handler:^(UIAlertAction *action) {
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]];
}]];
[((DDYAppDelegate *)[UIApplication sharedApplication].delegate).window.rootViewController presentViewController:alertC animated:YES completion:block];
}
#pragma mark 摄像头权限
+ (BOOL)checkCameraAuthority {
return [self checkAuthority:[AVCaptureDevice authorizationStatusForMediaType:AVMediaTypeVideo]];
}
+ (void)cameraAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail;{
if ([self checkCameraAuthority]) {
if (success) {
success();
}
}else{
[self showAlertController:fail device:CameraText];
}
}
#pragma mark 麦克风权限
+ (BOOL)checkAudioAuthority {
return [self checkAuthority:[AVCaptureDevice authorizationStatusForMediaType:AVMediaTypeAudio]];
}
+ (void)audioAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail{
if ([self checkAudioAuthority]) {
if (success) {
success();
}
}else{
[self showAlertController:fail device:AudioText];
}
}
#pragma mark 相册权限
+ (BOOL)checkAlbumAuthority {
return [ALAssetsLibrary authorizationStatus] == ALAuthorizationStatusAuthorized;
}
+ (void)albumAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail {
if ([self checkAlbumAuthority]) {
if (success) {
success();
}
}else{
[self showAlertController:fail device:AlbumText];
}
}
#pragma mark 位置权限
+ (BOOL)checkLocationAuthority {
return [CLLocationManager locationServicesEnabled];
}
+ (void)locationAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail {
if ([self checkLocationAuthority]) {
if (success) {
success();
}
}else{
[self showAlertController:fail device:LocationText];
}
}
#pragma mark 推送通知权限
+ (BOOL)checkPushNotificationAuthority {
return [[UIApplication sharedApplication] currentUserNotificationSettings].types != UIUserNotificationTypeNone;
}
+ (void)pushNotificationAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail {
if ([self checkPushNotificationAuthority]) {
if (success) {
success();
}
}else{
[self showNotificationAlertController:fail];
}
}
#pragma mark 通讯录权限
+ (BOOL)checkAddressBookAuthority {
return ABAddressBookGetAuthorizationStatus() == kABAuthorizationStatusAuthorized || ABAddressBookGetAuthorizationStatus() == kABAuthorizationStatusNotDetermined;
}
+ (void)AddressBookAuthorizedSuccess:(AuthorizedFinishBlock)success fail:(AuthorizedFinishBlock)fail{
if ([self checkAddressBookAuthority]) {
if (success) {
success();
}
} else {
[self showAlertController:fail device:ContactText];
}
}
#pragma mark 默认无权限提示
+ (void)showAlertWithAppName:(NSString *)appName device:(NSString *)device
{
UIAlertController *alertC = [UIAlertController alertControllerWithTitle:@"没有权限" message:[NSString stringWithFormat:@"请开启‘%@’对 %@ 的使用权限",appName,device] preferredStyle:UIAlertControllerStyleAlert];
[alertC addAction:[UIAlertAction actionWithTitle:CancelText style:UIAlertActionStyleCancel handler:nil]];
[alertC addAction:[UIAlertAction actionWithTitle:OKText style:UIAlertActionStyleDefault handler:^(UIAlertAction *action) {
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]];
}]];
[((DDYAppDelegate *)[UIApplication sharedApplication].delegate).window.rootViewController presentViewController:alertC animated:YES completion:nil];
}
#pragma mark 麦克风权限
+ (void)audioAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show
{
AVAuthorizationStatus authStatus = [AVCaptureDevice authorizationStatusForMediaType:AVMediaTypeAudio];
switch (authStatus)
{
case AVAuthorizationStatusNotDetermined: // 有没有询问过还否开启麦克风权限(用户未确定过)
{
[[AVAudioSession sharedInstance] requestRecordPermission:^(BOOL granted) {
if (granted)
{
if (success)
{
success();
}
}
else
{
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"麦克风"];
}
if (fail)
{
fail();
}
}
}];
}
break;
case AVAuthorizationStatusRestricted: // 未授权,且用户无法更新,如家长控制情况下
case AVAuthorizationStatusDenied: // 用户拒绝App使用该权限
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"麦克风"];
}
if (fail)
{
fail();
}
break;
case AVAuthorizationStatusAuthorized: // 已授权
if (success)
{
success();
}
break;
}
}
#pragma mark 摄像头权限
+ (void)cameraAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show
{
AVAuthorizationStatus authStatus = [AVCaptureDevice authorizationStatusForMediaType:AVMediaTypeVideo];
switch (authStatus)
{
case AVAuthorizationStatusNotDetermined:
{
[AVCaptureDevice requestAccessForMediaType:AVMediaTypeVideo completionHandler:^(BOOL granted) {
if (granted)
{
NSLog(@"我点击了授权");
if (success)
{
success();
}
}
else
{
NSLog(@"我点击了拒绝");
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"摄像头"];
}
if (fail)
{
fail();
}
}
}];
}
break;
case AVAuthorizationStatusRestricted:
case AVAuthorizationStatusDenied:
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"摄像头"];
}
if (fail)
{
fail();
}
break;
case AVAuthorizationStatusAuthorized:
if (success)
{
success();
}
break;
}
}
#pragma mark 相册权限
+ (void)albumAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show
{
// ALAuthorizationStatus status = [ALAssetsLibrary authorizationStatus]; // 6-9
PHAuthorizationStatus authStatus = [PHPhotoLibrary authorizationStatus]; // 8+
switch (authStatus)
{
case AVAuthorizationStatusNotDetermined:
{
[PHPhotoLibrary requestAuthorization:^(PHAuthorizationStatus status) {
if (status == PHAuthorizationStatusAuthorized)
{
if (success)
{
success();
}
}
else
{
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"相册"];
}
if (fail)
{
fail();
}
}
}];
}
break;
case AVAuthorizationStatusRestricted:
case AVAuthorizationStatusDenied:
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"相册"];
}
if (fail)
{
fail();
}
break;
case AVAuthorizationStatusAuthorized:
if (success)
{
success();
}
break;
}
}
#pragma mark 推送通知权限
+ (void)pushNotificationAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show
{
UIUserNotificationSettings *settings = [[UIApplication sharedApplication] currentUserNotificationSettings];
switch (settings.types)
{
case UIUserNotificationTypeNone:
{
UIUserNotificationSettings *setting = [UIUserNotificationSettings settingsForTypes:UIUserNotificationTypeSound | UIUserNotificationTypeAlert | UIUserNotificationTypeBadge categories:nil];
[[UIApplication sharedApplication] registerUserNotificationSettings:setting];
}
break;
case UIUserNotificationTypeBadge:
case UIUserNotificationTypeSound:
case UIUserNotificationTypeAlert:
if (success)
{
success();
}
break;
}
}
#pragma mark 通讯录权限
+ (void)contactsAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show
{
ABAuthorizationStatus authStatus = ABAddressBookGetAuthorizationStatus();
switch (authStatus)
{
case AVAuthorizationStatusNotDetermined:
{
ABAddressBookRef addressBook = ABAddressBookCreateWithOptions(NULL, NULL);
ABAddressBookRequestAccessWithCompletion(addressBook, ^(bool granted, CFErrorRef error) {
if (granted)
{
if (success)
{
success();
}
}
else
{
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"通讯录"];
}
if (fail)
{
fail();
}
}
});
}
break;
case AVAuthorizationStatusRestricted:
case AVAuthorizationStatusDenied:
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"通讯录"];
}
if (fail)
{
fail();
}
break;
case AVAuthorizationStatusAuthorized:
if (success)
{
success();
}
break;
}
}
#pragma mark 定位权限
+ (void)locationAuthSuccess:(AuthorityBlock)success fail:(AuthorityBlock)fail alertShow:(BOOL)show
{
BOOL isLocation = [CLLocationManager locationServicesEnabled];
if (isLocation)
{
NSLog(@"not turn on the location");
if (success)
{
success();
}
}
else
{
CLLocationManager *manager = [[CLLocationManager alloc] init];
// [manager requestAlwaysAuthorization];//一直获取定位信息
[manager requestWhenInUseAuthorization];//使用的时候获取定位信息
// manager.delegate = self;
}
CLAuthorizationStatus CLstatus = [CLLocationManager authorizationStatus];
switch (CLstatus)
{
case kCLAuthorizationStatusAuthorizedAlways:
NSLog(@"Always Authorized");
break;
case kCLAuthorizationStatusAuthorizedWhenInUse:
NSLog(@"AuthorizedWhenInUse");
break;
case kCLAuthorizationStatusDenied:
{
NSLog(@"Denied");
if (show)
{
[self showAlertWithAppName:@"测试APP" device:@"定位"];
}
if (fail)
{
fail();
}
}
break;
case kCLAuthorizationStatusNotDetermined:
NSLog(@"not Determined");
break;
case kCLAuthorizationStatusRestricted:
NSLog(@"Restricted");
break;
default:
break;
}
}
- (void)locationManager:(CLLocationManager *)manager didChangeAuthorizationStatus:(CLAuthorizationStatus)status
{
switch (status)
{
case kCLAuthorizationStatusAuthorizedAlways:
NSLog(@"Always Authorized");
break;
case kCLAuthorizationStatusAuthorizedWhenInUse:
NSLog(@"AuthorizedWhenInUse");
break;
case kCLAuthorizationStatusDenied:
NSLog(@"Denied");
break;
case kCLAuthorizationStatusNotDetermined:
NSLog(@"not Determined");
break;
case kCLAuthorizationStatusRestricted:
NSLog(@"Restricted");
break;
default:
break;
}
}
@end
权限判定 + 部分在未询问时主动申请 点个星星祝福你
码农不易点星星 scan code
附
网友评论