題外話:
-
在移動互聯網時代,移動app能解決用戶的很多生活瑣事,比如
- 導航:去任意陌生的地方
- 周邊:找餐館,找酒店,找銀行,找電影院
-
在上述應用中都用到了地圖和定位功能,在iOS開發中,要想加入這2大功能,必須基于2個框架進行開發
- Map Kit :用于地圖展示
- Core Location:用于地理定位
-
兩個專業術語:
- LBS :Location Based Service (基于定位的服務)
- SoloMo : Social Local mobile (所羅門)
1.CoreLocation框架的使用
CoreLocation框架使用的前提
導入框架(需要注意的Xcode5以后不需要手動導入,以前需要手動導入)
導入頭文件 #import <CoreLocation/CoreLocation.h>
1.CoreLocation框架使用須知
2.CoreLocation框架中所有的數據類型的前綴都是CL
3.CoreLocation 中使用CLLocationManger 對象來做用戶定位
-
最主要的5步(不要怕,很簡單,相信我,試著敲下來)
1.創建CoreLocation 管理者(最好采用懶加載,管理者對象永遠不死)
-(CLLocationManager *)locationManger { if (!_locationManger) { //1.創建CoreLocation 管理者 _locationManger = [[CLLocationManager alloc]init]; } return _locationManger; }
2.成為CoreLocation 管理者的代理監聽獲取到的位置(遵守協議)
self.locationManger.delegate = self;
3.定位授權,還需要在在info.plist里面進行配置(僅僅在大于等于ios8里面才要求用戶主動授權,這是出于對安全性的要求)
//授權(這是一個方法) if ([[UIDevice currentDevice].systemVersion doubleValue] >= 8.0) { NSLog(@"是ios8"); //主動要求用戶對我們的程序授權,授權狀態改變就會通知代理 [self.locationManger requestAlwaysAuthorization];//請求前臺和后臺定位權限 //[self.locationManger requestWhenInUseAuthorization];//請求前臺定位權限 } else { NSLog(@"不是iOS8"); }
** 配置的方法:點擊 requestAlwaysAuthorization **
4.開始監聽(開始獲取位置)
[self.locationManger startUpdatingLocation];
NSLog(@"開始定位");
5.實現代理方法
/*
* 獲取到位置信息之后就會被調用
*
* @param manger 觸發事件的對象
*
* @param locations 獲取到的位置
*/
//這步操作是很耗電的(一定要設置定位暫停)
-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations
{
NSLog(@"%s",__func__);
[self.locationManger stopUpdatingLocation];
NSLog(@"定位結束");
}
對于上面其他的一些設置
1.設置獲取位置的精確度
如:self.locationManger.distanceFilter = kCLLocationAccuracyNearestTenMeters;
kCLLocationAccuracyBestForNavigation
kCLLocationAccuracyBest;
kCLLocationAccuracyNearestTenMeters;
kCLLocationAccuracyHundredMeters;
kCLLocationAccuracyKilometer;
kCLLocationAccuracyThreeKilometers;
2.設置多久距離獲取一次location
self.locationManger.distanceFilter = 500; //filter |?f?lt?(r) 過濾
3.何時開啟定位?(獲取權限之后)
-(void)locationManager:(CLLocationManager *)manager didChangeAuthorizationStatus:(CLAuthorizationStatus)status
{
/*
//1.用戶從未選擇過授權
kCLAuthorizationStatusNotDetermined = 0
//2.無法使用定位服務,該狀態用戶無法改變
kCLAuthorizationStatusRestricted
//3.用戶拒絕該應用定服務,或是定位服務總開關出于關閉狀態
kCLAuthorizationStatusDenied
//4.已經授權(廢棄)
kCLAuthorizationStatusAuthorized
//5.用戶允許該程序無論何時都可以使用地理信息
kCLAuthorizationStatusAuthorizedAlways
//6.用戶同意程序在可見時使用地理位置
kCLAuthorizationStatusAuthorizedWhenInUse
****"最主要是后兩個:定位成功"******
*/
if (status == kCLAuthorizationStatusNotDetermined) {
NSLog(@"等待用戶授權");
}else if (status == kCLAuthorizationStatusAuthorizedAlways || status == kCLAuthorizationStatusAuthorizedWhenInUse)
{
NSLog(@"授權成功");
//4.開始監聽(開始獲取位置)
[self.locationManger startUpdatingLocation];
NSLog(@"開始定位");
}else
{
NSLog(@"授權失敗");
}
}
2.打印定位信息
latitude |?l?t?tju?d, American -tu?d| 緯度
longitude |?l?nd??tju?d, American ?l??nd??tu?d| 經度
degree |d??gri?| 度
coordinate |k?????d?n?t |noun 坐標
//7.監聽定位信息
-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations
{
CWLog(@"%s",__func__);
//8.獲取CLLocation對象(獲取用戶最后一次的位置)
/*
location.coordinate; 坐標,包含經緯度
location.altitude;設置海拔高度,單位是米
location.course;設置前進方向 0表示北 90東 180南 270西
location.horizontalAccuracy; 水平精準度
location.verticalAccuracy; 垂直精準度
location.timeatamp;定位信息返回的時間
location.speed; 設備移動速度 單位是米/秒 ,適于行車速度而不太適于步行
*/
/*
可以設置模擬器的速度
bicycle ride 騎車速度
run 跑步
freeway drive 告訴公路駕車
*/
CLLocation *location = [locations lastObject];
NSLog(@"經度=%f 緯度=%f speed = %f",location.coordinate.latitude,location.coordinate.longitude,location.speed);
//如果只需要獲取一次,可以獲取到位置之后就停止
//[self.locationManager stopUpdatingLocation];
CWLog(@"關閉定位");
}
3.回顧一下CLLocationManger 的常用操作
1.開始用戶定位
-(void)startUpdatingLocation;2.停止用戶定位
-(void)stopUpdatingLocation;當用戶調用了startUpdatingLocation的方法之后,就開始不斷地定位用戶的位置,中途會頻繁的調用代理的下面方法
-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations
location 參數里面裝著CLLocation的對象
4.有關-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations方法里面的一些操作(做一個類似導航的東西,界面自己布局)
聲明
//上一次的位置
@property(nonatomic,strong)CLLocation *previousLocation;//previous |?pri?v??s| 先前的
//計算總的距離
@property(nonatomic,assign)CLLocationDistance sumDistance;
//記錄總時間
@property(nonatomic,assign)NSTimeInterval sumTime;
方法的實現
//6.定位調用
-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations
{
CWLog(@"定位信息打印");
/* CLLocation 屬性
timestap 獲取到當前位置信息的時間
*/
/*
獲取走了多遠(用這一次的位置減去上一次的時間)
獲取走這段路花了多長時間(這一次的時間減去上一次的時間)
獲取速度(走了多遠 / 花了多少時間)
獲取總共走的路程 (把每次獲取到走了多遠累加起來)
獲取平均速度 (總路程 / 總時間)
*/
CLLocation *newlocation = [locations lastObject];
if (self.previousLocation != nil) {
//計算兩次的距離(單位是米)
CLLocationDistance distance = [newlocation distanceFromLocation:self.previousLocation];
//計算兩次之間的時間(單位是秒)
NSTimeInterval dTime = [newlocation.timestamp timeIntervalSinceDate:self.previousLocation.timestamp];
//計算速度(米/秒)
CGFloat speed = distance/dTime;
CWLog(@"距離=%f 時間=%f 速度=%f ",distance,dTime,speed);
//累加時間
self.sumTime += dTime;
//累加距離
self.sumDistance += distance;
//計算平均速度
CGFloat averangeSpeed = self.sumDistance/self.sumTime;
CWLog(@"兩次之間的距離=%f 時間=%f 當前速度=%f 全程時間= %f 全程距離= %f 全程的平均速度 = %f",distance,dTime,speed,self.sumTime,self.sumDistance,averangeSpeed);
}
//記錄上一次的位置
self.previousLocation = newlocation;
}
提示:
CLLocationDistance distance = [newlocation distanceFromLocation:self.previousLocation];很重要獲取兩個位置之間的距離