I am trying to implement dark theme in my app.
I am using Android Preferences DataStore to save user preference for theme.
The datastore class exposes a flow for preferred theme themeFLow
and a suspend function updateTheme()
to update the preferred theme.
I have a ThemeManager class to manage theme changes. It looks like this.
class ThemeManager {
private val currentTheme = themeDataStore.themeFlow
init {
scope.launch(Dispatchers.Main) {
currentTheme.collect {
AppCompatDelegate.setDefaultNightMode(it)
}
}
}
fun setCurrentTheme(newTheme: Int) {
scope.launch {
themeDataStore.updateTheme(newTheme)
}
}
}
In UI, I display a dialog box to choose current theme and call themeManager.setCurrentTheme(newTheme)
The problem is that theme changes with a flicker. See video (slowed down)
Other SO answers on this question (like this and this) provide a solution which involves finishing and restarting the activity. In my app, I am following a single activity + fragments architecture (using Jetpack Navigation Library), so when I restart activity like this, activity starts from home fragment and the current destination is lost.
Is there some way to get rid of this flickering?