定期iOS的后台位置更新-- 相关资料收集,待有时间进行整理
2015-07-29 12:52
706 查看
1,材料一:(http://codego.net/610454/)
我正在写,需要具有高精确度和低频率的后台位置更新的应用程序。该解决方案似乎是一个后台任务的启动位置管理器的更新,然后关机。这个问题已经被问过: 我如何获得一个后台位置更新每隔n分钟在我的iPhone应用程序? 位置的应用程序分钟后每隔n去背景 iOS的不是典型的背景定位轨迹问题 iOS的长期运行的背景,“位置”背景模式 iOS的基于位置的轨迹全后台服务 但我还没有得到工作的最小的例子。在尝试上述接受答案的每一个排列,我把一个起点。进入后台:
和
目前的行为是backgroundTimeRemaining180秒至零(在记录的位置),然后将到期处理程序执行和不产生进一步的位置更新。如何修改上面的代码,以便接收在后台周期性位置更新下去? 更新:我针对iOS的7似乎有证据表明,后台任务有不同的行为: 从后台任务启动位置管理器中的iOS 7
似乎stopUpdatingLocation是什么触发了看门狗的背景,所以我在更换它didUpdateLocation有:
这似乎有效断电的全局定位系统。选择为背景NSTimer然后
我做的是定期切换的准确性得到高精度的坐标每隔几分钟和locationManager一直没有停止,backgroundTimeRemaining保持在其最大值。从〜每小时10%这减少电池消耗(恒定kCLLocationAccuracyBest在背景中),以每小时1〜2%我的设备上。
2. 如果你有UIBackgroundModes在你的plist出现,location键,那么你就不需要beginBackgroundTaskWithExpirationHandler方法。这是多余的。还错误地’它(见这里),但是这毫无意义 CodeGo.net,因为你的plist设置。 同UIBackgroundModes location在plist中的应用程序将继续在后台只能无限期只要运行CLLocationManger正在运行。如果你打电话stopUpdatingLocation而在后台,然后应用程序将停止,将无法再次启动。 也许你可以调用beginBackgroundTaskWithExpirationHandler之前调用stopUpdatingLocation然后调用后startUpdatingLocation你可以调用endBackgroundTask以保持中背景而GPS已停止,但我从来没有尝试过的-它只是一个想法。 另一种选择(我没试过)是保持位置管理器,同时在后台运行,但一旦你得到一个准确的位置改变requiredAccuracy财产1000米或更高,以使GPS芯片得到关闭(以保存电池)。然后10多分钟后,当你需要另一个位置更新,改变requiredAccuracy回至100m打开GPS,直到你得到一个准确的位置,重复。 当你调用startUpdatingLocation上的位置管理,你必须给它得到一个位置。你不应该调用stopUpdatingLocation。我们让它最多10秒运行,直到我们得到一个非缓存的高精度定位。 你需要过滤掉缓存的位置,并检查你确保你的最低要求的精度(见这里)位置的准确性。你得到的优先个更新可能是10分钟或10天之久。优先精度你可能3000米。 在显著位置变化的API来代替.a旦你获得了显著变更通知,你可以开始CLLocationManager几秒钟获得高精度的位置。我不能肯定,我已经在显著位置变更服务。
3. 怎么样给它一个尝试startMonitoringSignificantLocationChanges:API?这肯定与激发频率较低,准确度是相当不错的。此外,它有很多其他的优点locationManager的API。 关于这个API很多已经是这个链接
4. 你需要通过添加下列键添加的位置更新模式,在你的应用程序
didUpdateToLocation方法会被调用(即使你的应用程序是在后台)。您可以在通话的base进行任何东西
2,材料二:(http://blog.sina.com.cn/s/blog_7581a4c301015b27.html)
工作中碰到一个定位的应用场景:app需要在后台运行,实时上传用户地理位置。
苹果对iOS的规范性在提升了app的品质的同时也带来了对开发者的限制。翻阅了各种官方文档和资料,得出结论如下:
1、实现后台定位有2种方式:
standard location service(调用CLLocationManager的startUpdatingLocation)
significant-change location service(调用CLLocationManager 的startMonitoringSignificantLocationChanges)
2、两者区别:
前者(startUpdatingLocation)是标准定位,想要在后台使用必须在info.plist文件中增加Required background modes属性,并选择App registers for location updates值。
前者(startUpdatingLocation)在后台运行时可能会因为资源问题被系统挂起(suspend)或终止(terminate),但一旦有更新会被唤起,但是当更新时系统任然资源紧张,则会被延迟调用委托。如果对于实时性要求高的可能不适合这个,很难控制用户机器性能状况。
前者(startUpdatingLocation)如果被用户手动关闭,就不会再被唤醒。
前者定位基于gps/基站/wifi定位,具体使用哪一种CoreLocation框架有一套自己的规则。
后者(startMonitoringSignificantLocationChanges)是使用基站定位的,所以设备一定要有电话模块,在plist中可以设置xx属性来限制可被下载安装的设备。
后者(startMonitoringSignificantLocationChanges)不管是在后台还是用户手动关闭都会被唤醒调用委托,只有3种方法可以阻止它的更新。(1)用户关闭定位服务(2)用户关闭对该app的定位服务(3)设备处于飞行模式或者无法开启必要的硬件(猜测是定位模块的硬件)。
后者(startMonitoringSignificantLocationChanges)什么时候更新呢?是在更换基站的时候更新。所以更新频率与基站密度有关。市区更新频率较郊区高。所以很多同学说没有更新是因为还在同一组基站范围内。
前者较后者耗电且精度高。
3、两者共性:
两者都更新位置信息时都回调相同的委托方法:-(void)locationManager:(CLLocationManager )manager didUpdateLocations:(NSArray )locations;
4、上传信息:
由于后台任务只分配了有限时间执行必要的操作,所以如果在超时之前未完成(比如网络请求),app将会被终止。这里有一个方法,可以申请额外的10分钟让你执行想要的操作,申请后台任务:beginBackgroundTaskWithExpirationHandler(不详细说了,使用方法可以查一下资料)。
5、总结:
2种方式各有利弊,根据使用场景而决定,前台运行的app通常要求准确实时定位,并且运行时间有限,考虑用第一种标准定位,比如导航应用。如果移动速度快(距离变化明显),长时间定位(监控),可以考虑后者,比如打车应用。
reference:
[1]http://www.mindsizzlers.com/2011/07/ios-background-location/
[2]https://developer.apple.com/library/ios/#documentation/UserExperience/Conceptual/LocationAwarenessPG/CoreLocation/CoreLocation.html
3,NSTimer在后台运行(http://outofmemory.cn/code-snippet/8327/NSTimer-backend-run)
这段代码可以放在
- (void)applicationWillResignActive:(UIApplication )application
或者
- (void)applicationDidEnterBackground:(UIApplication )application 中,当然,当程序重新被激活的时候,需要将timer invalidate掉。
我正在写,需要具有高精确度和低频率的后台位置更新的应用程序。该解决方案似乎是一个后台任务的启动位置管理器的更新,然后关机。这个问题已经被问过: 我如何获得一个后台位置更新每隔n分钟在我的iPhone应用程序? 位置的应用程序分钟后每隔n去背景 iOS的不是典型的背景定位轨迹问题 iOS的长期运行的背景,“位置”背景模式 iOS的基于位置的轨迹全后台服务 但我还没有得到工作的最小的例子。在尝试上述接受答案的每一个排列,我把一个起点。进入后台:
- (void)applicationDidEnterBackground:(UIApplication *)application { self.bgTask = [[UIApplication sharedApplication] beginBackgroundTaskWithExpirationHandler:^{ NSLog(@"ending background task"); [[UIApplication sharedApplication] endBackgroundTask:self.bgTask]; self.bgTask = UIBackgroundTaskInvalid; }]; self.timer = [NSTimer scheduledTimerWithTimeInterval:60 target:self.locationManager selector:@selector(startUpdatingLocation) userInfo:nil repeats:YES]; }
和
- (void)locationManager:(CLLocationManager *)manager didUpdateToLocation:(CLLocation *)newLocation fromLocation:(CLLocation *)oldLocation { NSLog(@"%@", newLocation); NSLog(@"background time: %f", [UIApplication sharedApplication].backgroundTimeRemaining); [self.locationManager stopUpdatingLocation]; }
目前的行为是backgroundTimeRemaining180秒至零(在记录的位置),然后将到期处理程序执行和不产生进一步的位置更新。如何修改上面的代码,以便接收在后台周期性位置更新下去? 更新:我针对iOS的7似乎有证据表明,后台任务有不同的行为: 从后台任务启动位置管理器中的iOS 7
似乎stopUpdatingLocation是什么触发了看门狗的背景,所以我在更换它didUpdateLocation有:
[self.locationManager setDesiredAccuracy:kCLLocationAccuracyThreeKilometers]; [self.locationManager setDistanceFilter:99999];
这似乎有效断电的全局定位系统。选择为背景NSTimer然后
- (void) changeAccuracy { [self.locationManager setDesiredAccuracy:kCLLocationAccuracyBest]; [self.locationManager setDistanceFilter:kCLDistanceFilterNone]; }
我做的是定期切换的准确性得到高精度的坐标每隔几分钟和locationManager一直没有停止,backgroundTimeRemaining保持在其最大值。从〜每小时10%这减少电池消耗(恒定kCLLocationAccuracyBest在背景中),以每小时1〜2%我的设备上。
2. 如果你有UIBackgroundModes在你的plist出现,location键,那么你就不需要beginBackgroundTaskWithExpirationHandler方法。这是多余的。还错误地’它(见这里),但是这毫无意义 CodeGo.net,因为你的plist设置。 同UIBackgroundModes location在plist中的应用程序将继续在后台只能无限期只要运行CLLocationManger正在运行。如果你打电话stopUpdatingLocation而在后台,然后应用程序将停止,将无法再次启动。 也许你可以调用beginBackgroundTaskWithExpirationHandler之前调用stopUpdatingLocation然后调用后startUpdatingLocation你可以调用endBackgroundTask以保持中背景而GPS已停止,但我从来没有尝试过的-它只是一个想法。 另一种选择(我没试过)是保持位置管理器,同时在后台运行,但一旦你得到一个准确的位置改变requiredAccuracy财产1000米或更高,以使GPS芯片得到关闭(以保存电池)。然后10多分钟后,当你需要另一个位置更新,改变requiredAccuracy回至100m打开GPS,直到你得到一个准确的位置,重复。 当你调用startUpdatingLocation上的位置管理,你必须给它得到一个位置。你不应该调用stopUpdatingLocation。我们让它最多10秒运行,直到我们得到一个非缓存的高精度定位。 你需要过滤掉缓存的位置,并检查你确保你的最低要求的精度(见这里)位置的准确性。你得到的优先个更新可能是10分钟或10天之久。优先精度你可能3000米。 在显著位置变化的API来代替.a旦你获得了显著变更通知,你可以开始CLLocationManager几秒钟获得高精度的位置。我不能肯定,我已经在显著位置变更服务。
3. 怎么样给它一个尝试startMonitoringSignificantLocationChanges:API?这肯定与激发频率较低,准确度是相当不错的。此外,它有很多其他的优点locationManager的API。 关于这个API很多已经是这个链接
4. 你需要通过添加下列键添加的位置更新模式,在你的应用程序
<key>UIBackgroundModes</key> <array> <string>location</string> </array>
didUpdateToLocation方法会被调用(即使你的应用程序是在后台)。您可以在通话的base进行任何东西
2,材料二:(http://blog.sina.com.cn/s/blog_7581a4c301015b27.html)
工作中碰到一个定位的应用场景:app需要在后台运行,实时上传用户地理位置。
苹果对iOS的规范性在提升了app的品质的同时也带来了对开发者的限制。翻阅了各种官方文档和资料,得出结论如下:
1、实现后台定位有2种方式:
standard location service(调用CLLocationManager的startUpdatingLocation)
significant-change location service(调用CLLocationManager 的startMonitoringSignificantLocationChanges)
2、两者区别:
前者(startUpdatingLocation)是标准定位,想要在后台使用必须在info.plist文件中增加Required background modes属性,并选择App registers for location updates值。
前者(startUpdatingLocation)在后台运行时可能会因为资源问题被系统挂起(suspend)或终止(terminate),但一旦有更新会被唤起,但是当更新时系统任然资源紧张,则会被延迟调用委托。如果对于实时性要求高的可能不适合这个,很难控制用户机器性能状况。
前者(startUpdatingLocation)如果被用户手动关闭,就不会再被唤醒。
前者定位基于gps/基站/wifi定位,具体使用哪一种CoreLocation框架有一套自己的规则。
后者(startMonitoringSignificantLocationChanges)是使用基站定位的,所以设备一定要有电话模块,在plist中可以设置xx属性来限制可被下载安装的设备。
后者(startMonitoringSignificantLocationChanges)不管是在后台还是用户手动关闭都会被唤醒调用委托,只有3种方法可以阻止它的更新。(1)用户关闭定位服务(2)用户关闭对该app的定位服务(3)设备处于飞行模式或者无法开启必要的硬件(猜测是定位模块的硬件)。
后者(startMonitoringSignificantLocationChanges)什么时候更新呢?是在更换基站的时候更新。所以更新频率与基站密度有关。市区更新频率较郊区高。所以很多同学说没有更新是因为还在同一组基站范围内。
前者较后者耗电且精度高。
3、两者共性:
两者都更新位置信息时都回调相同的委托方法:-(void)locationManager:(CLLocationManager )manager didUpdateLocations:(NSArray )locations;
4、上传信息:
由于后台任务只分配了有限时间执行必要的操作,所以如果在超时之前未完成(比如网络请求),app将会被终止。这里有一个方法,可以申请额外的10分钟让你执行想要的操作,申请后台任务:beginBackgroundTaskWithExpirationHandler(不详细说了,使用方法可以查一下资料)。
5、总结:
2种方式各有利弊,根据使用场景而决定,前台运行的app通常要求准确实时定位,并且运行时间有限,考虑用第一种标准定位,比如导航应用。如果移动速度快(距离变化明显),长时间定位(监控),可以考虑后者,比如打车应用。
reference:
[1]http://www.mindsizzlers.com/2011/07/ios-background-location/
[2]https://developer.apple.com/library/ios/#documentation/UserExperience/Conceptual/LocationAwarenessPG/CoreLocation/CoreLocation.html
3,NSTimer在后台运行(http://outofmemory.cn/code-snippet/8327/NSTimer-backend-run)
这段代码可以放在
- (void)applicationWillResignActive:(UIApplication )application
或者
- (void)applicationDidEnterBackground:(UIApplication )application 中,当然,当程序重新被激活的时候,需要将timer invalidate掉。
UIApplication *app = [UIApplication sharedApplication]; __block UIBackgroundTaskIdentifier bgTask = [app beginBackgroundTaskWithExpirationHandler:^{ dispatch_async(dispatch_get_main_queue(), ^{ if (bgTask != UIBackgroundTaskInvalid) { [app endBackgroundTask:bgTask]; bgTask = UIBackgroundTaskInvalid; } }); }]; dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ testTimer = [NSTimer scheduledTimerWithTimeInterval:(0.01) target:self selector:@selector(doSomeTest) userInfo:nil repeats:YES]; [testTimer fire]; [[NSRunLoop currentRunLoop] addTimer:testTimer forMode:NSRunLoopCommonModes]; [[NSRunLoop currentRunLoop] run]; dispatch_async(dispatch_get_main_queue(), ^{ if (bgTask != UIBackgroundTaskInvalid) { [app endBackgroundTask:bgTask]; bgTask = UIBackgroundTaskInvalid; } }); });
相关文章推荐
- HDU 1017 A Mathematical Curiosity
- IOS 值得注意的地方
- iOS HTML图片本地预览
- ios 获取屏幕的属性和宽度
- iOS开发多线程篇—多线程简单介绍
- 防止在iOS设备中的Safari将数字识别为电话号码
- iOS手动内存管理
- iOS中锁的应用
- IOS CoreText
- ios的一种简单的模糊效果
- iOS字符串和可变字符串
- 百度地图iOS SDK开发教程(珍藏版)
- ios 使用GCD 多线程 教程
- iOS 手势识别器概述
- iOS各版本图标尺寸汇总
- 使用PhoneGap打包HTML成iOS应用
- IOS 整体框架类图值得收藏
- ios文件预览以及使用其他应用打开文件
- 申请苹果加急审核
- 9秒学院教你如何成为iOS开发达人