So SwiftUI in 2023 makes it easier than ever to build your app using the MVVM architecture, thanks to @Observation
and @Environment
.
But at the same time, it did not address how to save the app state, which has always been the elephant in the room with SwiftUI.
Previously, I could use @AppStorage
in @ObservableObject
classes, now we can't, but it never really worked well though. It would fail intermittently.
We can use @AppStorage
in our Views and it works, but IMO we need to change these variables in the ViewModels, otherwise it breaks the concept of MVVM. Also, I may want to access some user settings it in the ViewModel because it might change the logic of some functions.
How would you guys do to save the app state in an iOS App, in order to have the same settings back even after killing and relaunching the app ?
So far I made this, and it works, but it's quite a lot of boiler plate code and I don't even know if making a macro is possible :
import SwiftUI
import Observation
enum AppStorageKeys: String {
case forceDarkMode
}
@Observable class ContentViewModel {
var forceDarkMode: Bool = UserDefaults.standard.bool(forKey: AppStorageKeys.forceDarkMode.rawValue)
}
struct ContentView: View {
var viewModel = ContentViewModel()
var body: some View {
VStack {
Text("Force Dark Mode : " + viewModel.forceDarkMode.description)
Button { viewModel.forceDarkMode.toggle() } label: {
Text("Tap to toggle UI style")
}
}
.onChange(of: viewModel.forceDarkMode) { _, newValue in
UserDefaults.standard.set(newValue, forKey: AppStorageKeys.forceDarkMode.rawValue)
}
}
}