Set labels on creation

This commit is contained in:
Jackson Harper
2023-05-15 14:59:22 +08:00
parent b9c4a6a476
commit 49af48a695
4 changed files with 57 additions and 15 deletions

View File

@ -262,7 +262,7 @@ fun LabelsSelectionSheetContent(
savedItemLabelId = "",
name = name.text,
labelDescription = "",
color = "#FFFFFF", // LabelSwatchHelper.random(),
color = LabelSwatchHelper.random(),
createdAt = LocalDate.now().atStartOfDay().atOffset(ZoneOffset.UTC).format(
DateTimeFormatter.ISO_DATE_TIME),
serverSyncStatus = ServerSyncStatus.NEEDS_CREATION.rawValue

View File

@ -10,17 +10,18 @@ import androidx.compose.foundation.lazy.LazyListState
import androidx.compose.foundation.lazy.items
import androidx.compose.foundation.lazy.rememberLazyListState
import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material.ExperimentalMaterialApi
import androidx.compose.material.ModalBottomSheetLayout
import androidx.compose.material.ModalBottomSheetValue
import androidx.compose.material.*
import androidx.compose.material.DrawerValue
import androidx.compose.material.icons.Icons
import androidx.compose.material.icons.filled.MoreVert
import androidx.compose.material.icons.outlined.Delete
import androidx.compose.material.pullrefresh.PullRefreshIndicator
import androidx.compose.material.pullrefresh.pullRefresh
import androidx.compose.material.pullrefresh.rememberPullRefreshState
import androidx.compose.material.rememberModalBottomSheetState
import androidx.compose.material3.*
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Scaffold
import androidx.compose.material3.SnackbarHost
import androidx.compose.runtime.*
import androidx.compose.runtime.livedata.observeAsState
import androidx.compose.ui.Alignment
@ -49,6 +50,7 @@ fun LibraryView(
libraryViewModel: LibraryViewModel,
navController: NavHostController
) {
val scaffoldState: ScaffoldState = rememberScaffoldState()
val showLabelsSelectionSheet: Boolean by libraryViewModel.showLabelsSelectionSheetLiveData.observeAsState(false)
val coroutineScope = rememberCoroutineScope()
@ -67,6 +69,13 @@ fun LibraryView(
}
}
libraryViewModel.snackbarMessage?.let {
coroutineScope.launch {
scaffoldState.snackbarHostState.showSnackbar(it)
libraryViewModel.clearSnackbarMessage()
}
}
ModalBottomSheetLayout(
sheetBackgroundColor = Color.Transparent,
sheetState = modalBottomSheetState,
@ -76,6 +85,7 @@ fun LibraryView(
}
) {
Scaffold(
scaffoldState = scaffoldState,
topBar = {
LibraryNavigationBar(
savedItemViewModel = libraryViewModel,
@ -164,6 +174,7 @@ fun LibraryViewContent(libraryViewModel: LibraryViewModel, modifier: Modifier) {
.fillMaxSize()
.pullRefresh(pullRefreshState)
) {
LazyColumn(
state = listState,
verticalArrangement = Arrangement.Top,

View File

@ -1,9 +1,14 @@
package app.omnivore.omnivore.ui.library
import android.content.Context
import android.util.Log
import android.widget.Toast
import androidx.compose.material3.SnackbarHostState
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.platform.LocalContext
import androidx.lifecycle.*
import app.omnivore.omnivore.*
import app.omnivore.omnivore.dataService.*
@ -36,6 +41,9 @@ class LibraryViewModel @Inject constructor(
private var searchIdx = 0
private var receivedIdx = 0
var snackbarMessage by mutableStateOf<String?>(null)
private set
// Live Data
private var itemsLiveDataInternal = dataService.db.savedItemDao().filteredLibraryData(
allowedArchiveStates = listOf(0),
@ -77,6 +85,10 @@ class LibraryViewModel @Inject constructor(
}
}
fun clearSnackbarMessage() {
snackbarMessage = null
}
fun refresh() {
cursor = null
librarySearchCursor = null
@ -285,27 +297,39 @@ class LibraryViewModel @Inject constructor(
fun updateSavedItemLabels(savedItemID: String, labels: List<SavedItemLabel>) {
viewModelScope.launch {
withContext(Dispatchers.IO) {
val synced = labels.filter { it.serverSyncStatus == ServerSyncStatus.IS_SYNCED.rawValue }
val unsynced = labels.filter { it.serverSyncStatus != ServerSyncStatus.IS_SYNCED.rawValue }
val syncedLabels = labels.filter { it.serverSyncStatus == ServerSyncStatus.IS_SYNCED.rawValue }
val unsyncedLabels = labels.filter { it.serverSyncStatus != ServerSyncStatus.IS_SYNCED.rawValue }
var labelIds = mutableListOf<String>()
labelIds.addAll(synced.map { it.savedItemLabelId })
unsynced.forEach { label ->
var labelCreationError = false
val createdLabels = unsyncedLabels.mapNotNull { label ->
val result = networker.createNewLabel(CreateLabelInput(
name = label.name,
color = presentIfNotNull(label.color),
description = presentIfNotNull(label.labelDescription),
))
result?.let {
labelIds.add(it.id)
SavedItemLabel(
savedItemLabelId = result.id,
name = result.name,
color = result.color,
createdAt = result.createdAt.toString(),
labelDescription = result.description,
serverSyncStatus = ServerSyncStatus.IS_SYNCED.rawValue
)
} ?: run {
labelCreationError = true
null
}
}
val input = SetLabelsInput(labelIds = labels.map { it.savedItemLabelId }, pageId = savedItemID)
dataService.db.savedItemLabelDao().insertAll(createdLabels)
val allLabels = syncedLabels + createdLabels
val input = SetLabelsInput(labelIds = allLabels.map { it.savedItemLabelId }, pageId = savedItemID)
val networkResult = networker.updateLabelsForSavedItem(input)
// TODO: assign a server sync status to these
val crossRefs = labels.map {
val crossRefs = allLabels.map {
SavedItemAndSavedItemLabelCrossRef(
savedItemLabelId = it.savedItemLabelId,
savedItemId = savedItemID
@ -318,6 +342,12 @@ class LibraryViewModel @Inject constructor(
// Add back the current labels
dataService.db.savedItemAndSavedItemLabelCrossRefDao().insertAll(crossRefs)
if (!networkResult || labelCreationError) {
snackbarMessage = "Unable to set labels"
} else {
snackbarMessage = "Labels updated"
}
CoroutineScope(Dispatchers.Main).launch {
handleFilterChanges()
}

View File

@ -65,6 +65,7 @@ fun SavedItemCard(savedItemViewModel: SavedItemViewModel, savedItem: SavedItemWi
text = savedItem.savedItem.title,
style = TextStyle(
fontSize = 18.sp,
color = MaterialTheme.colorScheme.onBackground,
fontWeight = FontWeight.SemiBold
),
maxLines = 2,