I did this but in this whole contentView is loading again and the app is coming to the start screen.
struct ThemeChangeDemoApp: App {
@AppStorage("theme") var currentThemeRawValue: String = "dark"
var body: some Scene {
WindowGroup {
switch currentThemeRawValue {
case Theme.dark.rawValue:
ContentView().environment(\.colorScheme, .dark)
case Theme.light.rawValue:
ContentView().environment(\.colorScheme, .light)
default:
ContentView().environment(\.colorScheme, .dark)
}
}
}
}
And from here I am changing the theme. I am saving the rawValue of the enum as "dark" or "light".
struct Settings: View {
var body: some View {
Button {
let currentTheme = UserDefaultsHelper.getCurrentTheme()
switch currentTheme {
case Theme.dark.rawValue:
UserDefaultsHelper.saveTheme(theme: .light)
case Theme.light.rawValue:
UserDefaultsHelper.saveTheme(theme: .dark)
default:
UserDefaultsHelper.saveTheme(theme: .light)
}
} label: {
Text("Toggle theme")
}
}
}
CodePudding user response:
WindowGroup {
switch currentThemeRawValue {
case Theme.dark.rawValue:
ContentView().environment(\.colorScheme, .dark)
case Theme.light.rawValue:
ContentView().environment(\.colorScheme, .light)
default:
ContentView().environment(\.colorScheme, .dark)
}
}
The switch statement means that SwiftUI is populating the view with conditional content, so it would rebuild the entire hierarchy if the value changes. You only really want to change the environment value itself, so something like this would probably be better:
WindowGroup {
ContentView()
.environment(\.colorScheme, currentThemeRawValue == "dark" ?? .dark : .light)
}