Context
To performance operation on the Core Data object, the managed object context managedObjectContext
is needed. The context is passed into View via the environment variable inside SceneDelegate
when the project is generated with the "using Core Data" option checked (see below). A related question is Why does Core Data context object have to be passed via environment variable?
let contentView = MainView().environment(\.managedObjectContext, context)
However, when I try to pass the context
into the View Model, it complains the following
Cannot use instance member 'context' within property initializer; property initializers run before 'self' is available
struct MainView: View {
@Environment(\.managedObjectContext) var context
// Computed property cannot be used because of the property wrapper
@ObservedObject var viewModel = ViewModel(context: context)
}
class ViewModel: ObservableObject {
var context: NSManagedObjectContext
}
Adding an init()
to initialize the view model inside the view causes a different error which fails the build.
Failed to produce diagnostic for expression; please file a bug report
init() {
self.viewModel = ViewModel(context: context)
}
Question
So how can I use / get / pass the context inside the view model? What's the better way to get a context inside the view model?
MVVM is the new standard architecture One way or another, the way SwiftUI views work with the state very much resembles the classical MVVM (unless we introduce a more complex graph of programming entities). And well, you don't need a ViewController anymore.
Here is your scenario
let contentView = MainView(context: context) // << inject
.environment(\.managedObjectContext, context)
struct MainView: View {
@Environment(\.managedObjectContext) var context
@ObservedObject private var viewModel: ViewModel // << declare
init(context: NSManagedObjectContext) {
self.viewModel = ViewModel(context: context) // initialize
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With