Swift 始终调用 LocationManager didChangeAuthorizationStatus

Swift LocationManager didChangeAuthorizationStatus Always Called

我有一个实现 CLLocationManagerDelegate 的视图控制器。我创建了一个 CLLocationManager 变量:

let locationManager = CLLocationManager()

然后在viewDidLoad,我设置属性:

// Set location manager properties
locationManager.delegate = self
locationManager.desiredAccuracy = kCLLocationAccuracyHundredMeters
locationManager.distanceFilter = 50

问题是在我检查授权状态之前就调用了该函数。

func locationManager(manager: CLLocationManager!, didChangeAuthorizationStatus status: CLAuthorizationStatus) {
    if (status == .AuthorizedWhenInUse) {
        // User has granted autorization to location, get location
        locationManager.startUpdatingLocation()
    }
}

任何人都可以告诉我是什么导致了这种情况发生吗?

- locationManager:didChangeAuthorizationStatus:CLLocationManager 初始化后不久被调用。

如果需要,您可以在委托方法中请求授权:

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
    }
}

请注意,如果您想让它起作用,您需要在 'timely' 事务中分配代理人。

如果您以某种方式延迟委托分配,例如通过异步设置,您可能会错过对 - locationManager:didChangeAuthorizationStatus:.

的初始调用

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
        }
    }

其他答案可能会引入新的不良行为。

您可以只添加一个布尔值和一个守卫来防止第一次调用,并附上一些解释错误的评论:

var firstTimeCalled = true

// ...    

func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {

    guard !firstTimeCalled else {
        firstTimeCalled = false
        return
    }

    // ... send status to listeners
}