-->

recieving位置更新的应用程序被终止后,(recieving location updates

2019-06-25 09:31发布

我需要跟踪用户位置的所有的时间(但不消耗电池)。 我的理解应用程序是使用startMonitoringSignificantLocationChanges终止后获取更新的唯一途径。

从startMonitoringSignificantLocationChanges苹果的位置感知编程指南:

如果启动该服务,并您的应用程序随后终止,如果一个新的事件到达时,系统会自动将重新启动应用程序进入后台。 在这种情况下,选择字典传递到应用程序中:didFinishLaunchingWithOptions:您的应用程序委托的方法中包含的关键UIApplicationLaunchOptionsLocationKey,表明您的应用程序,因为定位事件的启动。 在重新开张,你还必须配置一个位置管理对象,并调用该方法可以继续接收位置的事件。 当您重新启动位置服务,当前事件被立即传送到您的委托。 此外,你的位置管理对象的位置属性填入您启动定位服务甚至在最近的位置的对象。

我会很高兴,如果有人可以在代码演示了(举个例子)我应该使用哪些方法

在下面的代码我我特林: - 启动在的appdelegate外景经理这strats的signinficant显示器改变更新和startupdating。 - 在didUpdateToLocation我打电话stopupdating - 在didFinishLaunchingWithOptions当我检查,如果我为了知道有一个UIApplicationLaunchOptionsLocationKey如果我在后台我并推出了由于siginificant监控位置更新。 - 如果是的话,我再打电话startMonitoringSignificantLocationChanges(不知道为什么......),并开始调用startupdating方法UIBackgeoundTaskIdentifier。

LocationController.m : 
+ (LocationController*)sharedInstance {
    @synchronized(self) {
        if (sharedCLDelegate == nil) {
            [[self alloc] init];
        }
    }
    return sharedCLDelegate;
}

- (id)init
{
    self = [super init];
    if (self != nil) {
        self.locationManager = [[[CLLocationManager alloc] init] autorelease];
        self.locationManager.delegate = self;
        self.locationManager.desiredAccuracy = kCLLocationAccuracyNearestTenMeters;
        [self.locationManager startUpdatingLocation];
        [self.locationManager startMonitoringSignificantLocationChanges];

    }
    return self;
}
- (void) startMonitoringSignificantLocationChanges
{
    [self.locationManager startMonitoringSignificantLocationChanges];
}
- (void) stopMonitoringSignificantLocationChanges
{
    [self.locationManager stopMonitoringSignificantLocationChanges];
}
-(void) start{
    [self.locationManager startUpdatingLocation];
}
- (void)locationManager:(CLLocationManager *)manager 
    didUpdateToLocation:(CLLocation *)newLocation 
           fromLocation:(CLLocation *)oldLocation{
    if ( abs([newLocation.timestamp timeIntervalSinceDate: [NSDate date]]) < 30) {
        self.lastLocation = newLocation;
        [self updateLocation]; //sending location to server
        [self.locationManager stopUpdatingLocation];
    }
}
- (void)locationManager:(CLLocationManager*)manager
       didFailWithError:(NSError*)error{
    [self.locationManager stopUpdatingLocation];
}

AppDelegate.h : 

@interface AppDelegate : NSObject <UIApplicationDelegate> {
    UIBackgroundTaskIdentifier bgTask;
}

AppDelegate.m : 

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {    
        id locationValue = [launchOptions objectForKey:UIApplicationLaunchOptionsLocationKey];
        if (locationValue) {
            [[LocationController sharedInstance] startMonitoringSignificantLocationChanges];
            UIApplication *app  = [UIApplication sharedApplication];
            bgTask = [app beginBackgroundTaskWithExpirationHandler:^{ 
                [app endBackgroundTask:bgTask]; 
                bgTask = UIBackgroundTaskInvalid;
            }];
            [[LocationController sharedInstance] start]; //startupdating
            return YES;
        }
    else { 
            [[LocationController sharedInstance] init];
    }
}
-(void) applicationDidEnterBackground:(UIApplication *) application
{
    NSLog(@"entered background Mode");
}

-(void) applicationDidBecomeActive:(UIApplication *) application
{
    NSLog(@"application Did Become Active");
}

谢谢。

Answer 1:

使用你的类,这是我会做什么。

在你AppDelegate.m,当你的应用程序是在前台或后台,我会移动CLLocationManager在前台/后台匹配运行。 我这样做的原因是因为如果CLLocationManager不会移动到后台时,应用程序在后台运行,没有位置更新发送到CLLocationManager的回调

- (void)applicationDidEnterBackground:(UIApplication *) application {
    [[LocationController sharedInstance] stop];
    [[LocationController sharedInstance] startMonitoringSignificantLocationChanges];
    NSLog(@"entered background Mode");
}

- (void)applicationDidBecomeActive:(UIApplication *) application {
    [[LocationController sharedInstance] stopMonitoringSignificantLocationChanges];
    [[LocationController sharedInstance] start];
    NSLog(@"application Did Become Active");
}

因此,可以说您的应用程序,然后移动到背景,一段时间后,iOS的决定是使用了太多的内存,并杀死你的应用程序。

几分钟后,iOS设备则接收位置更新和重生你的应用程序,让它知道它的位置服务重生所致。 然后,您需要重新启动后台位置服务,因为这将是你的应用程序有这样做的唯一机会。

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {    
    if ([launchOptions objectForKey:UIApplicationLaunchOptionsLocationKey]) {
        [[LocationController sharedInstance] startMonitoringSignificantLocationChanges];
    }
    return YES;
}

哦,最后一个变化,我不知道为什么在你locationManager:didUpdateToLocation:fromLocation:方法你停止位置服务,当你这样做没有更多的更新来通过的。 只要把它运行,然后每一个位置的改变是通过你的时间可以发送到服务器。

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

    if ( abs([newLocation.timestamp timeIntervalSinceDate: [NSDate date]]) < 30) {
        self.lastLocation = newLocation;
        [self updateLocation]; //sending location to server

}


文章来源: recieving location updates after app is terminated