mirror of
https://github.com/mihonapp/mihon.git
synced 2025-11-14 13:08:56 +01:00
Use Compose on Clear Database screen (#7639)
This commit is contained in:
@@ -0,0 +1,57 @@
|
||||
package eu.kanade.presentation.more.settings.database
|
||||
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.platform.LocalContext
|
||||
import eu.kanade.presentation.components.Scaffold
|
||||
import eu.kanade.presentation.more.settings.database.components.ClearDatabaseContent
|
||||
import eu.kanade.presentation.more.settings.database.components.ClearDatabaseDeleteDialog
|
||||
import eu.kanade.presentation.more.settings.database.components.ClearDatabaseFloatingActionButton
|
||||
import eu.kanade.presentation.more.settings.database.components.ClearDatabaseToolbar
|
||||
import eu.kanade.presentation.util.plus
|
||||
import eu.kanade.tachiyomi.R
|
||||
import eu.kanade.tachiyomi.ui.setting.database.ClearDatabasePresenter
|
||||
import eu.kanade.tachiyomi.util.system.toast
|
||||
|
||||
@Composable
|
||||
fun ClearDatabaseScreen(
|
||||
presenter: ClearDatabasePresenter,
|
||||
navigateUp: () -> Unit,
|
||||
) {
|
||||
val context = LocalContext.current
|
||||
Scaffold(
|
||||
topBar = {
|
||||
ClearDatabaseToolbar(
|
||||
state = presenter,
|
||||
navigateUp = navigateUp,
|
||||
onClickSelectAll = { presenter.selectAll() },
|
||||
onClickInvertSelection = { presenter.invertSelection() },
|
||||
)
|
||||
},
|
||||
floatingActionButton = {
|
||||
ClearDatabaseFloatingActionButton(
|
||||
isVisible = presenter.selection.isNotEmpty(),
|
||||
onClickDelete = {
|
||||
presenter.dialog = ClearDatabasePresenter.Dialog.Delete(presenter.selection)
|
||||
},
|
||||
)
|
||||
},
|
||||
) { paddingValues ->
|
||||
ClearDatabaseContent(
|
||||
state = presenter,
|
||||
contentPadding = paddingValues,
|
||||
onClickSelection = { source ->
|
||||
presenter.toggleSelection(source)
|
||||
},
|
||||
)
|
||||
}
|
||||
if (presenter.dialog is ClearDatabasePresenter.Dialog.Delete) {
|
||||
ClearDatabaseDeleteDialog(
|
||||
onDismissRequest = { presenter.dialog = null },
|
||||
onDelete = {
|
||||
presenter.removeMangaBySourceId((presenter.dialog as ClearDatabasePresenter.Dialog.Delete).sourceIds)
|
||||
presenter.clearSelection()
|
||||
context.toast(R.string.clear_database_completed)
|
||||
},
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,28 @@
|
||||
package eu.kanade.presentation.more.settings.database
|
||||
|
||||
import androidx.compose.runtime.Stable
|
||||
import androidx.compose.runtime.derivedStateOf
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.setValue
|
||||
import eu.kanade.domain.source.model.SourceWithCount
|
||||
import eu.kanade.tachiyomi.ui.setting.database.ClearDatabasePresenter
|
||||
|
||||
@Stable
|
||||
interface ClearDatabaseState {
|
||||
val items: List<SourceWithCount>
|
||||
val selection: List<Long>
|
||||
val isEmpty: Boolean
|
||||
var dialog: ClearDatabasePresenter.Dialog?
|
||||
}
|
||||
|
||||
fun ClearDatabaseState(): ClearDatabaseState {
|
||||
return ClearDatabaseStateImpl()
|
||||
}
|
||||
|
||||
class ClearDatabaseStateImpl : ClearDatabaseState {
|
||||
override var items: List<SourceWithCount> by mutableStateOf(emptyList())
|
||||
override var selection: List<Long> by mutableStateOf(emptyList())
|
||||
override val isEmpty: Boolean by derivedStateOf { items.isEmpty() }
|
||||
override var dialog: ClearDatabasePresenter.Dialog? by mutableStateOf(null)
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
package eu.kanade.presentation.more.settings.database.components
|
||||
|
||||
import androidx.compose.animation.Crossfade
|
||||
import androidx.compose.foundation.layout.PaddingValues
|
||||
import androidx.compose.foundation.layout.WindowInsets
|
||||
import androidx.compose.foundation.layout.asPaddingValues
|
||||
import androidx.compose.foundation.layout.navigationBars
|
||||
import androidx.compose.foundation.lazy.items
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import eu.kanade.domain.source.model.Source
|
||||
import eu.kanade.presentation.components.EmptyScreen
|
||||
import eu.kanade.presentation.components.FastScrollLazyColumn
|
||||
import eu.kanade.presentation.more.settings.database.ClearDatabaseState
|
||||
import eu.kanade.presentation.util.plus
|
||||
import eu.kanade.tachiyomi.R
|
||||
|
||||
@Composable
|
||||
fun ClearDatabaseContent(
|
||||
state: ClearDatabaseState,
|
||||
contentPadding: PaddingValues,
|
||||
onClickSelection: (Source) -> Unit,
|
||||
) {
|
||||
Crossfade(targetState = state.isEmpty.not()) { _state ->
|
||||
when (_state) {
|
||||
true -> FastScrollLazyColumn(
|
||||
contentPadding = contentPadding + WindowInsets.navigationBars.asPaddingValues(),
|
||||
) {
|
||||
items(state.items) { sourceWithCount ->
|
||||
ClearDatabaseItem(
|
||||
source = sourceWithCount.source,
|
||||
count = sourceWithCount.count,
|
||||
isSelected = state.selection.contains(sourceWithCount.id),
|
||||
onClickSelect = { onClickSelection(sourceWithCount.source) },
|
||||
)
|
||||
}
|
||||
}
|
||||
false -> EmptyScreen(message = stringResource(id = R.string.database_clean))
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
package eu.kanade.presentation.more.settings.database.components
|
||||
|
||||
import androidx.compose.material3.AlertDialog
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import eu.kanade.presentation.components.TextButton
|
||||
import eu.kanade.tachiyomi.R
|
||||
|
||||
@Composable
|
||||
fun ClearDatabaseDeleteDialog(
|
||||
onDismissRequest: () -> Unit,
|
||||
onDelete: () -> Unit,
|
||||
) {
|
||||
AlertDialog(
|
||||
onDismissRequest = onDismissRequest,
|
||||
confirmButton = {
|
||||
TextButton(onClick = onDelete) {
|
||||
Text(text = stringResource(id = android.R.string.ok))
|
||||
}
|
||||
},
|
||||
dismissButton = {
|
||||
TextButton(onClick = onDismissRequest) {
|
||||
Text(text = stringResource(id = android.R.string.cancel))
|
||||
}
|
||||
},
|
||||
text = {
|
||||
Text(text = stringResource(id = R.string.clear_database_confirmation))
|
||||
},
|
||||
)
|
||||
}
|
||||
@@ -0,0 +1,38 @@
|
||||
package eu.kanade.presentation.more.settings.database.components
|
||||
|
||||
import androidx.compose.animation.AnimatedVisibility
|
||||
import androidx.compose.animation.fadeIn
|
||||
import androidx.compose.animation.fadeOut
|
||||
import androidx.compose.foundation.layout.navigationBarsPadding
|
||||
import androidx.compose.material.icons.Icons
|
||||
import androidx.compose.material.icons.outlined.Delete
|
||||
import androidx.compose.material3.Icon
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import eu.kanade.presentation.components.ExtendedFloatingActionButton
|
||||
import eu.kanade.tachiyomi.R
|
||||
|
||||
@Composable
|
||||
fun ClearDatabaseFloatingActionButton(
|
||||
isVisible: Boolean,
|
||||
onClickDelete: () -> Unit,
|
||||
) {
|
||||
AnimatedVisibility(
|
||||
visible = isVisible,
|
||||
enter = fadeIn(),
|
||||
exit = fadeOut(),
|
||||
) {
|
||||
ExtendedFloatingActionButton(
|
||||
modifier = Modifier.navigationBarsPadding(),
|
||||
text = {
|
||||
Text(text = stringResource(id = R.string.action_delete))
|
||||
},
|
||||
icon = {
|
||||
Icon(Icons.Outlined.Delete, contentDescription = "")
|
||||
},
|
||||
onClick = onClickDelete,
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,53 @@
|
||||
package eu.kanade.presentation.more.settings.database.components
|
||||
|
||||
import androidx.compose.foundation.clickable
|
||||
import androidx.compose.foundation.layout.Column
|
||||
import androidx.compose.foundation.layout.Row
|
||||
import androidx.compose.foundation.layout.height
|
||||
import androidx.compose.foundation.layout.padding
|
||||
import androidx.compose.material3.Checkbox
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.Alignment
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.unit.dp
|
||||
import eu.kanade.domain.source.model.Source
|
||||
import eu.kanade.presentation.browse.components.SourceIcon
|
||||
import eu.kanade.presentation.util.selectedBackground
|
||||
import eu.kanade.tachiyomi.R
|
||||
|
||||
@Composable
|
||||
fun ClearDatabaseItem(
|
||||
source: Source,
|
||||
count: Long,
|
||||
isSelected: Boolean,
|
||||
onClickSelect: () -> Unit,
|
||||
) {
|
||||
Row(
|
||||
modifier = Modifier
|
||||
.selectedBackground(isSelected)
|
||||
.clickable(onClick = onClickSelect)
|
||||
.padding(horizontal = 8.dp)
|
||||
.height(56.dp),
|
||||
verticalAlignment = Alignment.CenterVertically,
|
||||
) {
|
||||
SourceIcon(source = source)
|
||||
Column(
|
||||
modifier = Modifier
|
||||
.padding(start = 8.dp)
|
||||
.weight(1f),
|
||||
) {
|
||||
Text(
|
||||
text = source.nameWithLanguage,
|
||||
style = MaterialTheme.typography.bodyMedium,
|
||||
)
|
||||
Text(text = stringResource(id = R.string.clear_database_source_item_count, count))
|
||||
}
|
||||
Checkbox(
|
||||
checked = isSelected,
|
||||
onCheckedChange = { onClickSelect() },
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
package eu.kanade.presentation.more.settings.database.components
|
||||
|
||||
import androidx.compose.material.icons.Icons
|
||||
import androidx.compose.material.icons.outlined.FlipToBack
|
||||
import androidx.compose.material.icons.outlined.SelectAll
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.ui.res.stringResource
|
||||
import eu.kanade.presentation.components.AppBar
|
||||
import eu.kanade.presentation.components.AppBarActions
|
||||
import eu.kanade.presentation.more.settings.database.ClearDatabaseState
|
||||
import eu.kanade.tachiyomi.R
|
||||
|
||||
@Composable
|
||||
fun ClearDatabaseToolbar(
|
||||
state: ClearDatabaseState,
|
||||
navigateUp: () -> Unit,
|
||||
onClickSelectAll: () -> Unit,
|
||||
onClickInvertSelection: () -> Unit,
|
||||
) {
|
||||
AppBar(
|
||||
title = stringResource(id = R.string.pref_clear_database),
|
||||
navigateUp = navigateUp,
|
||||
actions = {
|
||||
if (state.isEmpty.not()) {
|
||||
AppBarActions(
|
||||
actions = listOf(
|
||||
AppBar.Action(
|
||||
title = stringResource(id = R.string.action_select_all),
|
||||
icon = Icons.Outlined.SelectAll,
|
||||
onClick = onClickSelectAll,
|
||||
),
|
||||
AppBar.Action(
|
||||
title = stringResource(id = R.string.action_select_all),
|
||||
icon = Icons.Outlined.FlipToBack,
|
||||
onClick = onClickInvertSelection,
|
||||
),
|
||||
),
|
||||
)
|
||||
}
|
||||
},
|
||||
)
|
||||
}
|
||||
Reference in New Issue
Block a user