在上文中遵守CLLocationManagerDelegate协议方法 我们可以从其locations获取一下信息
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations{
CLLocation* location=[locations lastObject];
NSLog(@"%f %f",location.coordinate.latitude,location.coordinate.longitude);
/**
location.coordinate; 坐标, 包含经纬度
location.altitude; 设备海拔高度 单位是米
location.course; 设置前进方向 0表示北 90东 180南 270西
location.horizontalAccuracy; 水平精准度
location.verticalAccuracy; 垂直精准度
location.timestamp; 定位信息返回的时间
location.speed; 设备移动速度 单位是米/秒, 适用于行车速度而不太适用于不行
*/
}
下面说下指南针的使用与实现
定义一个UIImageView对象
@property (strong ,nonatomic) UIImageView* imageView;
设置一个图片
self.imageView=[[UIImageView alloc]initWithFrame:CGRectMake(0, 0, self.view.frame.size.width, self.view.frame.size.width)];
[self.imageView setImage:[UIImage imageNamed:@"zhinan.jpg"]];
self.imageView.center=CGPointMake(self.view.center.x, self.view.center.y);
[self.view addSubview:self.imageView];
实现指南针旋转功能
//当获取到用户方向就会调用,CLLocationManagerDelegate协议方法
- (void)locationManager:(CLLocationManager *)manager didUpdateHeading:(CLHeading *)newHeading{
/**
magneticHeading 设备与磁北的相对角度
trueHeading 设置与真北的相对角度, 必须和定位一起使用, iOS需要设置的位置来计算真北
真北始终指向地理北极点
磁北对应随着时间变化的地球磁场北极*/
//将获取的角度转换为弧度
CGFloat angle=newHeading.magneticHeading * M_PI / 180;
//旋转图片
self.imageView.transform=CGAffineTransformIdentity;
self.imageView.transform=CGAffineTransformMakeRotation(-angle);
}
效果:旋转手机,手机上的图片会随之旋转,且一直指向北方。(旋转功能需要使用真机测试,模拟器无法模拟)
接下来是对区域的监听
@interface ViewController ()<CLLocationManagerDelegate>
@property (strong ,nonatomic) CLLocationManager *manager;
@end
- (void)viewDidLoad {
[super viewDidLoad];
self.manager.delegate = self;
//如果为iOS8,想进行区域监测,必须自己请求获取用户隐私的权限(还需在Info.plist文件中添加一项属性,详细操作请见MapKit/CoreLocation使用(一))
if ([[UIDevice currentDevice].systemVersion doubleValue] >= 8.0) {
[self.manager requestAlwaysAuthorization];
}
//开始检测用户所在区域
/**
创建区域
CLRegion 有两个子类是专门用于指定区域的:
一个专门指定蓝牙范围/一个指定圆形的范围*/
// 创建中心点,东西经各180度,南北纬各90度。
CLLocationCoordinate2D center=CLLocationCoordinate2DMake(39.91405,116.399669);
//创建圆形区域,指定中心点的经纬度以及半径
CLCircularRegion *circular = [[CLCircularRegion alloc] initWithCenter:center radius:500 identifier:@"天安门"];
[self.manager startMonitoringForRegion:circular];
}
#pragma mark - CLLocationManagerDelegate
//进入监听区域时调用
- (void)locationManager:(CLLocationManager *)manager didEnterRegion:(CLRegion *)region{
NSLog(@"进入监听区域");
}
//离开监听区域时调用
- (void)locationManager:(CLLocationManager *)manager didExitRegion:(CLRegion *)region{
NSLog(@"离开监听区域");
}
#pragma mark - 懒加载
- (CLLocationManager *)manager{
if (!_manager) {
_manager=[[CLLocationManager alloc] init];
}
return _manager;
}
@end
运行的结果如下图:首先我们使用模拟器将模拟器位置修改为监听区域范围内(如果不知道怎么打开模拟器位置,请见MapKit/CoreLocation使用(一))
之后我们再将模拟器位置修改为监听区域外,经纬度没增加1大概相当于111km。
CLGeocoder
CLGeocoder可以完成“地理编码”以及“反地理编码”。
地理编码:根据给定的定名,获得其具体的位置。例如经纬度,地址的全称等。
反地理编码: 就是根据给定的经纬度,获取具体的位置信息。
地理编码的实现
@interface ViewController ()
//创建地理编码对象
@property (nonatomic ,strong) CLGeocoder *geoder;
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
//利用地理编码对象编码
//根据传入的地址获取该地址对应的经纬度信息
[self.geoder geocodeAddressString:@"北京" completionHandler:^(NSArray *placemarks, NSError *error) {
//placemarks地标数组,存放着地标,每一个地标包含了该位置的经纬度以及城市/区域/国家代码/邮编等
CLPlacemark *placeMark=[placemarks firstObject];
NSLog(@"%@",placeMark);
}];
}
- (CLGeocoder *)geoder{
if (_geoder == nil) {
_geoder = [[CLGeocoder alloc] init];
}
return _geoder;
}
@interface ViewController ()
//创建地理编码对象
@property (nonatomic ,strong) CLGeocoder *geoder;
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
CLLocation *location = [[CLLocation alloc] initWithLatitude:39.91405 longitude:116.399669];
[self.geoder reverseGeocodeLocation:location completionHandler:^(NSArray *placemarks, NSError *error) {
for (CLPlacemark *placeMark in placemarks) {
NSLog(@"%@",placeMark);
}
}];
}
- (CLGeocoder *)geoder{
if (_geoder == nil) {
_geoder = [[CLGeocoder alloc] init];
}
return _geoder;
}
github网址:https://github.com/intuit/LocationManager
注意:iOS8需要在Info.plist文件中添加NSLocationAlwaysUsageDescription和NSLocationWhenInUseUsageDescript这两个键值
#import "ViewController.h"
#import "INTULocationManager.h"
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
INTULocationManager *manager= [INTULocationManager sharedInstance];
//获取当前的位置
[manager requestLocationWithDesiredAccuracy:INTULocationAccuracyRoom timeout:10 block:^(CLLocation *currentLocation, INTULocationAccuracy achievedAccuracy, INTULocationStatus status) {
if (status == INTULocationStatusSuccess) {
NSLog(@"获取位置成功");
}else{
NSLog(@"获取位置失败");
}
}];
//持续获取位置
[manager subscribeToLocationUpdatesWithBlock:^(CLLocation *currentLocation, INTULocationAccuracy achievedAccuracy, INTULocationStatus status) {
NSLog(@"%f %f",currentLocation.coordinate.latitude,currentLocation.coordinate.longitude);
}];
}
@end