背景
因為蘋果在不允許使用第三方庫進行定位,即使是百度地圖的定位也是在蘋果API的基礎上進行了封裝,所以學習下iOS中定位的功能還是有必要的
CoreLocation框架
-
CLLocationManager是一個非常重要的對象
//位置服務是否可用
+ (BOOL)locationServicesEnabled __OSX_AVAILABLE_STARTING(__MAC_10_7,__IPHONE_4_0);
//方向服務是否可用
+ (BOOL)headingAvailable __OSX_AVAILABLE_STARTING(__MAC_10_7,__IPHONE_4_0);
//每隔指定距離定位一次(米)
@property(assign, nonatomic) CLLocationDistance distanceFilter;
//定位精度,精度越高需要定位的時間越長,越耗電
@property(assign, nonatomic) CLLocationAccuracy desiredAccuracy;
CLLocationManager 定位的結果一般會通過代理CLLocationManagerDelegate中的方法返回,具體使用方法請參考頭文件
獲取用戶權限
- iOS8之前
如果想要定位需要在plist文件中位置keyPrivacy - Location Usage Description,默認只在前臺定位,如果想開啟后臺定位需要在開啟后臺模式
Snip20150825_1.png - iOS8
需要在plist文件中配置NSLocationWhenInUseUsageDescription(前臺定位)
NSLocationAlwaysUsageDescription(前后臺定位)
并且需要在代碼中去請求相應的權限
//請求前臺定位權限
- (void)requestWhenInUseAuthorization __OSX_AVAILABLE_STARTING(__MAC_NA, __IPHONE_8_0);
//請求前后臺定位權限,即使當前權限為前臺定位也會生效
- (void)requestAlwaysAuthorization __OSX_AVAILABLE_STARTING(__MAC_NA, __IPHONE_8_0);
注意:如果是前臺定位權限,但是開始了后臺模式,在后臺也是可以定位的,但是屏幕的上邊會有藍條,提示用戶是哪個應用在定位
iOS 9
如果想要在后臺定位,除了配置NSLocationAlwaysUsageDescription(前后臺定位)外,還需要手動設置allowsBackgroundLocationUpdates = YES
監(jiān)聽角度的改變
//每隔多少度監(jiān)聽一次
@property(assign, nonatomic) CLLocationDegrees headingFilter __OSX_AVAILABLE_STARTING(__MAC_NA,__IPHONE_3_0);
//設備開始監(jiān)聽設備角度的改變,即設備的朝向
- (void)startUpdatingHeading __OSX_AVAILABLE_STARTING(__MAC_NA,__IPHONE_3_0);
//監(jiān)聽到改變后調用此代理方法
- (void)locationManager:(CLLocationManager *)manager
didUpdateHeading:(CLHeading *)newHeading __OSX_AVAILABLE_STARTING(__MAC_NA,__IPHONE_3_0);
區(qū)域監(jiān)聽
//開始監(jiān)聽
- (void)startMonitoringForRegion:(CLRegion *)region __OSX_AVAILABLE_STARTING(__MAC_TBD,__IPHONE_5_0);
//請求監(jiān)聽區(qū)域
- (void)requestStateForRegion:(CLRegion *)region __OSX_AVAILABLE_STARTING(__MAC_NA,__IPHONE_7_0);
//進入該區(qū)域會調用此代理方法
- (void)locationManager:(CLLocationManager *)manager
didEnterRegion:(CLRegion *)region __OSX_AVAILABLE_STARTING(__MAC_10_7,__IPHONE_4_0);
//離開該區(qū)域是調用此代理方法
- (void)locationManager:(CLLocationManager *)manager didExitRegion:(CLRegion *)region __OSX_AVAILABLE_STARTING(__MAC_10_7,__IPHONE_4_0);
//判斷狀態(tài)(是否在該區(qū)域內)
- (void)locationManager:(CLLocationManager *)manager
didDetermineState:(CLRegionState)state forRegion:(CLRegion *)region __OSX_AVAILABLE_STARTING(__MAC_NA,__IPHONE_7_0);
示例代碼
// 區(qū)域監(jiān)聽
/** 位置管理者 */
@property (nonatomic, strong) CLLocationManager *manager;
CLLocationCoordinate2D center = {維度, 經度};
CLCircularRegion *region = [[CLCircularRegion alloc] initWithCenter:center radius:區(qū)域半徑 identifier:對該區(qū)域的描述];
//開始監(jiān)聽區(qū)域狀態(tài)
[self.manager startMonitoringForRegion:region];
//開始請求區(qū)域狀態(tài)
[self.manager requestStateForRegion: region]
// 進入區(qū)域
-(void)locationManager:(CLLocationManager *)manager didEnterRegion:(CLRegion *)region
{
NSLog(@"進入區(qū)域--%@", region.identifier);
}
// 離開區(qū)域
-(void)locationManager:(CLLocationManager *)manager didExitRegion:(CLRegion *)region
{
NSLog(@"離開區(qū)域--%@", region.identifier);
}
//判斷狀態(tài)
-(void)locationManager:(CLLocationManager *)manager didDetermineState:(CLRegionState)state forRegion:(CLRegion *)region
{
NSLog(@"%zd", state);
}
