2018.01.18更新
近日遇到通過xcode的upload to AppStrore 上傳成功后,在iTunes的MyApps中找不到構(gòu)建的版本~,后面通過查詢資料才知道。是因?yàn)樯暾?qǐng)對(duì)應(yīng)權(quán)限時(shí)沒有在value中填寫對(duì)應(yīng)內(nèi)容引起的~~markmarkmark。蠢哭了
原文
由于蘋果對(duì)于獲取用戶隱私權(quán)限的嚴(yán)格控制,在獲取用戶相機(jī)/相冊(cè)/位置/通知等權(quán)限時(shí),必須由用戶手動(dòng)授權(quán)之后方可獲取。故事,就是在這樣的場(chǎng)景下開始的...
一、權(quán)限設(shè)置
Q:獲取對(duì)應(yīng)權(quán)限需要做些什么?
A:需要在info.plist中預(yù)設(shè)對(duì)應(yīng)權(quán)限key值,如下
Privacy - Camera Usage Description -> 相機(jī)
Privacy - Microphone Usage Description -> 麥克風(fēng)
Privacy - Photo Library Usage Description -> 讀取相冊(cè)
Privacy - Photo Library Additions Usage Description -> 保存圖片至相冊(cè)
Privacy - NSLocationAlwaysUsageDescription -> 始終獲取地理位置
Privacy - NSLocationWhenInUseUsageDescription -> 使用時(shí)獲取地理位置
PS:位置授權(quán)二選一即可
在使用對(duì)應(yīng)功能如調(diào)起相冊(cè)時(shí)系統(tǒng)會(huì)彈框要求用戶授權(quán)。
二、授權(quán)狀態(tài)檢測(cè)
Q:如果用戶沒有同意授權(quán)或拒絕授權(quán),如何保證在使用相關(guān)功能時(shí)提示用戶開啟權(quán)限?
A:需要檢測(cè)對(duì)應(yīng)權(quán)限狀態(tài),
如果用戶未授權(quán)---->提示用戶授權(quán)(系統(tǒng)行為)
如果用戶之前拒絕授權(quán)---->提示用戶開啟授權(quán)(App實(shí)現(xiàn))
如下
檢測(cè)麥克風(fēng)權(quán)限<支持7.0+>
+(BOOL)detectionMediaState:(void(^)())authorizedBlock
{
BOOL isAvalible = NO;
NSString *mediaType = AVMediaTypeAudio;
AVAuthorizationStatus authStatus = [AVCaptureDevice authorizationStatusForMediaType:mediaType];
//用戶尚未授權(quán)->申請(qǐng)權(quán)限
if (authStatus == AVAuthorizationStatusNotDetermined)
{
[AVCaptureDevice requestAccessForMediaType:mediaType completionHandler:^(BOOL granted) {
if(granted)
{
if (authorizedBlock)
{
authorizedBlock();
}
}}];
}
//用戶已經(jīng)授權(quán)
else if (authStatus == AVAuthorizationStatusAuthorized)
{
isAvalible = YES;
if (authorizedBlock)
{
authorizedBlock();
}
}
//用戶拒絕授權(quán)
else
{
//提示用戶開啟麥克風(fēng)權(quán)限
[SystemManager openSettingPagewithMessage:@"麥克風(fēng)"];
}
return isAvalible;
}
相冊(cè)訪問權(quán)限<支持7.0+>
+(BOOL)detectionPhotoState:(void(^)())authorizedBlock
{
BOOL isAvalible = NO;
if (iOS8OrLater)
{
PHAuthorizationStatus authStatus = [PHPhotoLibrary authorizationStatus];
//用戶尚未授權(quán)
if (authStatus == PHAuthorizationStatusNotDetermined)
{
[PHPhotoLibrary requestAuthorization:^(PHAuthorizationStatus status) {
if (status == PHAuthorizationStatusAuthorized)
{
if (authorizedBlock)
{
authorizedBlock();
}
}}];
}
//用戶已經(jīng)授權(quán)
else if (authStatus == PHAuthorizationStatusAuthorized)
{
isAvalible = YES;
if (authorizedBlock)
{
authorizedBlock();
}
}
//用戶拒絕授權(quán)
else
{
//提示用戶開啟相冊(cè)權(quán)限
[SystemManager openSettingPagewithMessage:@"照片"];
}
}
else
{
ALAuthorizationStatus authStatus = [ALAssetsLibrary authorizationStatus];
//用戶已經(jīng)授權(quán)
if (authStatus == ALAuthorizationStatusAuthorized)
{
isAvalible = YES;
if (authorizedBlock)
{
authorizedBlock();
}
}
//用戶拒絕授權(quán)
else
{
//提示用戶開啟相冊(cè)權(quán)限
[SystemManager openSettingPagewithMessage:@"照片"];
}
}
return isAvalible;
}
相機(jī)訪問權(quán)限<支持7.0+>
+(BOOL)detectionCameraState:(void(^)())authorizedBlock
{
BOOL isAvalible = NO;
AVAuthorizationStatus authStatus = [AVCaptureDevice authorizationStatusForMediaType:AVMediaTypeVideo];
//用戶尚未授權(quán)
if (authStatus == AVAuthorizationStatusNotDetermined)
{
[AVCaptureDevice requestAccessForMediaType:AVMediaTypeVideo completionHandler:^(BOOL granted) {
if (granted)
{
if (authorizedBlock)
{
authorizedBlock();
}
}
}];
}
//用戶已經(jīng)授權(quán)
else if (authStatus == AVAuthorizationStatusAuthorized)
{
isAvalible = YES;
if (authorizedBlock)
{
authorizedBlock();
}
}
//用戶拒絕授權(quán)
else
{
//提示用戶開啟相機(jī)權(quán)限
[SystemManager openSettingPagewithMessage:@"相機(jī)"];
}
return isAvalible;
}
通知權(quán)限<支持8.0+>
+(BOOL)detectionNotificationState:(void(^)())authorizedBlock
{
BOOL isAvalible = NO;
if (iOS8OrLater)
{
//用戶拒絕授權(quán)
if ([UIApplication sharedApplication].currentUserNotificationSettings.types == UIUserNotificationTypeNone)
{
isAvalible = NO;
//提示用戶開啟通知權(quán)限
[SystemManager openSettingPagewithMessage:@"通知"];
}
else
{
isAvalible = YES;
}
}
return isAvalible;
}
定位權(quán)限<支持8.0+>
+(BOOL)detectionLocationState:(void(^)())authorizedBlock
{
BOOL isAvalible = NO;
CLAuthorizationStatus authStatus = [CLLocationManager authorizationStatus];
if (iOS8OrLater)
{
//用戶尚未授權(quán)
if (authStatus == kCLAuthorizationStatusNotDetermined)
{
//檢測(cè)位置服務(wù)是否可用
if([CLLocationManager locationServicesEnabled])
{
if(!_locationManager)
{
_locationManager = [[CLLocationManager alloc] init];
if([_locationManager respondsToSelector:@selector(requestWhenInUseAuthorization)])
{
[_locationManager requestWhenInUseAuthorization];
}
//設(shè)置代理
[_locationManager setDelegate:self];
//設(shè)置定位精度
[_locationManager setDesiredAccuracy:kCLLocationAccuracyBest];
//設(shè)置距離篩選
[_locationManager setDistanceFilter:100];
[_locationManager startUpdatingHeading];
}
else
{
//開始定位
[_locationManager startUpdatingLocation];
}
}
else
{
//提示用戶打開定位權(quán)限
[SystemManager openSettingPagewithMessage:@"定位"];
}
}
//用戶已經(jīng)授權(quán)
else if (authStatus == kCLAuthorizationStatusAuthorizedAlways||authStatus == kCLAuthorizationStatusAuthorizedWhenInUse)
{
isAvalible = YES;
if (authorizedBlock)
{
authorizedBlock();
}
}
//用戶決絕授權(quán)
else
{
//提示用戶打開定位權(quán)限
[SystemManager openSettingPagewithMessage:@"定位"];
}
}
return isAvalible;
}
三、設(shè)置頁面跳轉(zhuǎn)
Q:提示用戶需要打開對(duì)應(yīng)權(quán)限,能否可以直接跳轉(zhuǎn)到對(duì)應(yīng)開關(guān)頁面?
A:iOS8之后是可以的
跳轉(zhuǎn)到設(shè)置界面
+(void)openSettingPagewithMessage:(NSString *)message
{
if (iOS8OrLater)
{
[[SystemManager shareManager] showSystemAlertwithTitle:@"提示" message:[NSString stringWithFormat:@"為了更好的體驗(yàn)功能,請(qǐng)到設(shè)置頁面->隱私->%@,將XX對(duì)應(yīng)開關(guān)開啟",message] cancelButtonTitle:@"下次提醒" otherButtonTitles:@"去設(shè)置" baseController:nil resultBlock:^(NSInteger index) {
if (index == 1)
{
NSURL *url = [NSURL URLWithString:UIApplicationOpenSettingsURLString];
if ([[UIApplication sharedApplication] canOpenURL:url])
{
[[UIApplication sharedApplication] openURL:url];
}
}
}];
}
//iOS8以下
else
{
[[SystemManager shareManager] showSystemAlertwithTitle:@"提示" message:[NSString stringWithFormat:@"為了更好的體驗(yàn)功能,請(qǐng)到設(shè)置頁面->隱私->%@,將XX對(duì)應(yīng)開關(guān)開啟",message] cancelButtonTitle:@"我知道了" otherButtonTitles:nil baseController:nil resultBlock:nil];
}
}
XX為App的名字
四、結(jié)束語
謝謝大家。