Skip to content

Commit efab97d

Browse files
Apply theme changes instantly instead of requiring a restart (#476)
Picking a new theme now recreates the current activity right away. Since the app has two activities (MainActivity and SettingsActivity), ThemingCallback also checks on every activity resume whether the saved theme differs from what that activity was created with, and recreates it too, so MainActivity picks up the change as soon as you back out of Settings instead of needing a full app restart. Removes the now-inaccurate "restart to apply" summary and string.
1 parent caf9965 commit efab97d

9 files changed

Lines changed: 32 additions & 20 deletions

File tree

app/app/src/main/java/com/github/livingwithhippos/unchained/base/ThemingCallback.kt

Lines changed: 30 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -13,21 +13,42 @@ import com.github.livingwithhippos.unchained.settings.view.SettingsFragment.Comp
1313
import com.github.livingwithhippos.unchained.settings.view.SettingsFragment.Companion.THEME_NIGHT
1414
import com.github.livingwithhippos.unchained.settings.view.ThemeItem
1515
import com.github.livingwithhippos.unchained.utilities.extension.getThemeList
16+
import java.util.WeakHashMap
1617

1718
class ThemingCallback(val preferences: SharedPreferences) : Application.ActivityLifecycleCallbacks {
1819

20+
// theme resource id each currently alive activity was (re)created with, so a change made
21+
// while another activity is on top can be detected and applied on resume, see #305
22+
private val appliedThemes = WeakHashMap<Activity, Int>()
23+
1924
override fun onActivityCreated(activity: Activity, savedInstanceState: Bundle?) {
20-
val themeRes =
21-
preferences.getInt(
22-
SettingsFragment.KEY_THEME_NEW,
23-
R.style.Theme_Unchained_Material3_Green_One,
24-
)
25+
val themeRes = currentThemeRes()
2526
val themesList = activity.applicationContext.getThemeList()
2627
val currentTheme: ThemeItem = themesList.find { it.themeID == themeRes } ?: themesList[1]
2728
setupNightMode(currentTheme.nightMode)
28-
if (activity is AppCompatActivity) setCustomTheme(activity, themeRes)
29+
if (activity is AppCompatActivity) {
30+
setCustomTheme(activity, themeRes)
31+
appliedThemes[activity] = themeRes
32+
}
33+
}
34+
35+
override fun onActivityResumed(activity: Activity) {
36+
if (activity !is AppCompatActivity) return
37+
val themeRes = currentThemeRes()
38+
val appliedThemeRes = appliedThemes[activity]
39+
if (appliedThemeRes != null && appliedThemeRes != themeRes) {
40+
// avoid re-triggering on the recreated instance's own resume
41+
appliedThemes.remove(activity)
42+
activity.recreate()
43+
}
2944
}
3045

46+
private fun currentThemeRes(): Int =
47+
preferences.getInt(
48+
SettingsFragment.KEY_THEME_NEW,
49+
R.style.Theme_Unchained_Material3_Green_One,
50+
)
51+
3152
private fun setCustomTheme(activity: Activity, themeRes: Int) {
3253
activity.setTheme(themeRes)
3354
/*
@@ -39,15 +60,15 @@ class ThemingCallback(val preferences: SharedPreferences) : Application.Activity
3960

4061
override fun onActivityStarted(activity: Activity) {}
4162

42-
override fun onActivityResumed(activity: Activity) {}
43-
4463
override fun onActivityPaused(activity: Activity) {}
4564

4665
override fun onActivityStopped(activity: Activity) {}
4766

4867
override fun onActivitySaveInstanceState(activity: Activity, outState: Bundle) {}
4968

50-
override fun onActivityDestroyed(activity: Activity) {}
69+
override fun onActivityDestroyed(activity: Activity) {
70+
appliedThemes.remove(activity)
71+
}
5172

5273
/** Set the night mode depending on the user preferences and what the theme support */
5374
private fun setupNightMode(themeNightModeSupport: String) {

app/app/src/main/java/com/github/livingwithhippos/unchained/settings/view/ThemePickerDialog.kt

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,6 @@ import com.github.livingwithhippos.unchained.R
1616
import com.github.livingwithhippos.unchained.databinding.ItemThemeListBinding
1717
import com.github.livingwithhippos.unchained.settings.viewmodel.SettingsViewModel
1818
import com.github.livingwithhippos.unchained.utilities.extension.getThemeList
19-
import com.github.livingwithhippos.unchained.utilities.extension.showToast
2019
import com.google.android.material.dialog.MaterialAlertDialogBuilder
2120
import dagger.hilt.android.AndroidEntryPoint
2221

@@ -50,8 +49,8 @@ class ThemePickerDialog : DialogFragment(), ThemePickListener {
5049
it.getContentIfNotHandled()?.let { theme ->
5150
label.text = theme.name
5251
viewModel.applyTheme()
53-
context?.showToast(R.string.restart_to_apply)
5452
dialog?.cancel()
53+
activity?.recreate()
5554
}
5655
}
5756

app/app/src/main/res/values-es/strings.xml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -182,7 +182,6 @@
182182
<string name="share">Compartir</string>
183183
<string name="share_with">Comparte el enlace de descarga a través de:</string>
184184
<string name="share_all_with">Comparte todos los enlaces de descarga a través de:</string>
185-
<string name="restart_to_apply">Reiniciar para aplicar</string>
186185
<string name="remove">Eliminar</string>
187186
<string name="confirm_download_removal_description">¿Está seguro de que quiere eliminar la descarga? Esta acción no se puede deshacer.</string>
188187
<string name="yes_remove">Sí, quítalo</string>

app/app/src/main/res/values-fr/strings.xml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -182,7 +182,6 @@
182182
<string name="share">Partager</string>
183183
<string name="share_with">Partager le lien de téléchargement via:</string>
184184
<string name="share_all_with">Partagez tous les liens de téléchargement via:</string>
185-
<string name="restart_to_apply">Redémarrer pour appliquer les modifications</string>
186185
<string name="remove">Supprimer</string>
187186
<string name="confirm_download_removal_description">Êtes-vous bien sûr de vouloir supprimer ce téléchargement ? Cette action est irréversible.</string>
188187
<string name="yes_remove">Oui, supprimez-le</string>

app/app/src/main/res/values-it/strings.xml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -182,7 +182,6 @@
182182
<string name="share">Condividi</string>
183183
<string name="share_with">Condividi link di download tramite:</string>
184184
<string name="share_all_with">Condividi tutti i links di download tramite:</string>
185-
<string name="restart_to_apply">Riavvia per applicare</string>
186185
<string name="remove">Rimuovi</string>
187186
<string name="confirm_download_removal_description">Sei sicuro di voler rimuovere il download? Questa azione non può essere annullata.</string>
188187
<string name="yes_remove">Sì, rimuovilo</string>

app/app/src/main/res/values-ko/strings.xml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -184,7 +184,6 @@
184184
<string name="share">공유</string>
185185
<string name="share_with">다음으로 다운로드 링크 공유:</string>
186186
<string name="share_all_with">다음으로 모든 다운로드 링크 공유:</string>
187-
<string name="restart_to_apply">재시작하여 적용</string>
188187
<string name="remove">제거</string>
189188
<string name="confirm_download_removal_description">정말로 이 다운로드를 제거하시겠습니까? 이 작업은 되돌릴 수 없습니다.</string>
190189
<string name="yes_remove">네, 제거합니다</string>

app/app/src/main/res/values-tr/strings.xml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -184,7 +184,6 @@
184184
<string name="share">Paylaş</string>
185185
<string name="share_with">İndirme bağlantısını şununla paylaş:</string>
186186
<string name="share_all_with">Tüm indirme bağlantılarını şununla paylaş:</string>
187-
<string name="restart_to_apply">Uygulamak için yeniden başlat</string>
188187
<string name="remove">Kaldır</string>
189188
<string name="confirm_download_removal_description">İndirmeyi kaldırmak istediğinizden emin misiniz? Bu işlem geri alınamaz.</string>
190189
<string name="yes_remove">Evet, kaldır</string>

app/app/src/main/res/values/strings.xml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -395,7 +395,6 @@
395395
<string name="share">Share</string>
396396
<string name="share_with">Share download link via:</string>
397397
<string name="share_all_with">Share all download links via:</string>
398-
<string name="restart_to_apply">Restart to apply</string>
399398
<string name="remove">Remove</string>
400399
<string name="confirm_download_removal_description">Are you sure you want to remove the download? This action cannot be undone.</string>
401400
<string name="yes_remove">Yes, remove it</string>

app/app/src/main/res/xml/settings.xml

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,7 @@
22
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android"
33
xmlns:app="http://schemas.android.com/apk/res-auto">
44

5-
<PreferenceCategory
6-
android:summary="@string/restart_to_apply"
7-
android:title="@string/title_aspect">
5+
<PreferenceCategory android:title="@string/title_aspect">
86

97
<Preference
108
app:key="selected_theme"

0 commit comments

Comments
 (0)