前言
地图在现代生活中占据了很重要的位置,无论是去旅游,还是驾车,无论是步行还是坐公交,可以说都离不开地图。那么既然这么多的地方都用到地图,它用代码怎么实现呢,我们来看一下。
首先要介绍的是两个基本框架
.Core Location
一、功能
(1)基础的定位
(2)地理编码(将文字转换成地理位置)反编码(将地理位置转换成文字)
二、iOS8、iOS9之后的改变
1、iOS8的改变
(1)定位的服务目的(写在Infoplist中)
NSLocationAlwaysUsageDescription
NSLocationWhenInUseUsageDescription
注意:如果没有在Infoplist文件中写服务的目的,就不能使用定位功能,没有提示信息。
(2)请求用户授权
RequestAlwaysAuthorization
requestWhenInfoUseAuthorization
注意:(1)和(2)的两种状态分别是:①一直定位状态②使用app的时定位,如果两者不匹配,不能使用定位功能(既always与always匹配)
2、iOS9的变化
iOS9按home键进入后台,如果需要继续定位
(1)在Infoplist中添加Required background modes
->App registers for location updates
如果不添加这对键值,却使用定位功能,系统会直接崩溃。
(2)allowsBackgroundLocationUpdates需要同时设置成YES
三、定位的使用
一、使用定位服务所需的相关类和其他数据类型
(1)CLLocationManager:定位的管理者,通过这个类创建定位服务的功能
(2)CLLocation:地理位置信息相关的类
(3)CLLocationCoordinate2D:坐标的数据类型(结构体)
(4)CLRegion:表示范围的范围
(5)CLGeocoder:地理编码、反编码的类
(6)CLPlacemark:表示地标的一个类用文字表示位置信息的类(里面包含了location)
(7)CLHeading:表示导航方向的一个类
(2)CLLocation:地理位置信息相关的类
(3)CLLocationCoordinate2D:坐标的数据类型(结构体)
(4)CLRegion:表示范围的范围
(5)CLGeocoder:地理编码、反编码的类
(6)CLPlacemark:表示地标的一个类用文字表示位置信息的类(里面包含了location)
(7)CLHeading:表示导航方向的一个类
(8)CLLocationDistance:距离
二、具体使用
(1)定位CLLocationManager的使用
①导入框架
#import<CoreLocation/CoreLocation.h>
②检查用户是否在设置中打开定位服务
if(![CLLocationManagerlocationServicesEnabled]) {
// 判断是否可以打开
if ([[UIApplicationsharedApplication]canOpenURL:[NSURLURLWithString:UIApplicationOpenSettingsURLString]]) {
// 跳转到设置页面
[[UIApplicationsharedApplication]openURL:[NSURLURLWithString:UIApplicationOpenSettingsURLString]];
}
if ([[UIApplicationsharedApplication]canOpenURL:[NSURLURLWithString:UIApplicationOpenSettingsURLString]]) {
// 跳转到设置页面
[[UIApplicationsharedApplication]openURL:[NSURLURLWithString:UIApplicationOpenSettingsURLString]];
}
}
③初始化定位对象
locationManager= [[CLLocationManageralloc]init];
// 设置多少米去更新位置信息
locationManager.distanceFilter=100;
// 设置定位的精准度
locationManager.distanceFilter=100;
// 设置定位的精准度
locationManager.desiredAccuracy =10;
④Info中添加描述的使用定位的目的,并向用户请求授权
在Infoplist中添加
NSLocationAlwaysUsageDescription或者
NSLocationWhenInUseUsageDescription
[locationManagerrequestAlwaysAuthorization];//请求授权
⑤挂上代理,病史实现它的代理方法
locationManager.delegate=self;
⑥如果需要使用后台定位服务,需要在info中添加Required background modes这个key以及他里面的元素App registers for location updates
locationManager.allowsBackgroundLocationUpdates=YES;
⑦开始定位
[locationManagerstartUpdatingLocation];
三、位置信息 CLLocation
CLLocation位置信息的属性有
(1)coordinate:经纬度
①latitude:纬度
②longitude:经度
(2)altitude:高度
(3)horizontalAccuracy:水平的精准度
可以用他来检测是否定位成功(如果是正数=定位成功)
(4)verticalAccuracy:垂直的精准度
(5)course:0.0-359.9正北方向0.0
(6)speed:速度
(7)Timestamp:时间戳
①latitude:纬度
②longitude:经度
(2)altitude:高度
(3)horizontalAccuracy:水平的精准度
可以用他来检测是否定位成功(如果是正数=定位成功)
(4)verticalAccuracy:垂直的精准度
(5)course:0.0-359.9正北方向0.0
(6)speed:速度
(7)Timestamp:时间戳
(9)floor:楼层的高度
locationManager有一个代理方法设置CLLocation
-(void)locationManager:(CLLocationManager*)manager didUpdateLocations:(NSArray<CLLocation *> *)locations{
// 位置信息
CLLocation *loction = locations.firstObject;
// 坐标:经纬度:struct是一个结构体
// ①latitude:纬度
// ②longitude:经度
CLLocationCoordinate2D coordinate = loction.coordinate;
NSLog(@"经度%f纬度%f",coordinate.longitude,coordinate.latitude);
// CLLocationDistance->double
NSLog(@"高度%f",loction.altitude);
// 水平精准度,可以通过水平精准度来判断是否定位成功,如果是负数表示定位错误。
NSLog(@"水平精准度%f",loction.horizontalAccuracy);
// 垂直精准度,垂直方向的准确度数。
NSLog(@"垂直精准度%f",loction.verticalAccuracy);
// 航向,方向course
// 0表北方
// 90表东
// 180表南
// 270表西
NSLog(@"方向%f",loction.course);
// 速度表示当前行使的速度
NSLog(@"速度%f",loction.speed);
// 楼层的高度
NSLog(@"当前楼层是%ld",loction.floor.level);
// 当前定位的日期
NSLog(@"日期%@",loction.timestamp);
}
四、地理编码和地理反编码
地理编码:是将地名转换成位置信息
用处:把文字描述的位置转换成地图上的经纬度。
反地理编码:是将位置信息转换成文字
用处:把文字描述的位置转换成地图上的经纬度。
反地理编码:是将位置信息转换成文字
用处:可以通过点击选择地图上面的某个位置,来获得这个位置的文字描述
CLGeocoder *geocoder = [[CLGeocoderalloc]init];
// 不限制范围、方圆
// [geocoder geocodeAddressString:@"郑州科技学院" completionHandler:^(NSArray<CLPlacemark *> * _Nullable placemarks, NSError * _Nullable error) {
NSLog(@"%@",placemarks);
//
// CLPlacemark *placemark = placemarks.firstObject;
//
// CLLocation *loc = placemark.location;
//
// NSLog(@"纬度%f经度%f",loc.coordinate.latitude,loc.coordinate.longitude);
// }];
// 限制方圆、范围
// CLCircularRegion:CLRegion的子类,表示圆形的一个范围
//
// CLLocationCoordinate2D coordinate;
// coordinate.latitude = 34;
// coordinate.longitude = 113;
//
// CLCircularRegion *circularRegion = [[CLCircularRegion alloc] initWithCenter:coordinate radius:1000 identifier:@".."];
//
// [geocoder geocodeAddressString:@"郑州科技学院" inRegion:circularRegion completionHandler:^(NSArray<CLPlacemark *> * _Nullable placemarks, NSError * _Nullable error) {
// CLPlacemark *placemark = placemarks.firstObject;
// CLLocation *loc = placemark.location;
// NSLog(@"纬度%f经度%f",loc.coordinate.latitude,loc.coordinate.longitude);
// }];
// 设置优先级DISPATCH_QUEUE_PRIORITY_DEFAULT
/*
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_async(queue, ^{
[geocoder geocodeAddressString:@"郑州科技学院" completionHandler:^(NSArray<CLPlacemark *> * _Nullable placemarks, NSError * _Nullable error) {
CLLocation *loc = placemarks.firstObject.location;
NSLog(@"经度%f 纬度%f",loc.coordinate.longitude,loc.coordinate.latitude);
dispatch_queue_t quequ =dispatch_get_main_queue();
dispatch_sync(queue, ^{
// 更新UI,要在主线程更新UI
});
}];
});
*/
// 反地理编码:将经纬度转换成地名
CLLocation *loc = [[CLLocationalloc]initWithLatitude:31.6longitude:115.4];
[geocoder reverseGeocodeLocation:loccompletionHandler:^(NSArray<CLPlacemark *> *_Nullable placemarks, NSError * _Nullable error) {
NSLog(@"%@",placemarks.firstObject.name);
// [geocoder geocodeAddressString:@"郑州科技学院" completionHandler:^(NSArray<CLPlacemark *> * _Nullable placemarks, NSError * _Nullable error) {
NSLog(@"%@",placemarks);
//
// CLPlacemark *placemark = placemarks.firstObject;
//
// CLLocation *loc = placemark.location;
//
// NSLog(@"纬度%f经度%f",loc.coordinate.latitude,loc.coordinate.longitude);
// }];
// 限制方圆、范围
// CLCircularRegion:CLRegion的子类,表示圆形的一个范围
//
// CLLocationCoordinate2D coordinate;
// coordinate.latitude = 34;
// coordinate.longitude = 113;
//
// CLCircularRegion *circularRegion = [[CLCircularRegion alloc] initWithCenter:coordinate radius:1000 identifier:@".."];
//
// [geocoder geocodeAddressString:@"郑州科技学院" inRegion:circularRegion completionHandler:^(NSArray<CLPlacemark *> * _Nullable placemarks, NSError * _Nullable error) {
// CLPlacemark *placemark = placemarks.firstObject;
// CLLocation *loc = placemark.location;
// NSLog(@"纬度%f经度%f",loc.coordinate.latitude,loc.coordinate.longitude);
// }];
// 设置优先级DISPATCH_QUEUE_PRIORITY_DEFAULT
/*
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_async(queue, ^{
[geocoder geocodeAddressString:@"郑州科技学院" completionHandler:^(NSArray<CLPlacemark *> * _Nullable placemarks, NSError * _Nullable error) {
CLLocation *loc = placemarks.firstObject.location;
NSLog(@"经度%f 纬度%f",loc.coordinate.longitude,loc.coordinate.latitude);
dispatch_queue_t quequ =dispatch_get_main_queue();
dispatch_sync(queue, ^{
// 更新UI,要在主线程更新UI
});
}];
});
*/
// 反地理编码:将经纬度转换成地名
CLLocation *loc = [[CLLocationalloc]initWithLatitude:31.6longitude:115.4];
[geocoder reverseGeocodeLocation:loccompletionHandler:^(NSArray<CLPlacemark *> *_Nullable placemarks, NSError * _Nullable error) {
NSLog(@"%@",placemarks.firstObject.name);
}];