CLLocationManager является асинхронным.Возникли проблемы с этим - PullRequest
0 голосов
/ 19 марта 2019

То, что я делаю, очень просто.

class HomeDatasourceController: UICollectionViewController, CLLocationManagerDelegate{
let locationManager:CLLocationManager = CLLocationManager()

//CurrentLocation is my variable that isn't changing on time
var currentLocation = CLLocation(latitude: 5.0, longitude: 5.0)

override func viewDidLoad() {
    super.viewDidLoad()


    locationManager.delegate = self
    locationManager.requestAlwaysAuthorization()
    self.locationManager.startUpdatingLocation()


    fetchHomeFeed()
}

func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
    for currentLocationTemp in locations {
        self.currentLocation = currentLocationTemp
        print("This is latitude: \(currentLocation.coordinate.latitude) , and this is longitude: \(currentLocation.coordinate.longitude)")
    }
}
fetchHomeFeed(){
    print("Hello: ", self.currentLocation)
}

Когда вызывается fetchHomeFeed, он только распечатывает фиктивное местоположение, в котором я его установил (широта и долгота 5.0), а не мое фактическое местоположение. Я знаю, что это асинхронно, но я не уверен, как получить вызов по крайней мере ОДИН РАЗ в первый раз, чтобы я мог правильно распечатать свое местоположение (в первый раз).

Мне также необходимо продолжить обновление после этого, потому что я хочу, чтобы в режиме реального времени обновлялось местоположение пользователя.

Я пытался использовать fetchHomeFeed () внутри func locationManager, но это распечатывает ("Hello:", self.currentLocation) несколько раз, и я хочу, чтобы fetchHomeFeed () вызывался только ОДИН РАЗ (с правильным расположением) и после этого местоположение будет вызываться непрерывно, так как у меня будет другой метод, использующий это.

Я не уверен, как это реализовать.

Ответы [ 2 ]

0 голосов
/ 20 марта 2019

Удалить fetchHomeFeed из viewDidLoad.Это не правильно.

Сделайте это в вашей функции locationManager.Это гарантирует, что у вас есть действительное местоположение.Вы останавливаете менеджер местоположения, как только вы получили действительное местоположение, и перезапускаете при необходимостиЕсли вы хотите постоянно отслеживать местоположение, вам нужно переосмыслить решение, но это даст вам представление.

func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {

        guard let location = locations.last else {
               return
        }

        if location.horizontalAccuracy > 0 {
             locationManager.stopUpdatingLocation()
             locationManager.delegate = nil
             fetchHomeFeed()
        }
    }
0 голосов
/ 19 марта 2019

Из документации для didUpdateLocations :

местоположения

Массив объектов CLLocation, содержащий данные местоположения.Этот массив всегда содержит хотя бы один объект, представляющий текущее местоположение.Если обновления были отложены или если до их доставки было доставлено несколько мест, массив может содержать дополнительные записи.Объекты в массиве организованы в порядке их появления.Следовательно, самое последнее обновление местоположения находится в конце массива.

Так что вам не нужно циклически перемещаться по массиву местоположений, вы можете просто использовать locations.lastесли вашему приложению не нужно беспокоиться об отложенных обновлениях местоположения.

func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
    if let location = locations.last {
        currentLocation = location
    }
}

И если вы хотите, чтобы fetchHomeFeed вызывался только один раз, когда есть несколько опций, но самый простой - это логический флаг, который вы проверяете перед вызовом ивы меняете его в первый раз, когда он вызывается.

...