CLLocationManager是异步的。有这个问题

问题描述 投票:0回答:2

我正在做的很简单。

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纬度和经度),而不是我的实际位置。我知道这是异步的,但我不知道如何第一次至少接通电话,所以我可以正确打印我的位置(第一次)。

我还需要它在此之后继续更新,因为我想要实时更新用户的位置。

我已尝试在func locationManager中使用fetchHomeFeed(),但这会打印出多次(“Hello:”,self.currentLocation),而我只希望fetchHomeFeed()仅被调用ONCE(具有正确的位置),之后这个位置被连续调用,因为我将使用另一种方法。

我不确定如何实现这一点。

ios swift asynchronous cllocation
2个回答
0
投票

来自documentation for didUpdateLocations

地点

包含位置数据的CLLocation对象数组。此数组始终包含至少一个表示当前位置的对象。如果延迟更新或者在交付之前多个位置到达,则阵列可能包含其他条目。数组中的对象按它们出现的顺序组织。因此,最近的位置更新位于数组的末尾。

因此,您不需要遍历位置数组,只需使用locations.last,除非您的应用程序需要担心延迟的位置更新。

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

如果你想只调用fetchHomeFeed一次有几个选项,但最简单的是你在调用它之前检查的布尔标志,并在第一次调用它时更改它。


0
投票

从viewDidLoad中删除fetchHomeFeed。这是不对的。

在您的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()
        }
    }
© www.soinside.com 2019 - 2024. All rights reserved.