Reputation: 1670
To get the last know geolocation, I have:
CLLocationManager * locationManager = [[CLLocationManager alloc] init];
CLLocation * lastKnownLocation = [locationManager location];
Does the lastKnownLocation reflect the last location my app has been called back with or does it reflect a global iOS system level last location (which other app or the iOS might have queried for)?
I am doing this instead of actively querying for user's location so I don't waste the user's battery.
If user has not given permission to access location, obviously lastKnownLocation should be nil. My question is specifically for the case where user has given my app permission to access location.
Upvotes: 15
Views: 7415
Reputation: 285
I had the same question now in 2023 😅 and I still couldn't find any good response using Apple Docs or Google. I also tried to ask it for ChatGPT and the answer was
The lastLocation variable in your code reflects the last known location that your app has received through the CLLocationManager object. This means that it represents the location that your app has acquired, rather than a system-level location that other apps or the iOS might have queried for.
But I also wanted to make a test using the iOS simulator. I made two apps with different bundle ids.
App A has two buttons each of them with the following functionalities:
locationManager.requestLocation()
and print the result in func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]
locationManager.location
App B has only one button with the following functionality:
locationManager.requestLocation()
and print the result in func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]
After that, I followed these steps:
new location: [<-10.00000000,-20.00000000> +/- 5.00m (speed -1.00 mps / course -1.00) @ 18/04/2023 10:45:53 Horário Padrão de BrasÃlia]
last location: Optional(<-10.00000000,-20.00000000> +/- 5.00m (speed -1.00 mps / course -1.00) @ 18/04/2023 10:45:53 Horário Padrão de BrasÃlia)
Run App B in the same iOS simulator
Set simulated location (Features > Location > Custom location) to eg. (30, 40)
Request a fresh location. The app gives me the following:
[<+30.00000000,+40.00000000> +/- 5.00m (speed -1.00 mps / course -1.00) @ 18/04/2023 10:48:44 Horário Padrão de BrasÃlia]
Run app A again
Request the last location again (Second button). The app gives me the following:
last location: Optional(<+30.00000000,+40.00000000> +/- 5.00m (speed -1.00 mps / course -1.00) @ 18/04/2023 10:48:44 Horário Padrão de BrasÃlia)
last location: Optional(<+30.00000000,+40.00000000> +/- 5.00m (speed -1.00 mps / course -1.00) @ 18/04/2023 10:48:44 Horário Padrão de BrasÃlia)
So, if the device follows the simulators, locationManager.location
should give us a global iOS system level last location.
Upvotes: 3
Reputation: 6009
I know this is an old question but for the sake of being complete and maybe others ending up here:
The CLLocationManager
class has the location
property which returns (according to official Apple docs):
The most recently retrieved user location.
This method will return nil
when no location is known.
Upvotes: 1
Reputation: 119041
Generally you should not simply rely on the existing (if any) value returned from location
unless you check its accuracy and time stamp (compared to your requirements). It's better to start startUpdatingLocation
until you get a location which does match your accuracy requirements and then either stopUpdatingLocation
or switch to stopMonitoringSignificantLocationChanges
(if available).
The location returned from location
is very dependent upon history, so you can't definitely say one way or the other that it will be. You always need to verify the accuracy for your purposes.
Upvotes: 5