定位服务在iOS11系统上不能使用的问题

今天我突然发现以前维护的项目中开发的定位功能失效,显示“用户授权失败”。这个功能在当时是能成功实现的。于是我上网查找原因,网上说是因为苹果现在增加了一项新的隐私保护 NSLocationAlwaysAndWhenInUseUsageDescription ,并且原有的 NSLocationAlwaysUsageDescription 被降级为 NSLocationWhenInUseUsageDescription 。 所以在Xcode的控制台输出:

This app has attempted to access privacy-sensitive data without a usage description. The app's Info.plist must contain both NSLocationAlwaysAndWhenInUseUsageDescription and NSLocationWhenInUseUsageDescription keys with string values explaining to the user how the app uses this data

 

依照上述要求,我在项目的info.plist文件中加入

NSLocationAlwaysAndWhenInUseUsageDescription
    是否允许开启定位以始终访问位置

NSLocationWhenInUseUsageDescription
    是否允许开启定位以在使用期间访问位置

 

然后又重新实现了定位

/*
 iOS8以前:系统会自动申请用户位置权限
 iOS8之后(包含iOS8.0): 必须要程序员去申请用户的位置权限
*/

#import "ViewController.h"
#import 

@interface ViewController ()

@property (nonatomic,strong) CLLocationManager *locationManager;

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    //位置管理器常见属性
    //当用户移动了多长的距离之后,才更新用户位置,单位(米)
    self.locationManager.distanceFilter = 10;
    
    //定位精度,精度越高越费电
    self.locationManager.desiredAccuracy = kCLLocationAccuracyBestForNavigation;
    
    //extern const CLLocationAccuracy kCLLocationAccuracyBestForNavigation; 导航使用最好进度
    //extern const CLLocationAccuracy kCLLocationAccuracyBest;  最高精度
    //extern const CLLocationAccuracy kCLLocationAccuracyNearestTenMeters;  10M
    //extern const CLLocationAccuracy kCLLocationAccuracyHundredMeters; 100M
    //extern const CLLocationAccuracy kCLLocationAccuracyKilometer; 1000M
    //extern const CLLocationAccuracy kCLLocationAccuracyThreeKilometers; 3000M
    self.locationManager.activityType = CLActivityTypeFitness;
    
    //CLActivityTypeOther = 1,
    //CLActivityTypeAutomotiveNavigation,    // 汽车导航
    //CLActivityTypeFitness,                // 步行导航
    //CLActivityTypeOtherNavigation         // 其他导航,比如轮船,火车,飞机

    if ([UIDevice currentDevice].systemVersion.doubleValue >= 8.0) {
        //申请用户位置权限
        //无论应用在前台还是在后台都需要使用用户的位置信息
        [self.locationManager requestAlwaysAuthorization];
     }else{
            
        //开始更新用户位置
        [self.locationManager startUpdatingLocation];
    }
}


#pragma mark - CLLocationManagerDelegate
//当授权状态发生改变了就调用该代理方法
- (void)locationManager:(CLLocationManager *)manager didChangeAuthorizationStatus:(CLAuthorizationStatus)status{
    //当前请求到用户的权限后开始定位
    if (status == kCLAuthorizationStatusAuthorizedAlways) {
        
        [self.locationManager startUpdatingLocation];
    }else{
        
        NSLog(@"用户授权失败");
    }
}

//当更新用户位置的时候执行
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations{
    //距离当前时间最近的那个位置是这个数组的最后一个元素
    CLLocation *location = locations.lastObject;
    CLLocationCoordinate2D coordinate = location.coordinate;
    NSLog(@"当前纬度:%f 当前经度:%f", coordinate.latitude, coordinate.longitude);
    
    //根据经纬度反向地理编译出地址信息
    CLGeocoder *geoCoder = [[CLGeocoder alloc] init];
    [geoCoder reverseGeocodeLocation:location completionHandler:^(NSArray *placemarks, NSError *error) {
        
        for (CLPlacemark *placemark in placemarks) {
            
            NSDictionary *address = [placemark addressDictionary];
            NSLog(@"当前地址:%@ %@ %@ %@ %@",address[@"Country"],address[@"City"],address[@"SubLocality"],address[@"Street"],address[@"Name"]);
        }
    }];
}


//懒加载
- (CLLocationManager *)locationManager{
    if (_locationManager == nil) {
        _locationManager = [[CLLocationManager alloc] init];
        _locationManager.delegate = self;
    }
    
    return _locationManager;
}


@end

Xcode控制台输出

 

你可能感兴趣的:(定位服务在iOS11系统上不能使用的问题)