From fba652581a4c18402630cd4f488f01047ddde038 Mon Sep 17 00:00:00 2001 From: MM20 <15646950+MM2-0@users.noreply.github.com> Date: Sun, 23 Nov 2025 20:19:43 +0100 Subject: [PATCH] Move time format preference to locale settings screen --- .../ui/launcher/widgets/clock/ClockWidget.kt | 51 ------------------- .../settings/locale/LocaleSettingsScreen.kt | 22 +++++++- .../settings/locale/LocaleSettingsScreenVM.kt | 8 +++ .../preferences/LauncherSettingsData.kt | 6 ++- .../de/mm20/launcher2/preferences/Module.kt | 2 + .../preferences/ui/ClockWidgetSettings.kt | 4 +- .../preferences/ui/LocaleSettings.kt | 19 +++++++ 7 files changed, 57 insertions(+), 55 deletions(-) create mode 100644 core/preferences/src/main/java/de/mm20/launcher2/preferences/ui/LocaleSettings.kt diff --git a/app/ui/src/main/java/de/mm20/launcher2/ui/launcher/widgets/clock/ClockWidget.kt b/app/ui/src/main/java/de/mm20/launcher2/ui/launcher/widgets/clock/ClockWidget.kt index 5f6eb403f..b94348655 100644 --- a/app/ui/src/main/java/de/mm20/launcher2/ui/launcher/widgets/clock/ClockWidget.kt +++ b/app/ui/src/main/java/de/mm20/launcher2/ui/launcher/widgets/clock/ClockWidget.kt @@ -353,7 +353,6 @@ fun ConfigureClockWidgetSheet( val alignment by viewModel.alignment.collectAsState() val showSeconds by viewModel.showSeconds.collectAsState() val monospaced by viewModel.monospaced.collectAsState() - val timeFormat by viewModel.timeFormat.collectAsState() val useAccentColor by viewModel.useThemeColor.collectAsState() val parts by viewModel.parts.collectAsState() @@ -514,56 +513,6 @@ fun ConfigureClockWidgetSheet( } ) } - AnimatedVisibility( - style !is ClockWidgetStyle.Analog && - style !is ClockWidgetStyle.Custom && - style !is ClockWidgetStyle.Empty - ) { - var showDropdown by remember { mutableStateOf(false) } - Preference( - title = stringResource(R.string.preference_clock_widget_time_format), - summary = when (timeFormat) { - TimeFormat.TwelveHour -> stringResource(R.string.preference_clock_widget_time_format_12h) - TimeFormat.TwentyFourHour -> stringResource(R.string.preference_clock_widget_time_format_24h) - TimeFormat.System -> stringResource(R.string.preference_value_system_default) - }, - icon = R.drawable.schedule_24px, - onClick = { - showDropdown = true - } - ) - DropdownMenu( - expanded = showDropdown, - onDismissRequest = { showDropdown = false }) { - DropdownMenuItem( - text = { - Text(stringResource(R.string.preference_value_system_default)) - }, - onClick = { - viewModel.setTimeFormat(TimeFormat.System) - showDropdown = false - } - ) - DropdownMenuItem( - text = { - Text(stringResource(R.string.preference_clock_widget_time_format_24h)) - }, - onClick = { - viewModel.setTimeFormat(TimeFormat.TwentyFourHour) - showDropdown = false - } - ) - DropdownMenuItem( - text = { - Text(stringResource(R.string.preference_clock_widget_time_format_12h)) - }, - onClick = { - viewModel.setTimeFormat(TimeFormat.TwelveHour) - showDropdown = false - } - ) - } - } } } OutlinedCard( diff --git a/app/ui/src/main/java/de/mm20/launcher2/ui/settings/locale/LocaleSettingsScreen.kt b/app/ui/src/main/java/de/mm20/launcher2/ui/settings/locale/LocaleSettingsScreen.kt index 87a2e00ac..bc44715a0 100644 --- a/app/ui/src/main/java/de/mm20/launcher2/ui/settings/locale/LocaleSettingsScreen.kt +++ b/app/ui/src/main/java/de/mm20/launcher2/ui/settings/locale/LocaleSettingsScreen.kt @@ -8,15 +8,19 @@ import androidx.activity.compose.LocalActivity import androidx.appcompat.app.AppCompatActivity import androidx.appcompat.app.AppCompatDelegate import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue import androidx.compose.runtime.remember import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.platform.LocalResources import androidx.compose.ui.res.stringResource import androidx.core.net.toUri import androidx.core.os.LocaleListCompat +import androidx.lifecycle.compose.collectAsStateWithLifecycle +import androidx.lifecycle.viewmodel.compose.viewModel import androidx.navigation3.runtime.NavKey import de.mm20.launcher2.ktx.isAtLeastApiLevel import de.mm20.launcher2.ktx.tryStartActivity +import de.mm20.launcher2.preferences.TimeFormat import de.mm20.launcher2.ui.R import de.mm20.launcher2.ui.component.preferences.ListPreference import de.mm20.launcher2.ui.component.preferences.Preference @@ -31,7 +35,9 @@ data object LocaleSettingsRoute: NavKey @Composable fun LocaleSettingsScreen() { val context = LocalContext.current - val resources = LocalResources.current + val viewModel: LocaleSettingsScreenVM = viewModel() + + val timeFormat by viewModel.timeFormat.collectAsStateWithLifecycle(null) val language = remember { AppCompatDelegate.getApplicationLocales().get(0) @@ -44,6 +50,7 @@ fun LocaleSettingsScreen() { item { PreferenceCategory { Preference( + icon = R.drawable.flag_24px, title = stringResource(R.string.preference_language), summary = if (language == null) stringResource(R.string.preference_value_system_default) else language.getDisplayName(language), enabled = isAtLeastApiLevel(33), @@ -55,6 +62,19 @@ fun LocaleSettingsScreen() { ) } ) + ListPreference( + icon = R.drawable.schedule_24px, + title = stringResource(R.string.preference_clock_widget_time_format), + value = timeFormat, + onValueChanged = { + if (it != null) viewModel.setTimeFormat(it) + }, + items = listOf( + stringResource(R.string.preference_value_system_default) to TimeFormat.System, + stringResource(R.string.preference_clock_widget_time_format_12h) to TimeFormat.TwelveHour, + stringResource(R.string.preference_clock_widget_time_format_24h) to TimeFormat.TwentyFourHour, + ) + ) } } } diff --git a/app/ui/src/main/java/de/mm20/launcher2/ui/settings/locale/LocaleSettingsScreenVM.kt b/app/ui/src/main/java/de/mm20/launcher2/ui/settings/locale/LocaleSettingsScreenVM.kt index 6a184ebcb..7d970a6c3 100644 --- a/app/ui/src/main/java/de/mm20/launcher2/ui/settings/locale/LocaleSettingsScreenVM.kt +++ b/app/ui/src/main/java/de/mm20/launcher2/ui/settings/locale/LocaleSettingsScreenVM.kt @@ -1,8 +1,16 @@ package de.mm20.launcher2.ui.settings.locale import androidx.lifecycle.ViewModel +import de.mm20.launcher2.preferences.TimeFormat +import de.mm20.launcher2.preferences.ui.LocaleSettings import org.koin.core.component.KoinComponent +import org.koin.core.component.inject class LocaleSettingsScreenVM: ViewModel(), KoinComponent { + private val localeSettings: LocaleSettings by inject() + val timeFormat = localeSettings.timeFormat + fun setTimeFormat(timeFormat: TimeFormat) { + localeSettings.setTimeFormat(timeFormat) + } } \ No newline at end of file diff --git a/core/preferences/src/main/java/de/mm20/launcher2/preferences/LauncherSettingsData.kt b/core/preferences/src/main/java/de/mm20/launcher2/preferences/LauncherSettingsData.kt index 66f8ef224..f9a339925 100644 --- a/core/preferences/src/main/java/de/mm20/launcher2/preferences/LauncherSettingsData.kt +++ b/core/preferences/src/main/java/de/mm20/launcher2/preferences/LauncherSettingsData.kt @@ -5,6 +5,7 @@ import de.mm20.launcher2.search.SearchFilters import de.mm20.launcher2.serialization.UUIDSerializer import kotlinx.serialization.SerialName import kotlinx.serialization.Serializable +import kotlinx.serialization.json.JsonNames import java.util.UUID @Serializable @@ -47,7 +48,6 @@ data class LauncherSettingsData internal constructor( val clockWidgetColors: ClockWidgetColors = ClockWidgetColors.Auto, val clockWidgetShowSeconds: Boolean = false, val clockWidgetMonospaced: Boolean = false, - val clockWidgetTimeFormat: TimeFormat = TimeFormat.System, val clockWidgetUseThemeColor: Boolean = false, val clockWidgetAlarmPart: Boolean = true, val clockWidgetBatteryPart: Boolean = true, @@ -193,6 +193,10 @@ data class LauncherSettingsData internal constructor( ), + @JsonNames("clockWidgetTimeFormat") + val localeTimeFormat: TimeFormat = TimeFormat.System, + + ) { constructor( context: Context, diff --git a/core/preferences/src/main/java/de/mm20/launcher2/preferences/Module.kt b/core/preferences/src/main/java/de/mm20/launcher2/preferences/Module.kt index 662202750..ab0d808c6 100644 --- a/core/preferences/src/main/java/de/mm20/launcher2/preferences/Module.kt +++ b/core/preferences/src/main/java/de/mm20/launcher2/preferences/Module.kt @@ -18,6 +18,7 @@ import de.mm20.launcher2.preferences.ui.BadgeSettings import de.mm20.launcher2.preferences.ui.ClockWidgetSettings import de.mm20.launcher2.preferences.ui.GestureSettings import de.mm20.launcher2.preferences.ui.IconSettings +import de.mm20.launcher2.preferences.ui.LocaleSettings import de.mm20.launcher2.preferences.ui.SearchUiSettings import de.mm20.launcher2.preferences.ui.UiSettings import de.mm20.launcher2.preferences.ui.UiState @@ -50,4 +51,5 @@ val preferencesModule = module { factory { ClockWidgetSettings(get()) } factory { LocationSearchSettings(get()) } factory { SearchFilterSettings(get()) } + factory { LocaleSettings(get()) } } \ No newline at end of file diff --git a/core/preferences/src/main/java/de/mm20/launcher2/preferences/ui/ClockWidgetSettings.kt b/core/preferences/src/main/java/de/mm20/launcher2/preferences/ui/ClockWidgetSettings.kt index 9b290093b..c9e2e926f 100644 --- a/core/preferences/src/main/java/de/mm20/launcher2/preferences/ui/ClockWidgetSettings.kt +++ b/core/preferences/src/main/java/de/mm20/launcher2/preferences/ui/ClockWidgetSettings.kt @@ -146,11 +146,11 @@ class ClockWidgetSettings internal constructor( } val timeFormat - get() = launcherDataStore.data.map { it.clockWidgetTimeFormat } + get() = launcherDataStore.data.map { it.localeTimeFormat } fun setTimeFormat(timeFormat: TimeFormat) { launcherDataStore.update { - it.copy(clockWidgetTimeFormat = timeFormat) + it.copy(localeTimeFormat = timeFormat) } } diff --git a/core/preferences/src/main/java/de/mm20/launcher2/preferences/ui/LocaleSettings.kt b/core/preferences/src/main/java/de/mm20/launcher2/preferences/ui/LocaleSettings.kt new file mode 100644 index 000000000..add9c5e7a --- /dev/null +++ b/core/preferences/src/main/java/de/mm20/launcher2/preferences/ui/LocaleSettings.kt @@ -0,0 +1,19 @@ +package de.mm20.launcher2.preferences.ui + +import de.mm20.launcher2.preferences.LauncherDataStore +import de.mm20.launcher2.preferences.TimeFormat +import kotlinx.coroutines.flow.map + + +class LocaleSettings internal constructor( + private val launcherDataStore: LauncherDataStore, +) { + val timeFormat + get() = launcherDataStore.data.map { it.localeTimeFormat } + + fun setTimeFormat(timeFormat: TimeFormat) { + launcherDataStore.update { + it.copy(localeTimeFormat = timeFormat) + } + } +} \ No newline at end of file