How to get Current Location with SwiftUI?

后端 未结 3 985
你的背包
你的背包 2020-12-15 09:07

Trying to get current location with using swiftUI. Below code, couldn\'t initialize with didUpdateLocations delegate.

class GetLocation : BindableObject {         


        
相关标签:
3条回答
  • 2020-12-15 09:23

    This code below works (Not production ready). Implementing the CLLocationManagerDelegate works fine and the lastKnownLocation is updated accordingly.

    Don't forget to set the NSLocationWhenInUseUsageDescription in your Info.plist

    class LocationManager: NSObject, CLLocationManagerDelegate, BindableObject {
        private let manager: CLLocationManager
        var didChange = PassthroughSubject<LocationManager, Never>()
    
        var lastKnownLocation: CLLocation? {
            didSet {
                didChange.send(self)
            }
        }
    
        init(manager: CLLocationManager = CLLocationManager()) {
            self.manager = manager
            super.init()
        }
    
        func startUpdating() {
            self.manager.delegate = self
            self.manager.requestWhenInUseAuthorization()
            self.manager.startUpdatingLocation()
        }
    
        func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
            print(locations)
            lastKnownLocation = locations.last
        }
    
        func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {
            if status == .authorizedWhenInUse {
                manager.startUpdatingLocation()
            }
        }
    }
    
    0 讨论(0)
  • 2020-12-15 09:40

    As of Xcode 11 beta 4, you will need to change didChange to willChange:

    var willChange = PassthroughSubject<LocationManager, Never>()
    
    var lastKnownLocation: CLLocation? {
        willSet {
            willChange.send(self)
        }
    }
    
    0 讨论(0)
  • 2020-12-15 09:49

    I have written a one-file swift package with usage instructions on https://github.com/himbeles/LocationProvider. It provides a ObservableObject-type wrapper class for CLLocationManager and its delegate. There is a published property location which can directly be used in SwiftUI, as well as a PassthroughSubject that you can subscribe to via Combine. Both update on every didUpdateLocations event of the CLLocationManager.

    It also handles the case where location access has previously been denied: The default behavior is to present the user with a request to enable access in the app settings and a link to go there.

    In SwiftUI, use as

    import SwiftUI
    import LocationProvider
    
    struct ContentView: View {
        @ObservedObject var locationProvider : LocationProvider
    
        init() {
            locationProvider = LocationProvider()
            do {try locationProvider.start()} 
            catch {
                print("No location access.")
                locationProvider.requestAuthorization()
            }
        }
    
        var body: some View {
            VStack{
            Text("latitude \(locationProvider.location?.coordinate.latitude ?? 0)")
            Text("longitude \(locationProvider.location?.coordinate.longitude ?? 0)")
            }
        }
    }
    
    0 讨论(0)
提交回复
热议问题