1、CoreLocation框架简介:
?了解
:在ios开发中,要想使用地图和定位功能,必须基于2个框架进行开发。CoreLocation框架
:主要用于地理定位;MapKit框架
:主要用于地图展示。
1-1、CoreLocation框架功能:
功能 | 作用 |
---|
地理定位 |
定位用户所在位置,获取对应的经纬度、海拔等位置信息 |
区域监听 |
事先在APP内部通过代码指定一个区域,当用户进入、或离开该区域的时候,可以通过对应的代理方法监听到用户的位置 |
地理编码 |
将详细的位置信息 转换为对应的经纬度 ,即:位置信息 ——> 经纬度 |
反地理编码 |
将经纬度转换为详细的位置,即:经纬度 ——> 位置信息 |
?重要
:CoreLocation框架着重于功能的实现,只有开发人员可以获取到对应的数据,用户是看不见、摸不着的;CoreLocation框架中所有的数据类型的前缀都是CL开头。
1-2、两个热门术语:
名称 | 含义 |
---|
LBS |
Location Based Service,基于位置的服务 |
SoLoMo |
Social Local Mobile(索罗门),社交、本地、移动 |
社交化 |
在APP里面假如一些社交元素 |
本地化 |
基于LBS的周边搜索,周边签到等服务 |
移动化 |
移动网:3G/4G网,相对于有线/无线电脑网络;移动APP:相对于PC端应用 |
1-3、CoreLocation框架使用主要步骤:
步骤 | 具体信息 |
---|
第一步 |
导入CoreLocation框架,Xcode5.0之后该步骤可以省略 |
第二步 |
导入主头文件,#import |
第三步 |
使用CLLocationManager对象调用相关方法(startUpdatingLocation —> 开启定位、stopUpdatingLocation —> 停止定位),开启定位功能,实现相关的位置服务 |
第四步 |
给CLLocationManager对象设置delegate |
第五步 |
实现相应的代理方法,监听相关位置信息变化 |
?注意
:只有使用了该框架里的某个类创建了一个对象,才会隐式的将该框架导入到项目中。
2、iOS8.0之前 - - - 定位功能:
1、?重要
:iOS8.0之前,实现定位功能不需要向用户请求授权。
2、?了解
:iOS8.0之前,版本即将被淘汰,不再做适配;而且iOS8.0以后的定位功能实现的代码可以直接运行在iOS8.0之前的设备上,不需要做任何修改;因为系统版本和Xcode版本问题,此处不再过于详细介绍iOS8.0之前的定位功能;只是列举大致实现步骤,详细步骤可以参阅iOS8.0之后的定为实现。
3、?了解
:iOS8.0之前,当应用程序使用后台定位功能时,屏幕上方是否会出现蓝色横幅未做验证
。
2-1、iOS8.0之前 - - - 前台定位:
2-1-1、详细步骤:
步骤 | 详情 |
---|
第一步 |
在info.plist 文件中配置Privacy - Location Usage Description 来说明定位目的 |
第二步 |
导入CoreLocation框架及对应的主头文件 |
第三步 |
创建CLLocationManager对象并设置代理(delegate ) |
第四步 |
调用startUpdatingLocation 方法,开始更新用户的位置信息 |
第五步 |
在对应的代理方法中获取位置信息,locationManager:didUpdateLocations: 代理方法一旦开始定位之后,将会每隔一秒钟自动调用;调用十分频繁,非常耗电 |
2-1-2、细节补充:
1、导入CoreLocation框架以及对应的主头文件。
1. #import
2、代理方法中无法定位原因:
?重要
:①、CLLocationManager对象为局部变量;②、没有调用相应的方法开启定位功能;③、模拟器出现问题;④、其它未知原因导致。
2-2、iOS8.0之前 - - - 后台定位:
2-1、详细步骤:
步骤 | 详情 |
---|
第一步 |
在info.plist 文件中配置Privacy - Location Usage Description 来说明定位目的 |
第二步 |
开启后台模式: ①、选中工程 -> 前往target -> capabilities -> Background Modes -> 勾选location updates ;②、直接在info.plist 文件中增加Required background modes 的key,该key为一个数组,在该数组中增加App registers for location updates 的值 |
第三步 |
导入CoreLocation框架及对应的主头文件 |
第四步 |
创建CLLocationManager对象并设置代理(delegate ) |
第五步 |
调用startUpdatingLocation 方法,开始更新用户的位置信息 |
第六步 |
在对应的代理方法中获取位置信息,locationManager:didUpdateLocations: 代理方法一旦开始定位之后,将会每隔一秒钟自动调用;调用十分频繁,非常耗电 |
2-2、开启后台模式两种方式:
?重要
:其实,两种开启后台模式的方式,本质都是操作info.plist
文件。
- ①、
选中工程
-> 前往target
-> capabilities
-> Background Modes
-> 勾选location updates
。
- ②、配置
info.plist
文件:
?了解
:其实,两种开启后台模式的方式,本质都是操作info.plist
文件。
2-3、细节补充:
?了解
:①、需要使用Xcode7.0之前的版本,模拟器应选择iOS8.0之前的版本;②、iOS8.0之前后台定位,当应用退出到后台时,在屏幕上方应该会出现蓝色横幅(未验证,不过查阅大量资粮都未说明会有蓝色横幅)。
2-4、常见问题:
?注意
:如果定位不到,对应的代理方法不执行;4中解决方案:①、检查模拟器是否为iOS8.0之前的系统版本,一定要使用iOS8.0之前的模拟器;②、检查模拟器是否有设置数据;③、检查代码是否存在逻辑错误、是否有设置代理、位置管理对象是否为局部变量;④、模拟器问题,请先将模拟器位置设为None
,然后再次设置数据;或者,重置模拟器。
2-5、示例代码:
1.#import "ViewController.h"
2.#import
3.
[email protected] ViewController ()
5.
6./** 位置管理者 */
[email protected] (nonatomic, strong) CLLocationManager *lM;
8.
[email protected]
10.
[email protected] ViewController
12.
13.#pragma mark - 懒加载
14.- (CLLocationManager *)lM
15.{
16. if (!_lM) {
17. // 1. 创建位置管理者
18. _lM = [[CLLocationManager alloc] init];
19. // 1.1 代理, 通知, block
20. _lM.delegate = self;
21.
22. // 距离筛选器: 每隔多米定位一次
23. _lM.distanceFilter = 100;
24.
25. // 精确度越高, 越耗电, 定位时间越长
26. _lM.desiredAccuracy = kCLLocationAccuracyBest;
27. }
28. return _lM;
29.}
30.
31.- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
32.{
33. // 2. 使用位置管理者,开始更新用户位置
34. // 默认只能在前台获取用户位置,
35. // 勾选后台模式 location updates
36. [self.lM startUpdatingLocation];
37.}
38.
39.#pragma mark - CLLocationManagerDelegate
40./**
41. * 更新到位置之后调用
42. *
43. * @param manager 位置管理者
44. * @param locations 位置数组
45. */
46.-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations
47.{
48. NSLog(@"定位到了");
49.
50. // 拿到位置,做一些业务逻辑操作
51.
52. // 停止更新
53. [manager stopUpdatingLocation];
54.}
[email protected]
3、iOS8.0 ~ iOS9.0 - - - 定位功能:
3-1、iOS8.0 ~ iOS9.0 - - - 前台定位:
1、详细步骤:
步骤 | 详情 |
---|
第一步 |
在info.plist 文件中配置key为NSLocationWhenInUseUsageDescription 的键值对、并调用CLLocationManager对象的requestWhenInUseAuthorization 方法请求用户授权 |
第二步 |
导入CoreLocation框架及对应的主头文件 |
第三步 |
创建CLLocationManager对象并设置代理(delegate ) |
第四步 |
调用startUpdatingLocation 方法,开始更新用户的位置信息 |
第五步 |
在对应的代理方法中获取位置信息,locationManager:didUpdateLocations: 代理方法一旦开始定位之后,将会每隔一秒钟自动调用;调用十分频繁,非常耗电,在该代理方法中执行相应的逻辑操作 |
2、细节补充:
?重要
:①、从iOS8.0开始,应用开启定位功能需要主动请求前台定位授权;除了使用CLLocationManager对象调用requestWhenInUseAuthorization
方法之外,还需要在info.plist
文件中配置NSLocationWhenInUseUsageDescription
的key(注意:千万不要出现空格),其value用以向用户说明应用程序使用定位功能主要用途(注意:value可以为空);如果没有配置该键值对,将不会弹框获取用户授权。②、需要注意版本适配问题,模拟器运行环境应当为iOS8.0之后,包括iOS8.0。
3、示例代码:
1.#import "ViewController.h"
2.#import
3.
[email protected] ViewController ()
5./** 定位管理者 */
[email protected] (strong, nonatomic) CLLocationManager *mgr;
7.
[email protected]
9.
[email protected] ViewController
11.
12.- (void)viewDidLoad {
13. [super viewDidLoad];
14.
15. // 1. 创建定位管理者对象, 创建对象调用init方法初始化时, 如无特殊操作; 可以使用new方法代替
16. self.mgr = [CLLocationManager new];
17.
18. // 2. 请求用户授权, 必须在info.plist文件配置键值对
19. // NSLocationWhenInUseUsageDescription : 前台定位授权
20. // requestWhenInUseAuthorization : 前台授权 ,使用应用时授权获取位置信息
21. // NSLocationAlwaysUsageDescription : 前后台授权
22. // requestAlwaysAuthorization : 前后台授权, 总是授权获取位置信息
23. if ([self.mgr respondsToSelector:@selector(requestWhenInUseAuthorization)]) {
24. [self.mgr requestWhenInUseAuthorization];
25. }
26.
27. // 3. 设置代理对象
28. self.mgr.delegate = self;
29.
30. // 4. 开启定位功能
31. [self.mgr startUpdatingLocation];
32.}
33.
34.#pragma mark -
35./**
36. 第一次成功获取用户位置时便会来到此代理方法, 之后每隔一秒钟调用一次; 调用十分频繁
37.
38. @param manager 定位管理者对象
39. @param locations 用户所有位置对象(数组中每一个元素代表一个位置)
40. */
41.- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations
42.{
43. NSLog(@"%@", locations);
44.
45. // 1. 停止定位
46. [self.mgr stopUpdatingLocation];
47.}
[email protected]
3-2、iOS8.0 ~ iOS9.0 - - - 后台定位:
3-2-1、前台授权 + 开启后台模式:
?重要
:①、一定要记得开启后台模式,否则,当应用程序退到后台模式时将不能进行定位操作;②、当APP退到后台,在屏幕上方会出现蓝色横幅
,已提醒用户应用程序正在使用定位功能。
1、详细步骤:
步骤 | 详情 |
---|
第一步 |
在info.plist 文件中配置key为NSLocationWhenInUseUsageDescription 的键值对、并调用CLLocationManager对象的requestWhenInUseAuthorization 方法请求用户授权 |
第二步 |
开启后台模式: ①、选中工程 -> 前往target -> capabilities -> Background Modes -> 勾选location updates ;②、直接在info.plist 文件中增加Required background modes 的key,该key为一个数组,在该数组中增加App registers for location updates 的值 |
第三步 |
导入CoreLocation框架及对应的主头文件 |
第四步 |
创建CLLocationManager对象并设置代理(delegate ) |
第五步 |
调用startUpdatingLocation 方法,开始更新用户的位置信息 |
第六步 |
在对应的代理方法中获取位置信息,locationManager:didUpdateLocations: 代理方法一旦开始定位之后,将会每隔一秒钟自动调用;调用十分频繁,非常耗电,在该代理方法中执行相应的逻辑操作 |
2、开启后台模式两种方式:
?重要
:其实,两种开启后台模式的方式,本质都是操作info.plist
文件。
- ①、
选中工程
-> 前往target
-> capabilities
-> Background Modes
-> 勾选location updates
。
- ②、配置
info.plist
文件:
3、示例代码:
?重要
:与前台定位的示例代码一致,只是,应用程序开启后台模式,能够在后台获取用户的位置信息;并在代理方法中执行相应的逻辑操作。
3-2-2、前后台授权:
?重要
:①、iOS8.0之后应用程序使用后台定位功能,前后台授权级别高于前台授权级别;当同时使用两种授权方式时会有两次弹框提醒。②、使用前后台授权,无论应用程序是否开启后台模式;应用程序退到后台都能获取位置信息。③、使用前后台授权,当应用退到后台,在屏幕上方不会出现蓝色横幅
。
1、详细步骤:
步骤 | 详情 |
---|
第一步 |
在info.plist 文件中配置key为NSLocationAlwaysUsageDescription 的键值对、并调用CLLocationManager对象的requestAlwaysAuthorization 方法请求用户授权 |
第二步 |
导入CoreLocation框架及对应的主头文件 |
第三步 |
创建CLLocationManager对象并设置代理(delegate ) |
第四步 |
调用startUpdatingLocation 方法,开始更新用户的位置信息 |
第五步 |
在对应的代理方法中获取位置信息,locationManager:didUpdateLocations: 代理方法一旦开始定位之后,将会每隔一秒钟自动调用;调用十分频繁,非常耗电,在该代理方法中执行相应的逻辑操作 |
2、细节补充:
?重要
:①、注意,在实际应用开发中可能需要版本适配;②、不要忘记配置info.plist
文件,否则,将不会出现弹框获取用户授权。
4、iOS9.0之后 - - - 定位功能:
?了解
:iOS9.0使用前台授权
+ 开启后台模式
实现后台定位功能有所改变,增加了新的步骤;需要设置CLLocationManager
对象的allowsBackgroundLocationUpdates
属性,代理对象还必须实现locationManager:didFailWithError:
代理方法,以达到监听定位失败的错误信息。
4-1、iOS9.0之后 - - - 前台定位:
?了解
:与iOS8.0 ~ iOS9.0前台定位实现步骤一致,并无任何新增变化;一定要注意使用前台定位功能需要获取用户授权,注意:需要配置info.plist
文件,否则,将不会出现弹框提醒用户、获取用户授权。
4-2、iOS9.0之后 - - - 后台定位:
4-2-1、前台授权
+ 开启后台模式
:
1、前台授权
+ 开启后台模式
:
?重要
:在前台定位授权的基础上,如果勾选了后台模式location updates
之后,还需要额外设置属性allowsBackgroundLocatiOnUpdates= YES
;代理对象还必须实现locationManager:didFailWithError:
代理方法,以达到监听定位失败的错误信息。使用allowsBackgroundLocationUpdates
属性注意需要做版本适配,该属性为iOS9.0 ~
。
2、示例代码:
1.// 5. 获取后台临时定位授权, 记得开启后台定位模式, 否则, 程序将会崩溃
2.if ([UIDevice currentDevice].systemVersion.doubleValue >= 9.0) {
3. self.mgr.allowsBackgroundLocatiOnUpdates= YES;
4.}
3、必须实现的代理方法:
1./**
2. 定位失败调用该代理方法
3.
4. @param manager 定位管理者对象
5. @param error 错误对象
6. */
7.- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error{
8. if (error != nil) {
9. NSLog(@"%@", error);
10. }
11.}
?重要
:没有实现该代理方法,程序将会崩溃。
4-2-2、前后台授权
:
?重要
:直接请求前后台定位授权,和iOS8.0 ~ iOS9.0之后一致;没有任何变化。注意:只能运行在iOS9.0之后的设备上,一定要注意版本适配。