Skip to content

Commit ee14d07

Browse files
committed
add settings import export
1 parent a476663 commit ee14d07

File tree

5 files changed

+166
-76
lines changed

5 files changed

+166
-76
lines changed

app/src/main/java/com/uravgcode/chooser/settings/presentation/SettingsScreen.kt

Lines changed: 6 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -17,29 +17,25 @@ package com.uravgcode.chooser.settings.presentation
1717

1818
import androidx.compose.foundation.layout.WindowInsets
1919
import androidx.compose.foundation.layout.fillMaxSize
20-
import androidx.compose.foundation.layout.fillMaxWidth
2120
import androidx.compose.foundation.layout.padding
2221
import androidx.compose.foundation.layout.safeDrawing
2322
import androidx.compose.foundation.lazy.LazyColumn
24-
import androidx.compose.material3.ElevatedButton
2523
import androidx.compose.material3.ExperimentalMaterial3Api
2624
import androidx.compose.material3.HorizontalDivider
2725
import androidx.compose.material3.Scaffold
28-
import androidx.compose.material3.Text
2926
import androidx.compose.material3.TopAppBarDefaults
3027
import androidx.compose.runtime.Composable
3128
import androidx.compose.runtime.collectAsState
3229
import androidx.compose.runtime.getValue
33-
import androidx.compose.runtime.mutableStateOf
34-
import androidx.compose.runtime.remember
3530
import androidx.compose.runtime.rememberCoroutineScope
36-
import androidx.compose.runtime.setValue
3731
import androidx.compose.ui.Modifier
3832
import androidx.compose.ui.input.nestedscroll.nestedScroll
3933
import androidx.compose.ui.unit.dp
4034
import androidx.datastore.core.DataStore
4135
import com.uravgcode.chooser.settings.data.SettingsData
42-
import com.uravgcode.chooser.settings.presentation.component.ResetDialog
36+
import com.uravgcode.chooser.settings.presentation.button.SettingsButtonExport
37+
import com.uravgcode.chooser.settings.presentation.button.SettingsButtonImport
38+
import com.uravgcode.chooser.settings.presentation.button.SettingsButtonReset
4339
import com.uravgcode.chooser.settings.presentation.component.SettingsSeparator
4440
import com.uravgcode.chooser.settings.presentation.component.SettingsTopAppBar
4541
import com.uravgcode.chooser.settings.presentation.row.SettingsRowPaddingSlider
@@ -58,17 +54,6 @@ fun SettingsScreen(
5854
val settings by dataStore.data.collectAsState(initial = SettingsData())
5955

6056
val scrollBehavior = TopAppBarDefaults.pinnedScrollBehavior()
61-
var showResetDialog by remember { mutableStateOf(false) }
62-
63-
ResetDialog(
64-
showResetDialog = showResetDialog,
65-
onDismiss = { showResetDialog = false },
66-
onReset = {
67-
coroutineScope.launch {
68-
dataStore.updateData { SettingsData(hasSeenTutorial = true) }
69-
}
70-
}
71-
)
7257

7358
Scaffold(
7459
modifier = Modifier
@@ -186,13 +171,9 @@ fun SettingsScreen(
186171

187172
item {
188173
HorizontalDivider(modifier = Modifier.padding(vertical = 8.dp))
189-
ElevatedButton(
190-
content = { Text("Reset Settings") },
191-
onClick = { showResetDialog = true },
192-
modifier = Modifier
193-
.fillMaxWidth()
194-
.padding(vertical = 8.dp)
195-
)
174+
SettingsButtonImport(dataStore)
175+
SettingsButtonExport(dataStore)
176+
SettingsButtonReset(dataStore)
196177
}
197178
}
198179
}
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
package com.uravgcode.chooser.settings.presentation.button
2+
3+
import android.widget.Toast
4+
import androidx.activity.compose.rememberLauncherForActivityResult
5+
import androidx.activity.result.contract.ActivityResultContracts
6+
import androidx.compose.foundation.layout.fillMaxWidth
7+
import androidx.compose.foundation.layout.padding
8+
import androidx.compose.material3.ElevatedButton
9+
import androidx.compose.material3.Text
10+
import androidx.compose.runtime.Composable
11+
import androidx.compose.runtime.rememberCoroutineScope
12+
import androidx.compose.ui.Modifier
13+
import androidx.compose.ui.platform.LocalContext
14+
import androidx.compose.ui.unit.dp
15+
import androidx.datastore.core.DataStore
16+
import com.uravgcode.chooser.settings.data.SettingsData
17+
import com.uravgcode.chooser.settings.data.SettingsSerializer
18+
import kotlinx.coroutines.flow.first
19+
import kotlinx.coroutines.launch
20+
21+
@Composable
22+
fun SettingsButtonExport(dataStore: DataStore<SettingsData>) {
23+
val coroutineScope = rememberCoroutineScope()
24+
val context = LocalContext.current
25+
26+
val exportLauncher = rememberLauncherForActivityResult(
27+
contract = ActivityResultContracts.CreateDocument("application/json")
28+
) { uri ->
29+
uri?.let {
30+
coroutineScope.launch {
31+
try {
32+
context.contentResolver.openOutputStream(uri)?.use { outputStream ->
33+
SettingsSerializer.writeTo(dataStore.data.first(), outputStream)
34+
}
35+
Toast.makeText(context, "Settings exported successfully", Toast.LENGTH_SHORT).show()
36+
} catch (e: Exception) {
37+
Toast.makeText(context, "Failed to export settings: ${e.message}", Toast.LENGTH_SHORT).show()
38+
}
39+
}
40+
}
41+
}
42+
43+
ElevatedButton(
44+
content = { Text("Export Settings") },
45+
onClick = { exportLauncher.launch("chooser_settings.json") },
46+
modifier = Modifier
47+
.fillMaxWidth()
48+
.padding(vertical = 8.dp)
49+
)
50+
}
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
package com.uravgcode.chooser.settings.presentation.button
2+
3+
import android.widget.Toast
4+
import androidx.activity.compose.rememberLauncherForActivityResult
5+
import androidx.activity.result.contract.ActivityResultContracts
6+
import androidx.compose.foundation.layout.fillMaxWidth
7+
import androidx.compose.foundation.layout.padding
8+
import androidx.compose.material3.ElevatedButton
9+
import androidx.compose.material3.Text
10+
import androidx.compose.runtime.Composable
11+
import androidx.compose.runtime.rememberCoroutineScope
12+
import androidx.compose.ui.Modifier
13+
import androidx.compose.ui.platform.LocalContext
14+
import androidx.compose.ui.unit.dp
15+
import androidx.datastore.core.DataStore
16+
import com.uravgcode.chooser.settings.data.SettingsData
17+
import com.uravgcode.chooser.settings.data.SettingsSerializer
18+
import kotlinx.coroutines.launch
19+
20+
@Composable
21+
fun SettingsButtonImport(dataStore: DataStore<SettingsData>) {
22+
val coroutineScope = rememberCoroutineScope()
23+
val context = LocalContext.current
24+
25+
val importLauncher = rememberLauncherForActivityResult(
26+
contract = ActivityResultContracts.OpenDocument()
27+
) { uri ->
28+
uri?.let {
29+
coroutineScope.launch {
30+
try {
31+
context.contentResolver.openInputStream(uri)?.use { inputStream ->
32+
val importedSettings = SettingsSerializer.readFrom(inputStream)
33+
dataStore.updateData { importedSettings }
34+
}
35+
Toast.makeText(context, "Settings imported successfully", Toast.LENGTH_SHORT).show()
36+
} catch (e: Exception) {
37+
Toast.makeText(context, "Failed to import settings: ${e.message}", Toast.LENGTH_SHORT).show()
38+
}
39+
}
40+
}
41+
}
42+
43+
ElevatedButton(
44+
content = { Text("Import Settings") },
45+
onClick = { importLauncher.launch(arrayOf("application/json")) },
46+
modifier = Modifier
47+
.fillMaxWidth()
48+
.padding(vertical = 8.dp)
49+
)
50+
}
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
package com.uravgcode.chooser.settings.presentation.button
2+
3+
import androidx.compose.foundation.layout.fillMaxWidth
4+
import androidx.compose.foundation.layout.padding
5+
import androidx.compose.material3.AlertDialog
6+
import androidx.compose.material3.Button
7+
import androidx.compose.material3.ElevatedButton
8+
import androidx.compose.material3.Text
9+
import androidx.compose.runtime.Composable
10+
import androidx.compose.runtime.getValue
11+
import androidx.compose.runtime.mutableStateOf
12+
import androidx.compose.runtime.remember
13+
import androidx.compose.runtime.rememberCoroutineScope
14+
import androidx.compose.runtime.setValue
15+
import androidx.compose.ui.Modifier
16+
import androidx.compose.ui.unit.dp
17+
import androidx.datastore.core.DataStore
18+
import com.uravgcode.chooser.settings.data.SettingsData
19+
import kotlinx.coroutines.launch
20+
21+
@Composable
22+
fun SettingsButtonReset(dataStore: DataStore<SettingsData>) {
23+
val coroutineScope = rememberCoroutineScope()
24+
var showResetDialog by remember { mutableStateOf(false) }
25+
26+
if (showResetDialog) {
27+
AlertDialog(
28+
onDismissRequest = { showResetDialog = false },
29+
confirmButton = {
30+
Button(
31+
onClick = {
32+
coroutineScope.launch {
33+
dataStore.updateData { SettingsData(hasSeenTutorial = true) }
34+
showResetDialog = false
35+
}
36+
}
37+
) {
38+
Text("Reset")
39+
}
40+
},
41+
dismissButton = {
42+
Button(
43+
onClick = { showResetDialog = false }
44+
) {
45+
Text("Cancel")
46+
}
47+
},
48+
title = { Text(text = "Reset Settings") },
49+
text = { Text(text = "Are you sure you want to reset all settings to their default values?") },
50+
)
51+
}
52+
53+
ElevatedButton(
54+
content = { Text("Reset Settings") },
55+
onClick = { showResetDialog = true },
56+
modifier = Modifier
57+
.fillMaxWidth()
58+
.padding(vertical = 8.dp)
59+
)
60+
}

app/src/main/java/com/uravgcode/chooser/settings/presentation/component/ResetDialog.kt

Lines changed: 0 additions & 51 deletions
This file was deleted.

0 commit comments

Comments
 (0)