美文网首页
iOS CoreLocation 定位实现

iOS CoreLocation 定位实现

作者: 骑行怪状 | 来源:发表于2016-05-02 18:33 被阅读385次
    Simulator Screen Shot 2016年5月2日 下午9.22.02.png

    CoreLocation 定位 iOS 地图 反编码


    CoreLocation 实现基于 8.0 之后的使用方法, 8.0 前后使用方法是有区别的。

    相关框架,类注释 API:

    • CoreLocation 框架主要用于地理定位,地理编码等。
    • CoreLocation 框架中使用 CLLocationManager 对象来做用户定位
    • CLGeocoder 根据地址关键字, 进行地理编码, 通过地址获取经纬度.
    • CLPlacemark 存储坐标数据,对于一个给定的经度和纬度。标数据包含的信息,如国家,州,城市,街道地址指定的坐标。它也可以包括点利息和地理位置相关的数据。此类有16个属性、1个实例方法。

    创建流程:

    • 创建定位管理对象
    • 设置定位管理对象(设置过滤、设置定位精度)
    • 设置定位管理对象的代理
    • 实现<CLLocationManagerDelegate>协议里的代理方法
    • 开始定位

    首先导入 CoreLocation.framework 框架,并在 VC 中引入头文件,签订协议

    #import <CoreLocation/CoreLocation.h>
     <CLLocationManagerDelegate>
    
    导入 CoreLocation.framework 框架导入 CoreLocation.framework 框架

    iOS 8.0 之后要注意,从iOS 8.0开始,苹果进一步加强了对用户隐私的保护。
    当app想访问用户的隐私时,系统不再自动弹出一个对话框让用户授

    (1) 调用ios8.0的api。主动请求用户授权
    -(void)requestAlwaysAuthorization // 请求允许在前后台都能获取用户位置的授权
    -(void)requestWhenInUseAuthorization // 请求允许在前台获取用户位置的授权(注意:当设置为前台授权时,通过设置后台模式:location updates后
    也可以后台获取定位信息,但是屏幕上方会出现蓝条)

    在Info.plist文件中添加如下配置:

    (1)NSLocationAlwaysUsageDescription

    (2)NSLocationWhenInUseUsageDescription

    添加的这两个描述为弹窗的提示内容

    添加允许添加允许

    代码示例:

       desiredAccuracy 属性枚举值:
        kCLLocationAccuracyBestForNavigation    最适合导航
        kCLLocationAccuracyBest    精度最好的
        kCLLocationAccuracyNearestTenMeters    附近10米
        kCLLocationAccuracyHundredMeters    附近100米
        kCLLocationAccuracyKilometer    附近1000米
        kCLLocationAccuracyThreeKilometers    附近3000米
    
    #import "ViewController.h"
    #import <CoreLocation/CoreLocation.h>
    
    @interface ViewController ()<CLLocationManagerDelegate>
    //位置管理器
    @property(nonatomic,strong)CLLocationManager *locMgr;
    //位置编码
    @property(nonatomic, strong)CLGeocoder *coder;
    
    @end
    
    @implementation ViewController
    
    
    #pragma mark-懒加载
    - (CLLocationManager *)locMgr{
            if (!_locMgr ) {
                
                //1.创建位置管理器(定位用户的位置)
                self.locMgr=[[CLLocationManager alloc]init];
                //2.设置代理
                self.locMgr.delegate=self;
            }
            return _locMgr;
         }
    
    // 位置编码
    - (CLGeocoder *)coder{
    
        // _coder == nil
        if (!_coder) {
            
            self.coder = [[CLGeocoder alloc] init];
        }
        return _coder;
    }
    
    
    - (void)viewDidLoad {
        [super viewDidLoad];
        // Do any additional setup after loading the view, typically from a nib.
        
    
        //判断用户定位服务是否开启
        if ([CLLocationManager locationServicesEnabled]) {
            
        // iOS 8 之后添加 始终允许访问位置信息, 请求前台定位授权, 并在Info.Plist文件中配置Key ( Nslocationwheninuseusagedescription )
            [self.locMgr requestAlwaysAuthorization];
        //当用户使用的时候授权
        [locationManager requestWhenInUseAuthorization];
            
        //开始定位用户的位置
        [self.locMgr startUpdatingLocation];
        //每隔多少米定位一次(这里的设置为任何的移动)
        self.locMgr.distanceFilter = kCLDistanceFilterNone;
        //设置定位的精准度,一般精准度越高,越耗电(这里设置为精准度最高的,适用于导航应用)
         self.locMgr.desiredAccuracy=kCLLocationAccuracyBestForNavigation;
           
    
            
        }else
        {//不能定位用户的位置
            //1.提醒用户检查当前的网络状况
            //2.提醒用户打开定位开关
        }
        
        //测试方法,计算两个位置之间的距离
        [self countDistance];
        
        
    }
    
    
    #pragma mark-CLLocationManagerDelegate
    /**
     *  当定位到用户的位置时,就会调用(调用的频率比较频繁)
     */
    -(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations
    {
        //locations数组里边存放的是CLLocation对象,一个CLLocation对象就代表着一个位置
        CLLocation *loc = [locations firstObject];
        
        NSLog(@"定位到了");
        //维度:loc.coordinate.latitude
        //经度:loc.coordinate.longitude
        NSLog(@"纬度=%f,经度=%f",loc.coordinate.latitude,loc.coordinate.longitude);
        NSLog(@"%lu",(unsigned long)locations.count);
    
        
        // 反编码
       
        [self.coder reverseGeocodeLocation:loc completionHandler:^(NSArray *placemarks, NSError *error) {
            
            // 包含区,街道等信息的地标对象
            CLPlacemark *placemark = [placemarks firstObject];
            // 城市名称
            NSString *city = placemark.locality;
            // 街道名称
            NSString *street = placemark.thoroughfare;
            // 全称
            NSString *name = placemark.name;
            NSString *str = [NSString stringWithFormat:@"%@, %@, %@", name,city,street];
            
            NSLog(@"城市信息%@", str);
    
        }];
        
        
        //停止更新位置(如果定位服务不需要实时更新的话,那么应该停止位置的更新)
        [self.locMgr stopUpdatingLocation];
    
    }
    
    
    // 定位错误的代理方法
    - (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error
    {
        if ([error code] == kCLErrorDenied)
        {
            //访问被拒绝
            NSLog(@"访问被拒绝");
        }
        if ([error code] == kCLErrorLocationUnknown) {
            //无法获取位置信息
             NSLog(@"无法获取位置信息");
        }
    }
    
    
    
    
    
    //计算两个位置之间的距离
    -(void)countDistance
    {
        //根据经纬度创建两个位置对象
        CLLocation *loc1=[[CLLocation alloc]initWithLatitude:40 longitude:116];
        CLLocation *loc2=[[CLLocation alloc]initWithLatitude:41 longitude:116];
        //计算两个位置之间的距离
        CLLocationDistance distance=[loc1 distanceFromLocation:loc2];
        NSLog(@"(%@)和(%@)的距离=%fM",loc1,loc2,distance);
    }
    

    感谢:

    http://www.jianshu.com/p/964b19ef0225
    http://www.jianshu.com/p/ddbb722066f6

    Demo 下载地址:

    https://github.com/qixingguaizhuang/MapDemo

    相关文章

      网友评论

          本文标题: iOS CoreLocation 定位实现

          本文链接:https://www.haomeiwen.com/subject/uwelrttx.html