//-------------------------------------------//
#pragma mark - 定位实现
// 导入头文件
#import <CoreLocation/CoreLocation.h>
// 创建定位管理中心属性,并 懒加载初始化 和 设置代理
@property (nonatomic, strong) CLLocationManager *manager;
// 授权设置
- (void)AuthorizationSetting {
// 第二步:判断用户设备是否开启定位设置
if (![CLLocationManager locationServicesEnabled]) {
// 如果定位服务不能使用,在这里设置弹窗提醒用户
NSLog(@"定位服务不能使用");
// 返回
return;
}
// 第四步:请求前台定位授权,并配置KEY
// iOS 7.0前(含)用户使用定位服务时会自动弹窗申请授权
// iOS 8.0开始,用户使用定位服务时需手动设置申请授权
if ([UIDevice currentDevice].systemVersion.floatValue >= 8.0) {
// 弹窗取得授权
[self.locationManager requestWhenInUseAuthorization]; // 当用户使用App时(前台)
[self.locationManager requestAlwaysAuthorization]; // 前后台都可以(会覆盖前台)
}
// 设置定位参数
self.locationManager.pausesLocationUpdatesAutomatically = YES; // 不需要数据时暂停
// 设置定位间隔距离
self.locationManager.distanceFilter = 100;
// 设置定位精度
self.locationManager.desiredAccuracy = kCLLocationAccuracyNearestTenMeters;
// 第五步:开启定位 (一般在用户同意授权后再开启)
// [self.locationManager startUpdatingLocation];
}
// 配置info.plist
NSLocationWhenInUseUsageDescription // iOS 8.0 使用前台定位服务
NSLocationAlwaysUsageDescription // iOS 8.0 使用前后台都会定位
// 实现代理方法(三个代理方法)
// 这个方法只要开启定位就会不断调用并返回当前地理信息,频率很高(耗电)
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations
// 定位失败的回调方法,在这里提醒用户如何重新开启应用使用定位服务
- (void)locationManager:(CLLocationManager *)manager didFailWithError:(nonnull NSError *)error {
if (error.code == kCLErrorDenied) {
// 弹窗提醒
// @"定位系统不可用" message:@"请进入设置页面 > 隐私 > 定位服务 > 打开定位服务 > 选择当前应用 > 勾上'使用应用期间'.设置完毕后请重新启动App运行."
}
// 停止更新定位
[self.locationManager stopUpdatingLocation];
}
// 当用户授权情况改变的时候就会调用(程序启动就会调用)
- (void)locationManager:(CLLocationManager *)manager didChangeAuthorizationStatus:(CLAuthorizationStatus)status {
if (status == kCLAuthorizationStatusAuthorizedWhenInUse || status == kCLAuthorizationStatusAuthorizedAlways) {
// 表示用户同意使用定位系统,在这里开启定位
[self.locationManager startUpdatingLocation];
}else if (status == kCLAuthorizationStatusDenied) {
// 用户拒绝使用定位,可以在这里设置一个默认的位置返回
}
}
//---------------------------------------------//
#pragma mark - 地理编码与反编码
// 编码方法。返回地标信息
- (void)geocodeAddressString:(NSString *)addressString completionHandler:(CLGeocodeCompletionHandler)completionHandler;
// 反编码
- (void)reverseGeocodeLocation:(CLLocation *)location completionHandler:(CLGeocodeCompletionHandler)completionHandler;
//---------------------------------------------//
#pragma mark - 地图 MKMapView
// 第一步:导入头文件
#import <MapKit/MapKit.h>
// 添加属性并懒加载设置属性
@property (nonatomic, strong) MKMapView *mapView;
// 设置自动跟随显示到当前位置
self.mapView.userTrackingMode = MKUserTrackingModeFollow;
// 设置地图模式
self.mapView.mapType = MKMapTypeStandard;
// 实现地图代理方法
// 地图显示完毕
- (void)mapViewDidFinishLoadingMap:(MKMapView *)mapView{
NSLog(@"地图显示完毕");
NSLog(@" %f, %f", mapView.region.span.latitudeDelta, mapView.region.span.longitudeDelta);
}
// 地图跟新到用户位置的时候促发,在这里获得当前用户位置
- (void)mapView:(MKMapView *)mapView didUpdateUserLocation:(MKUserLocation *)userLocation
// 地图显示区域即将改变
- (void)mapView:(MKMapView *)mapView regionWillChangeAnimated:(BOOL)animated {
NSLog(@"地图开始改变区域");
}
// 地图显示区域改变完成
- (void)mapView:(MKMapView *)mapView regionDidChangeAnimated:(BOOL)animated {
NSLog(@"区域已经改变完成");
}
#pragma mark - 大头针 MKPointAnnotation
// 获得当前长按的点
CGPoint point = [gesture locationInView:gesture.view];
// 根据点坐标从地图获得点对应的经纬度
CLLocationCoordinate2D coordinate = [self.mapView convertPoint:point toCoordinateFromView:gesture.view];
#pragma mark - 导航 MKDirections / MKDirectionsRequest
Demo: 根据起点与终点坐标, 向Apple服务器请求路线规划信息, 再绘制路线
1. 获取起点与终点的地理坐标
2. 创建 MKDirectionRequest , 配置起点与终点的 MapItem
3. 使用 MKDirection 进行路线规划请求 ( MKRoute, MKRouteStep )
calculateDirectionsWithCompletionHandler
4. 将获取到的路线信息绘制到地图上. ( MKPolyLineRender )
// 渲染方法
[self.mapView addOverlay:toute.polyline];
// 设置颜色的代理方法
// 渲染路线
- (MKOverlayRenderer *)mapView:(MKMapView *)mapView rendererForOverlay:(id<MKOverlay>)overlay {
// 设置颜色
MKPolylineRenderer *renderer = [[MKPolylineRenderer alloc] initWithOverlay:overlay];
renderer.lineWidth = 2.0;
renderer.strokeColor = [UIColor blueColor];
return renderer;
}