iphone中GPS精确定位及反向获取地址信息

来源:互联网 发布:vb 串口扫描枪 编辑:程序博客网 时间:2024/05/03 06:05
http://blog.csdn.net/aqliuqin/article/details/7826899
今天说下GPS定位和反向解析地址的问题。

刚开始习惯性用CoreLocation.framework框架中的CLLocationManagerDelegate,获取当前的经纬度,再用经纬度反向解析出当前位置。代码如下:

.h文件

#import<UIKit/UIKit.h>

#import<CoreLocation/CoreLocation.h>

#import<MapKit/MapKit.h>

@interface FirstViewController :UIViewController <CLLocationManagerDelegate,MKMapViewDelegate>{

   CLLocationManager *lm;

}

@property (retain,nonatomicIBOutletUILabel *locationLabel;

@property (retain,nonatomicIBOutletMKMapView *map;


.m文件

#import"FirstViewController.h"

@implementation FirstViewController;

@synthesize locationLabel;

@synthesize map;

- (void)viewDidLoad

{

    [superviewDidLoad];

    lm = [[CLLocationManageralloc]init];

    lm.delegate =self;

    lm.desiredAccuracy =kCLLocationAccuracyBest;//设置最高精度

    lm.distanceFilter =kCLDistanceFilterNone;

    [lmstartUpdatingHeading];//方向

    [lmstartUpdatingLocation];//位置

    map.delegate =self;

}

- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error

{

    NSLog(@"定位出错");

}

- (void)locationManager:(CLLocationManager *)manager didUpdateToLocation:(CLLocation *)newLocation

           fromLocation:(CLLocation *)oldLocation

{

        NSLog(@"%f,%f",newLocation.coordinate.latitude,newLocation.coordinate.longitude);

    //    //解析并获取当前坐标对应得地址信息

    if ([[[UIDevicecurrentDevicesystemVersion]floatValue] >= 5.0) {

       // NSLog(@"iphone :%f",[[[UIDevice currentDevice] systemVersion] floatValue]);

        CLGeocoder *clGeoCoder = [[CLGeocoderallocinit];

        CLGeocodeCompletionHandler handle = ^(NSArray *placemarks,NSError *error)

        {

            for (CLPlacemark * placeMarkin placemarks){

                self.locationLabel.text = placeMark.name;

            }

        };

        [clGeoCoder reverseGeocodeLocation:newLocationcompletionHandler:handle];

        [clGeoCoder release];

        [manager stopUpdatingLocation];

        

    }else {

        //[self startedReverseGeoderWithLatitude:newLocation.coordinate.latitude longitude:newLocation.coordinate.longitude];

        NSLog(@"iphone :%f",[[[UIDevicecurrentDevicesystemVersion]floatValue]);

    }

}

结果解析出的地址距离实际地址相差很远,而且很不稳定。基本上是围绕实际地址2KM里内胡乱定位。开始以为,获取的经纬度是正确的,是CLGeocoder反向解析的问题。但拿获取到的经纬度在google地图中搜索时,发现定位到的位置也是不准确的。后来在苹果官方文档中找到GeocoderDemo这个例子,在网上也看了一些关于“火星坐标系”的帖子,基本确定不是反向解析的问题。详细可参考火星坐标。
对于天国设置火星坐标的缘由以及效果不发表看法,赶紧找解决办法。既然坐标有偏移量,那咱们就把偏移量去掉,取得原来的坐标。但用真机测试的过程中发现,定位不固定,怀疑这偏移量是不是一个随机量。在网上提供的解决办法中,看着就觉得麻烦。我想我就定个位而已,暂时可能开不需要这么复杂的算法。无聊中打开iphone自带的地图,发现定位比较精确,难道不是用的CLLocationManagerDelegate?果然,人家直接用的MapKit.framework框架。改了实现方法后,果然管用,定位基本上在100M的误差范围了。代码如下:
.h文件基本一致
.m文件

 (void)viewDidLoad

{

    [superviewDidLoad];


    [mapsetHidden:YES];

   map.showsUserLocation =YES;

    map.delegate = self;

}

因为要调用MKMapViewDelegate委托里的方法,需实例化一个mapview,如果在实际项目过程中不想显示地图,可以设置位Hidden。

map.showsUserLocation设置为YES,才能开启定位获取到用户当前地理位置的信息。获取后再设置为NO即可停止定位。

注意下面这个方法是MKMapViewDelegate委托里的方法,而不是CLLocationManagerDelegate委托里的方法。反向解析的代码基本一致。

- (void)mapView:(MKMapView *)mapView didUpdateUserLocation:(MKUserLocation *)userLocation {

   //CLLocationCoordinate2D coords = userLocation.location.coordinate;

    CLLocation * newLocation = userLocation.location;

  // NSLog(@"2::::::%f,%f",newLocation.coordinate.latitude,newLocation.coordinate.longitude);

    //    //解析并获取当前坐标对应得地址信息

   if ([[[UIDevicecurrentDevicesystemVersion]floatValue] >= 5.0) {

        CLGeocoder *clGeoCoder = [[CLGeocoder allocinit];

        CLGeocodeCompletionHandler handle = ^(NSArray *placemarks,NSError *error)

        {

            for (CLPlacemark * placeMark in placemarks)

            {

                self.locationLabel.text = placeMark.name;

                map.showsUserLocation = NO;

            }

        };

        [clGeoCoderreverseGeocodeLocation:newLocation completionHandler:handle];

        [clGeoCoderrelease];

    }

}


原创粉丝点击