I’m working with a view that shows a listing of areas. When a consumer faucets on a location, a didSet
block containing a Activity
is triggered in a separate class wrapped with the @ObservedObject
property:
struct LocationSearch: View {
@StateObject var locationService = LocationService()
@IbservedObject var networking: Networking
var savedLocations = SavedLocations()
var physique: some View {
ForEach(locationService.searchResults, id: .self) { location in
Button(location.title) {
getCoordinate(addressString: location.title) { coordinates, error in
if error == nil {
networking.lastLocation = CLLocation(latitude: coordinates.latitude, longitude: coordinates.longitude)
// watch for networking.locationString to replace
// this smells unsuitable
// the best way to higher await Activity completion in didSet?
DispatchQueue.predominant.asyncAfter(deadline: .now() + 1) {
savedLocations.all.append(networking.locationString!.locality!)
UserDefaults.normal.set(savedLocations.all, forKey: "savedLocations")
dismiss()
}
}
}
}
}
}
}
The Activity
that will get triggered after netowrking.lastLocation
is about is as follows:
class Networking: NSObject, ObservableObject, CLLocationManagerDelegate {
@Printed public var lastLocation: CLLocation? {
didSet {
Activity {
getLocationString() { placemark in
self.locationString = placemark
}
getMainWeather(self.lastLocation?.coordinate.latitude ?? 0, self.lastLocation?.coordinate.longitude ?? 0)
getAQI(self.lastLocation?.coordinate.latitude ?? 0, self.lastLocation?.coordinate.longitude ?? 0)
locationManager.stopUpdatingLocation()
}
}
}
What’s a greater approach to make sure that the duty has had time to finish and that the brand new string will likely be saved to UserDefaults
versus freezing my software’s UI for one second?
In case it is not clear, if I do not watch for one second, as an alternative of the brand new worth of locationString
being saved to UserDefaults
, the previous worth is saved as an alternative as a result of the logic within the didSet
block hasn’t had time to finish.