iOS地图开发-地图的定位

定位

定位是一个很常用的功能,打开地图软件后如果用户允许软件定位的话,软件便会自动锁定到手机所在位置,并且地图上的位置会随着手机的移动而移动。定位使用到的类是Core Location框架中的CLLocationManager类。

CLLocationManager中常用的方法

*******类方法**********
//是否启用定位服务,通常如果用户没有启用定位服务可以提示用户打开定位服务       
+(BOOL)locationServicesEnabled;

/* 定位服务授权状态,返回枚举类型,下面是类型解释

 * kCLAuthorizationStatusNotDetermined: 用户尚未做出决定是否启用定位服务

 * kCLAuthorizationStatusRestricted: 没有获得用户授权使用定位服务,可能用户没有自己禁止访问授权

 * kCLAuthorizationStatusDenied :用户已经明确禁止应用使用定位服务或者当前系统定位服务处于关闭状态

 * kCLAuthorizationStatusAuthorizedAlways: 应用获得授权可以一直使用定位服务,即使应用不在使用状态

 * kCLAuthorizationStatusAuthorizedWhenInUse: 使用此应用过程中允许访问定位服务

 */ 
 +(CLAuthorizationStatus)authorizationStatus;
 *******对象方法**********
 //开始定位追踪,开始定位后将按照用户设置的更新频率执行-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations;方法反馈定位信息
 startUpdatingLocation

 //停止定位追踪
 stopUpdatingLocation

 //请求获得应用使用时的定位服务授权,注意使用此方法前在要在info.plist中配置NSLocationWhenInUseUsageDescription
 requestWhenInUseAuthorization

 //请求获得应用一直使用定位服务授权,注意使用此方法前要在info.plist中配置NSLocationAlwaysUsageDescription
 requestAlwaysAuthorization

 //开始导航方向追踪
 startUpdatingHeading

 //停止导航方向追踪
 stopUpdatingHeading

 //开始对某个区域进行定位追踪,开始对某个区域进行定位后。如果用户进入或者走出某个区域会调用相应的代理方法反馈相关信息

 //停止对某区域追踪
 stopMonitoringForRegion:
 *******代理方法*******
 //位置发生改变后执行(第一次定位到某个位置之后也会执行)
 -(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations;

 //导航方向发生变化后执行
 - (void)locationManager:(CLLocationManager *)manager didUpdateHeading:(CLHeading *)newHeading;

 // 进入某个区域之后执行
 - (void)locationManager:(CLLocationManager *)manager didEnterRegion:(CLRegion *)region;

  //走出某个区域之后执行
   - (void)locationManager:(CLLocationManager *)manager didExitRegion:(CLRegion *)region

实现定位的步骤

1.导入框架

#import <CoreLocation/CoreLocation.h>

2.声明全局的定位管理器

因为定位是持续性动作,如果声明为局部变量,还没有退出这个界面,定位管理器对象就会被释放,从而造成定位失败,而如果声明为全局变量,只有该界面对象被释放,这个定位管理器才会被释放。

CLLocationManager *_locationManager;

3.实例化定位管理器

_locationManager = [[CLLocationManager alloc]init];

4.判断当前系统是否打开定位服务

在设置->隐私里。这是能够控制手机上所有App的定位授权.

 if ([CLLocationManager locationServicesEnabled] == NO) 
 {

       //判断是否可以打开设置界面
       if ([[UIApplication sharedApplication] canOpenURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]]) {

             //跳转到设置页面
             [[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]];

       };

       return;
 }

5.定位授权

如果不授权就无法定位

//使用该应用时想要授权能够定位
[_locationManager requestWhenInUseAuthorization]; 

//也是授权定位,这种情况下,有时你应用没打开也会定位,如果苹果手机上有地图软件的话,你没有打开该软件,系统有时也会突然给你个提示框说某应用一直在使用定位功能,是否关闭。
// [_locationManager requestAlwaysAuthorization];

6.修改plist文件

在info.plist插入两个字段,不添加就无法定位

//都string类型,和第五步的两种授权,写入的内容会出现在定位授权提示框上
NSLocationWhenInUseUsageDescription和
NSLocationAlwaysUsageDescription

7.挂上代理

_locationManager.delegate = self;

8.使用后台定位

 _locationManager.allowsBackgroundLocationUpdates = YES;

9.设置定位信息

//设置定位精度
_locationManager.desiredAccuracy = 10;

//设置定位频率定位频率和定位精度并不应当越精确越好,需要视实际情况而定,因为越精确越耗性能,也就越费电。
CLLocationDistance distance=1.0;//1米定位一次
_locationManager.distanceFilter = distance;

10.开始追踪

[_locationManager startUpdatingLocation];

11.实现代理方法

#pragma mark delegate 
//定位成功
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations{

CLLocation *curLoc = locations.lastObject;

/* * 当前位置的经纬度 * typedef struct { CLLocationDegrees latitude; CLLocationDegrees longitude; } CLLocationCoordinate2D; * */
  CLLocationCoordinate2D coordinate = curLoc.coordinate;
  NSLog(@"经度:%f 纬度:%f",coordinate.longitude,coordinate.latitude);

  //海拔高度
  NSLog(@"海拔高度:%f",curLoc.altitude);

   //位置的精度,位置精度通过一个圆表示,实际位置可能位于这个圆内的任何地方。这个圆是由coordinate(坐标)和horizontalAccuracy(半径)共同决定的,horizontalAccuracy的值越大,那么定义的圆就越大,因此位置精度就越低。如果horizontalAccuracy的值为负,则表明coordinate的值无效。
  NSLog(@"位置的精度:%f",curLoc.horizontalAccuracy);

  //海拔高度的精度。为正值表示海拔高度的误差为对应的米数;为负表示altitude(海拔高度)的值无效。
  NSLog(@"海拔的精度:%f",curLoc.verticalAccuracy);

  //speed — 速度。该属性是通过比较当前位置和前一个位置,并比较它们之间的时间差异和距离计算得到的。鉴于Core Location更新的频率,speed属性的值不是非常精确,除非移动速度变化很小。
  NSLog(@"行驶速度:%f",curLoc.speed);

  //当前定位的日期
  NSLog(@"定位日期%@",curLoc.timestamp);

  //得到两个位置之间的距离,通过不断累加,来获取总距离
  // [curLoc distanceFromLocation:nil];

  //得到两次更新的时间之间的间隔,通过累加来获取行驶总时间
  // [curLoc.timestamp timeIntervalSinceDate:lastLoc.timestamp];

  //floor 楼层的高度 -> level 几层
  NSLog(@"当前楼层%ld层",curLoc.floor.level);

} 

 //定位失败
- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error{

   NSLog(@"定位失败%@",error);

}

总结

如果定位失败,首先检查一下几点:

定位管理器是否为全局变量
info.plist中的字段是否配置
在代码中是否做授权处理

你可能感兴趣的:(ios,地图)