Reputation: 3176
I have a view controller which implements the CLLocationManagerDelegate
. I create a the CLLocationManager variable:
let locationManager = CLLocationManager()
Then in the viewDidLoad
, I set properties:
// Set location manager properties
locationManager.delegate = self
locationManager.desiredAccuracy = kCLLocationAccuracyHundredMeters
locationManager.distanceFilter = 50
The problem comes that the function gets called even before I check the authorization status.
func locationManager(manager: CLLocationManager!, didChangeAuthorizationStatus status: CLAuthorizationStatus) {
if (status == .AuthorizedWhenInUse) {
// User has granted autorization to location, get location
locationManager.startUpdatingLocation()
}
}
Can anyone inform me what could be causing this to occur?
Upvotes: 33
Views: 19158
Reputation: 1392
- locationManager:didChangeAuthorizationStatus:
is called shortly after the CLLocationManager
is initialised.
You can request authorization inside the delegate method if you want:
func locationManager(manager: CLLocationManager!, didChangeAuthorizationStatus status: CLAuthorizationStatus) {
switch status {
case .notDetermined:
locationManager.requestAlwaysAuthorization()
break
case .authorizedWhenInUse:
locationManager.startUpdatingLocation()
break
case .authorizedAlways:
locationManager.startUpdatingLocation()
break
case .restricted:
// restricted by e.g. parental controls. User can't enable Location Services
break
case .denied:
// user denied your app access to Location Services, but can grant access from Settings.app
break
default:
break
}
}
Be aware that you need to assign the delegate in a 'timely' matter if you want this to work.
If you would somehow delay the delegate assignment, e.g. by setting it asynchronously, you might miss the initial call to - locationManager:didChangeAuthorizationStatus:
.
Upvotes: 59
Reputation: 10921
The other answers could introduce new undesirable behaviors.
You can just add a boolean and a guard to prevent the first call, with some comments explaining the bug :
var firstTimeCalled = true
// ...
func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {
guard !firstTimeCalled else {
firstTimeCalled = false
return
}
// ... send status to listeners
}
Upvotes: 3
Reputation: 27221
Swift 3
func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {
switch status {
case .notDetermined:
manager.requestAlwaysAuthorization()
break
case .authorizedWhenInUse:
manager.startUpdatingLocation()
break
case .authorizedAlways:
manager.startUpdatingLocation()
break
case .restricted:
// restricted by e.g. parental controls. User can't enable Location Services
break
case .denied:
// user denied your app access to Location Services, but can grant access from Settings.app
break
}
}
Upvotes: 7