I'm creating an app in SwiftUI, where I want to have @Observed class keeping selected tab and maybe navigation path in the future. Architecture I'm working on is MVVM. Currently when I switch tab and Navigator class is changed, all Views in TabView are re-created. They are not preserving the state. When I'm moving selectedTab value to @State it works fine.
import SwiftUI
@Observable
class Navigator {
var selectedTab = Tab.one
}
enum Tab: Equatable {
case one, two
}
struct ContentView: View {
@State private var navigator = Navigator()
var body: some View {
TabView(selection: $navigator.selectedTab) {
PageOne(viewModel: ViewModel(count: 0))
.tabItem { Text("one") }
.tag(Tab.one)
PageTwo(viewModel: ViewModel(count: 0))
.tabItem { Text("two") }
.tag(Tab.two)
}
.padding()
}
}
struct PageOne: View {
var viewModel: ViewModel
var body: some View {
VStack {
Button("increase page One") {
viewModel.count += 1
}
Text("Current count \(viewModel.count)")
}
}
}
@Observable
class ViewModel {
var count: Int
init(count: Int) {
self.count = count
}
}
struct PageTwo: View {
var viewModel: ViewModel
var body: some View {
VStack {
Button("increase page two") {
viewModel.count += 1
}
Text("Current count \(viewModel.count)")
}
}
}
You should hold on to the models, otherwise they will be lost on re-rendering the body: