2015-01-02 9 views
30

All'inizio del 2014, Apple ha aggiornato iOS 7.0 a 7.1 per consentire aggiornamenti di posizione anche quando l'app non è attiva in primo piano e non in background. Come lo facciamo?Ricevi aggiornamenti di posizione per l'app iOS anche se sospeso

Ho letto alcuni articoli come Apple's iOS 7.1 will fix a geolocation bug. Ma Apple non ha fornito molte comunicazioni relative a questo né alcun codice di esempio su come ottenere l'aggiornamento della posizione anche quando l'app viene uccisa/interrotta/sospesa.

Ho letto il Release Notes for iOS 7.1. Non ho trovato nulla di simile a questo.

Quindi, come possiamo ottenere l'aggiornamento della posizione per iOS 7 e 8 anche quando l'app è sospesa?

risposta

73

Dopo mesi di prove ed errori sperimentando la struttura centrale, ho trovato la soluzione per ottenere l'aggiornamento della posizione anche quando l'app viene uccisa/sospesa. Funziona bene sia per iOS 7 e 8.

Ecco la soluzione: -

Se la vostra applicazione è un'applicazione mobile basata luogo che ha bisogno di monitorare la posizione del dispositivo quando ha cambiamenti significativi, l'iOS ti restituirà alcune coordinate di posizione quando il dispositivo si è spostato a più di 500 metri dall'ultima posizione nota. Sì, anche quando l'app viene uccisa/sospesa dall'utente o da iOS, è comunque possibile ottenere gli aggiornamenti della posizione.

Quindi, per ottenere un aggiornamento della posizione per locationManager anche quando l'app viene uccisa/sospesa, è necessario utilizzare il metodo startMonitoringSignificantLocationChanges, non è possibile utilizzare startUpdatingLocation.

Quando iOS vuole restituire l'aggiornamento della posizione all'app, ti aiuterà a riavviare l'app e restituire una chiave UIApplicationLaunchOptionsLocationKey al metodo delegato dell'app didFinishLaunchingWithOptions.

La chiave UIApplicationLaunchOptionsLocationKey è molto importante e devi sapere come gestirla. È necessario creare una nuova istanza locationManager quando si riceve la chiave e si otterrà l'aggiornamento della posizione sul metodo delegato locationManager didUpdateLocations.

Ecco il codice di esempio: -

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions{ 
    self.shareModel = [LocationShareModel sharedModel]; 

    if ([launchOptions objectForKey:UIApplicationLaunchOptionsLocationKey]) { 
     self.shareModel.anotherLocationManager = [[CLLocationManager alloc]init]; 
     self.shareModel.anotherLocationManager.delegate = self; 
     self.shareModel.anotherLocationManager.desiredAccuracy = kCLLocationAccuracyBestForNavigation; 
     self.shareModel.anotherLocationManager.activityType = CLActivityTypeOtherNavigation; 

     if(IS_OS_8_OR_LATER) { 
     [self.shareModel.anotherLocationManager requestAlwaysAuthorization]; 
     } 

    [self.shareModel.anotherLocationManager startMonitoringSignificantLocationChanges]; 

    }  
     return YES; 
} 

Oltre al metodo didFinishLaunchingWithOptions, ho creato l'istanza locationManager quando l'applicazione è attiva. Ecco alcuni esempi di codice:

- (void)applicationDidEnterBackground:(UIApplication *)application 
{ 
    [self.shareModel.anotherLocationManager stopMonitoringSignificantLocationChanges]; 

    if(IS_OS_8_OR_LATER) { 
     [self.shareModel.anotherLocationManager requestAlwaysAuthorization]; 
    } 

    [self.shareModel.anotherLocationManager startMonitoringSignificantLocationChanges]; 
} 

- (void)applicationDidBecomeActive:(UIApplication *)application 
{ 
    if(self.shareModel.anotherLocationManager) 
     [self.shareModel.anotherLocationManager stopMonitoringSignificantLocationChanges]; 

    self.shareModel.anotherLocationManager = [[CLLocationManager alloc]init]; 
    self.shareModel.anotherLocationManager.delegate = self; 
    self.shareModel.anotherLocationManager.desiredAccuracy = kCLLocationAccuracyBestForNavigation; 
    self.shareModel.anotherLocationManager.activityType = CLActivityTypeOtherNavigation; 

    if(IS_OS_8_OR_LATER) { 
     [self.shareModel.anotherLocationManager requestAlwaysAuthorization]; 
    } 

    [self.shareModel.anotherLocationManager startMonitoringSignificantLocationChanges]; 
} 

Ho scritto un articolo che spiega sui dettagli su come ottenere l'aggiornamento posizione per iOS 7 e 8 anche quando l'applicazione viene ucciso/sospesa. Ho anche caricato il codice sorgente completo su GitHub con i passaggi su come testare questa soluzione.

Si prega di visitare i seguenti URL per maggiori informazioni: -

  1. Getting Location Updates for iOS 7 and 8 when the App is Killed/Terminated/Suspended
  2. Source Code on GitHub - Get the Location Updates Even when the iOS mobile apps is Suspended/Terminated/Killed
+1

"È necessario creare una nuova istanza locationManager quando si riceve la chiave" - ​​Sembra un po 'di confusione, intendi esattamente "NUOVA istanza di locationManager"? Ho una istanza condivisa di locationManager nel mio progetto - posso solo riutilizzarla? –

+5

Buona domanda. Quando l'app è sospesa, anche il locationManager condiviso creato in precedenza verrà cancellato dalla memoria. Come riutilizzare un'istanza che non esiste nella memoria? Quindi, creare una nuova istanza è l'unico modo. – Ricky

+0

Ciao Ricky, ottima risposta. Solo una domanda: lo stesso metodo può essere applicato al gestore di localizzazione standard rispetto al solo gestore di posizioni di modifica significativo? – Pacemaker

0
locationManager = [[CLLocationManager alloc] init]; 
#define IS_OS_8_OR_LATER ([[[UIDevice currentDevice] systemVersion] floatValue] >= 8.0) 


if(IS_OS_8_OR_LATER) 
{ 
    [locationManager requestWhenInUseAuthorization]; 
} 

locationManager.delegate = self; 
locationManager.distanceFilter = kCLDistanceFilterNone; //whenever we move 
locationManager.desiredAccuracy = kCLLocationAccuracyHundredMeters; 

[locationManager startUpdatingLocation]; 

che aggiornamento del codice di localizzazione utente unica applicazione forground in esecuzione ma non correre sfondo

[locationManager requestWhenInUseAuthorization]; 
Problemi correlati