這兩天把定位的功能仔細(xì)捋了一下,做個(gè)總結(jié):
用系統(tǒng)自帶的定位功能舉例吧
如果應(yīng)用只有簡(jiǎn)單的定位需求企锌,一般用系統(tǒng)自帶的定位功能就可以解決問(wèn)題了角寸,使用方法如下:
1、導(dǎo)入
CoreLocation.framework
2死相、使用的類(lèi)里引入頭文件
#import <CoreLocation/CoreLocation.h>
3融求、遵守定位的代理
<CLLocationManagerDelegate>
4、聲明定位功能管理對(duì)象
@property (nonatomic, strong) CLLocationManager* locationManager;
5算撮、檢測(cè)定位授權(quán)狀態(tài)
- (void)checkServiceStatus
{
if([CLLocationManager locationServicesEnabled]) {
CLAuthorizationStatus status = [CLLocationManager authorizationStatus];
//確定用戶的位置服務(wù)啟用
if(status == kCLAuthorizationStatusNotDetermined){
//用戶未選擇生宛,繼續(xù)請(qǐng)求授權(quán)
[self requestLocationServicesAuthorization];
}else if(status == kCLAuthorizationStatusRestricted){
//功能受限制县昂,嘗試提示用戶進(jìn)入設(shè)置頁(yè)面看一下(一般不會(huì)返回該值)
}else if (status == kCLAuthorizationStatusDenied){
//位置服務(wù)是在設(shè)置中禁用,用戶選擇了“不允許”
UIAlertController *alert = [UIAlertController alertControllerWithTitle:@"提示" message:@"位置權(quán)限未開(kāi)啟陷舅,請(qǐng)到設(shè)置-隱私-定位中開(kāi)啟" preferredStyle:UIAlertControllerStyleAlert];
UIAlertAction *cancelAction = [UIAlertAction actionWithTitle:@"暫不" style:UIAlertActionStyleCancel handler:nil];
UIAlertAction *okAction = [UIAlertAction actionWithTitle:@"去設(shè)置" style:UIAlertActionStyleDefault handler:^(UIAlertAction * _Nonnull action) {
//進(jìn)入系統(tǒng)設(shè)置頁(yè)面倒彰,APP本身的權(quán)限管理頁(yè)面
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString] options:@{} completionHandler:nil];
}];
[alert addAction:cancelAction];
[alert addAction:okAction];
[self presentViewController:alert animated:YES completion:nil];
}else if(status == kCLAuthorizationStatusAuthorizedWhenInUse){
//已授權(quán)使用
}else if(status == kCLAuthorizationStatusAuthorizedAlways) {
//已授權(quán)始終使用
}
}
}
6、授權(quán)開(kāi)啟定位功能
//授權(quán)開(kāi)啟定位功能
- (void)requestLocationServicesAuthorization {
if (!self.locationManager) {
//初始化管理器
self.locationManager = [[CLLocationManager alloc] init];
self.locationManager.delegate = self;
self.locationManager.desiredAccuracy = kCLLocationAccuracyBest;
self.locationManager.distanceFilter = 100.0f;
}
[self.locationManager requestAlwaysAuthorization];
[self.locationManager requestWhenInUseAuthorization];
//開(kāi)始定位
[self.locationManager startUpdatingLocation];
}
7莱睁、target中的設(shè)置
(1)info.plist中添加定位相關(guān)的key
如果只需要前臺(tái)定位功能待讳,無(wú)需開(kāi)啟后臺(tái)定位,則只需要添加一個(gè)key即可:NSLocationWhenInUseUsageDescription仰剿,對(duì)應(yīng)的value是字符串创淡,就是彈出框的副標(biāo)題,顯示給用戶看的南吮,比如“App需要訪問(wèn)您的位置信息琳彩,以便為您提供最優(yōu)服務(wù)”之類(lèi)的,自己定義即可部凑。
如果前后臺(tái)定位都需要開(kāi)啟汁针,為了考慮iOS系統(tǒng)版本的問(wèn)題,需要再添加兩個(gè)key:NSLocationAlwaysAndWhenInUseUsageDescription(適用于iOS11之前的后臺(tái)定位) 和 NSLocationAlwaysUsageDescription (iOS11以后要使用后臺(tái)定位必加)砚尽,三個(gè)key對(duì)應(yīng)的value內(nèi)容最好都保持一致施无。
(2)如果需要啟用后臺(tái)定位功能,需要操作這一步
彈框輸入background Modes,找到這個(gè)選項(xiàng)必孤,雙擊一下就添加進(jìn)去了
這個(gè)選項(xiàng)需要勾選猾骡。
對(duì)了,順便說(shuō)一下敷搪,以前遠(yuǎn)程推送的服務(wù)也是點(diǎn)擊加號(hào)后自己去找到push notifications這一項(xiàng)兴想,雙擊添加的。
8赡勘、定位的代理方法
#pragma mark - ************** 定位的代理回調(diào)方法 **************************
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations {
// 1.獲取用戶位置的對(duì)象
CLLocation *location = [locations lastObject];
CLLocationCoordinate2D coordinate = location.coordinate;
NSLog(@"緯度:%f 經(jīng)度:%f", coordinate.latitude, coordinate.longitude);
// 2.停止定位
[manager stopUpdatingLocation];
CLLocation *newLocation = [locations firstObject];
CLGeocoder *geocoder = [[CLGeocoder alloc]init];
[geocoder reverseGeocodeLocation:newLocation completionHandler:^(NSArray<CLPlacemark *> *_Nullable placemarks, NSError * _Nullable error) {
for (CLPlacemark *place in placemarks) {
NSLog(@"name,%@",place.name); // 位置名
NSLog(@"thoroughfare,%@",place.thoroughfare); // 街道
NSLog(@"subThoroughfare,%@",place.subThoroughfare);// 子街道
NSLog(@"locality,%@",place.locality); // 市
NSLog(@"subLocality,%@",place.subLocality); // 區(qū)
NSLog(@"country,%@",place.country); // 國(guó)家
}
}];
}
//定位失敗
- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error {
if (error.code == kCLErrorDenied) {
// 提示用戶出錯(cuò)原因嫂便,kCLErrorDenied是個(gè)枚舉值,可查看其它錯(cuò)誤原因
}
}
至此闸与,定位的簡(jiǎn)單應(yīng)用已完成毙替,后面是一些對(duì)細(xì)節(jié)的講解:
針對(duì)第六步中的兩個(gè)方法:
[self.locationManager requestAlwaysAuthorization];
[self.locationManager requestWhenInUseAuthorization];
(1)如果項(xiàng)目中前后臺(tái)定位都需要使用,直接調(diào)用上面這個(gè)方法即可践樱,plist中的key值也需要添加那三個(gè)厂画。
(2)如果只需要前臺(tái)定位,那就調(diào)用下面的方法拷邢,key值只寫(xiě)一個(gè)使用中的就行袱院。
(3)這兩個(gè)方法的作用就是主動(dòng)調(diào)起系統(tǒng)的定位權(quán)限彈窗,一定要在調(diào)用startUpdatingLocation
方法前調(diào)用這個(gè)兩個(gè)方法其中的一個(gè),如果都不調(diào)忽洛,則無(wú)法彈出權(quán)限彈窗腻惠。
(4)如果key里面配置了后臺(tái)定位功能,但你調(diào)用的是下面[self.locationManager requestWhenInUseAuthorization];
方法欲虚,則彈窗提示詢問(wèn)用戶是否在應(yīng)用使用期間定位集灌,選項(xiàng)也只有允許和不允許兩個(gè),用戶如果要開(kāi)啟后臺(tái)定位苍在,只能自己去設(shè)置-隱私-定位中找到app绝页,把定位權(quán)限從使用期間切換到始終允許上面荠商,彈窗里不能選擇始終允許寂恬,所以如果需要使用后臺(tái)定位,務(wù)必定位前要調(diào)用上面[self.locationManager requestAlwaysAuthorization];
這個(gè)方法莱没,這樣用戶在彈窗里就可以選擇授權(quán)的權(quán)限初肉。
如有不對(duì)的地方,煩請(qǐng)多多指正饰躲,謝謝~