Skip to content

Commit 16929e7

Browse files
committed
Refactor preference items to use rememberSaveable for state management and improve localization
1 parent c6926a8 commit 16929e7

5 files changed

Lines changed: 42 additions & 9 deletions

File tree

app/src/main/java/com/drdisagree/iconify/core/ui/components/preferences/EditTextPreferenceItem.kt

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@ import androidx.compose.material3.Text
1313
import androidx.compose.runtime.Composable
1414
import androidx.compose.runtime.getValue
1515
import androidx.compose.runtime.mutableStateOf
16-
import androidx.compose.runtime.remember
1716
import androidx.compose.runtime.saveable.rememberSaveable
1817
import androidx.compose.runtime.setValue
1918
import androidx.compose.ui.Modifier
@@ -71,7 +70,7 @@ fun EditTextPreferenceItem(
7170
}
7271

7372
if (showDialog) {
74-
var draft by remember { mutableStateOf(storedValue) }
73+
var draft by rememberSaveable { mutableStateOf(storedValue) }
7574
AlertDialog(
7675
onDismissRequest = { showDialog = false },
7776
title = { Text(prefDefinition.title.resolve()) },

app/src/main/java/com/drdisagree/iconify/core/ui/components/preferences/FilePickerPreferenceItem.kt

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ import androidx.compose.ui.Modifier
4444
import androidx.compose.ui.draw.clip
4545
import androidx.compose.ui.graphics.Color
4646
import androidx.compose.ui.platform.LocalContext
47+
import androidx.compose.ui.res.stringResource
4748
import androidx.compose.ui.text.style.TextOverflow
4849
import androidx.compose.ui.unit.dp
4950
import com.drdisagree.iconify.R
@@ -249,7 +250,7 @@ fun FilePickerPreferenceItem(
249250

250251
if (uri != null && type.saveFileUri) {
251252
FilenameChip(
252-
name = fileName ?: "Unknown file",
253+
name = fileName ?: stringResource(R.string.file_unknown_name),
253254
type = type.pickerType,
254255
isEnabled = isEnabled,
255256
onClear = withHaptic {
@@ -269,7 +270,10 @@ fun FilePickerPreferenceItem(
269270
shapes = ButtonDefaults.shapes(),
270271
contentPadding = PaddingValues(horizontal = 16.dp, vertical = 8.dp),
271272
) {
272-
Text(text = if (uri != null) "Replace" else type.pickerType.label.resolve())
273+
Text(
274+
text = if (uri != null) stringResource(R.string.btn_replace_file)
275+
else type.pickerType.label.resolve()
276+
)
273277
}
274278
}
275279
}
@@ -341,7 +345,7 @@ private fun FilenameChip(
341345
) {
342346
Icon(
343347
imageVector = Icons.Outlined.Close,
344-
contentDescription = "Clear",
348+
contentDescription = stringResource(R.string.file_clear),
345349
tint = contentColor,
346350
modifier = Modifier.size(14.dp),
347351
)

app/src/main/java/com/drdisagree/iconify/core/ui/components/preferences/MultiListPreferenceItem.kt

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ import androidx.compose.runtime.derivedStateOf
2525
import androidx.compose.runtime.getValue
2626
import androidx.compose.runtime.mutableStateOf
2727
import androidx.compose.runtime.remember
28+
import androidx.compose.runtime.saveable.listSaver
2829
import androidx.compose.runtime.saveable.rememberSaveable
2930
import androidx.compose.runtime.setValue
3031
import androidx.compose.ui.Alignment
@@ -93,7 +94,12 @@ fun MultiListPreferenceItem(
9394
}
9495

9596
if (showDialog) {
96-
var localSelected by remember { mutableStateOf(selectedValues) }
97+
var localSelected by rememberSaveable(
98+
stateSaver = listSaver(
99+
save = { it.toList() },
100+
restore = { it.toSet() }
101+
)
102+
) { mutableStateOf(selectedValues) }
97103

98104
AlertDialog(
99105
onDismissRequest = { showDialog = false },

app/src/main/java/com/drdisagree/iconify/core/ui/components/preferences/SliderPreferenceItem.kt

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ import androidx.compose.material3.MaterialTheme
1717
import androidx.compose.material3.Slider
1818
import androidx.compose.material3.Text
1919
import androidx.compose.runtime.Composable
20+
import androidx.compose.runtime.LaunchedEffect
2021
import androidx.compose.runtime.getValue
2122
import androidx.compose.runtime.mutableFloatStateOf
2223
import androidx.compose.runtime.mutableStateOf
@@ -39,6 +40,7 @@ import com.drdisagree.iconify.core.preferences.resolveOrNull
3940
import com.drdisagree.iconify.core.preferences.toValueOrNull
4041
import com.drdisagree.iconify.core.ui.components.others.withHaptic
4142
import com.drdisagree.iconify.helpers.replaceAll
43+
import kotlin.math.abs
4244
import kotlin.math.roundToInt
4345

4446
@OptIn(ExperimentalMaterial3ExpressiveApi::class)
@@ -59,9 +61,23 @@ fun SliderPreferenceItem(
5961
val persistedValue by prefController.observe(prefDefinition.key, defaultValue)
6062
var sliderValue by remember { mutableFloatStateOf(persistedValue) }
6163
var previousLabel by remember { mutableStateOf<String?>(null) }
64+
65+
val defaultEpsilon = if (type.steps > 0) {
66+
(type.max - type.min) / (type.steps + 1) / 2f
67+
} else {
68+
0.0001f
69+
}
70+
val isAtDefault = abs(sliderValue - defaultValue) <= defaultEpsilon
71+
72+
LaunchedEffect(persistedValue) {
73+
if (sliderValue != persistedValue) {
74+
sliderValue = persistedValue
75+
}
76+
}
77+
6278
val originalValueLabel = type.valueLabel?.invoke(sliderValue)
6379
?: sliderValue.roundToInt().toString()
64-
val valueLabel = if (type.showDefaultIndicator && sliderValue == defaultValue) {
80+
val valueLabel = if (type.showDefaultIndicator && isAtDefault) {
6581
if (type.hideDefaultValue) {
6682
stringResource(R.string.opt_default).replaceAll("(" to "", ")" to "")
6783
} else {
@@ -100,7 +116,12 @@ fun SliderPreferenceItem(
100116
}
101117

102118
fun persistValue(value: Float) {
103-
prefController.setFloat(prefDefinition.key, value)
119+
val snapped = if (abs(value - defaultValue) <= defaultEpsilon) {
120+
defaultValue
121+
} else {
122+
value
123+
}
124+
prefController.setFloat(prefDefinition.key, snapped)
104125
}
105126

106127
PreferenceContainer(
@@ -153,7 +174,7 @@ fun SliderPreferenceItem(
153174
)
154175
if (type.showResetButton) {
155176
IconButton(
156-
enabled = isEnabled && sliderValue != defaultValue,
177+
enabled = isEnabled && !isAtDefault,
157178
shapes = IconButtonDefaults.shapes(),
158179
colors = IconButtonDefaults.filledIconButtonColors(),
159180
onClick = {

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

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1518,6 +1518,9 @@
15181518
<string name="btn_pick_pdf">Pick PDF</string>
15191519
<string name="btn_pick_document">Pick document</string>
15201520
<string name="btn_pick_file">Pick file</string>
1521+
<string name="btn_replace_file">Replace</string>
1522+
<string name="file_unknown_name">Unknown file</string>
1523+
<string name="file_clear">Clear</string>
15211524
<string name="advanced_color_settings_title">Advanced Settings</string>
15221525
<string name="advanced_color_settings_desc">Get advanced color customizations</string>
15231526
<string name="look_and_feel_title">Look &amp; Feel</string>

0 commit comments

Comments
 (0)