From e401b3e34b0a4c874ce2217331f783a1ae153f84 Mon Sep 17 00:00:00 2001 From: KaasKop- Date: Sun, 23 Apr 2023 16:07:23 +0200 Subject: [PATCH] Basic item editing implemented. --- .../com/mitchelbv/thuis_c/MainActivity.kt | 6 +- .../com/mitchelbv/thuis_c/ThuisDestination.kt | 2 +- .../freezer/item_list/FreezerItemListView.kt | 9 +- .../item_list/edit_item/FreezerItemEdit.kt | 164 ++++++++++++++---- .../edit_item/FreezerItemEditViewModel.kt | 37 +++- app/src/main/res/values/strings.xml | 6 + 6 files changed, 178 insertions(+), 46 deletions(-) diff --git a/app/src/main/java/com/mitchelbv/thuis_c/MainActivity.kt b/app/src/main/java/com/mitchelbv/thuis_c/MainActivity.kt index 1d6fc36..5adaeea 100644 --- a/app/src/main/java/com/mitchelbv/thuis_c/MainActivity.kt +++ b/app/src/main/java/com/mitchelbv/thuis_c/MainActivity.kt @@ -99,18 +99,18 @@ class MainActivity : ComponentActivity() { FreezerItemListScreen( onEditItem = {freezerItem -> // I want onEditItem to open a modal dialog, so not sure if this is needed here... - navController.navigate("${FreezerItemDetail.route}/${freezerItem}") + navController.navigate("${FreezerItemDetailDestination.route}/${freezerItem}") }) } // Edit items - composable(route = "${FreezerItemDetail.route}/{freezer_id}", arguments = listOf( + composable(route = "${FreezerItemDetailDestination.route}/{freezer_id}", arguments = listOf( navArgument("freezer_id") { this.type = NavType.IntType this.nullable = false } )) { - FreezerItemEditScreen() + FreezerItemEditScreen { navController.popBackStack() } } } } diff --git a/app/src/main/java/com/mitchelbv/thuis_c/ThuisDestination.kt b/app/src/main/java/com/mitchelbv/thuis_c/ThuisDestination.kt index 815df60..cbc93da 100644 --- a/app/src/main/java/com/mitchelbv/thuis_c/ThuisDestination.kt +++ b/app/src/main/java/com/mitchelbv/thuis_c/ThuisDestination.kt @@ -41,7 +41,7 @@ object FreezerItemListDestination : ThuisDestination { override val route = "freezer_item_list" } -object FreezerItemDetail : ThuisDestination { +object FreezerItemDetailDestination : ThuisDestination { override val icon = Icons.Default.DateRange override val destinationName = R.string.home_card_freezer override val route = "freezer_item_detail" diff --git a/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/FreezerItemListView.kt b/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/FreezerItemListView.kt index 3c60e55..f72627a 100644 --- a/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/FreezerItemListView.kt +++ b/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/FreezerItemListView.kt @@ -8,6 +8,7 @@ import androidx.compose.runtime.* import androidx.compose.runtime.livedata.observeAsState import androidx.compose.ui.Alignment import androidx.compose.ui.res.stringResource +import androidx.compose.ui.window.Dialog import androidx.lifecycle.compose.collectAsStateWithLifecycle import androidx.lifecycle.viewmodel.compose.viewModel import com.mitchelbv.thuis_c.R @@ -31,9 +32,9 @@ fun FreezerItemListScreen( ) }, onEditItem = onEditItem) } - FloatingActionButton(onClick = { /*TODO*/ }) { - - } +// FloatingActionButton(onClick = { /*TODO*/ }) { +// +// } } @OptIn(ExperimentalMaterial3Api::class) @@ -74,4 +75,4 @@ fun FreezerItemElement( } } ) -} +} \ No newline at end of file diff --git a/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/edit_item/FreezerItemEdit.kt b/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/edit_item/FreezerItemEdit.kt index 602dc82..e1d0bc3 100644 --- a/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/edit_item/FreezerItemEdit.kt +++ b/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/edit_item/FreezerItemEdit.kt @@ -1,20 +1,14 @@ package com.mitchelbv.thuis_c.views.freezer.item_list.edit_item -import androidx.compose.foundation.layout.Arrangement -import androidx.compose.foundation.layout.Column -import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.* import androidx.compose.foundation.text.KeyboardOptions -import androidx.compose.material3.ExperimentalMaterial3Api -import androidx.compose.material3.FloatingActionButton -import androidx.compose.material3.Text -import androidx.compose.material3.TextField +import androidx.compose.material3.* import androidx.compose.runtime.Composable -import androidx.compose.runtime.collectAsState import androidx.compose.runtime.getValue -import androidx.compose.runtime.livedata.observeAsState import androidx.compose.runtime.mutableStateOf -import androidx.compose.runtime.saveable.rememberSaveable +import androidx.compose.runtime.remember import androidx.compose.runtime.setValue +import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.res.stringResource import androidx.compose.ui.text.input.KeyboardType @@ -24,54 +18,160 @@ import androidx.core.text.isDigitsOnly import androidx.lifecycle.compose.collectAsStateWithLifecycle import androidx.lifecycle.viewmodel.compose.viewModel import com.mitchelbv.thuis_c.R +import com.mitchelbv.thuis_c.network.thuis.responses.Freezer import com.mitchelbv.thuis_c.network.thuis.responses.FreezerItem -import com.mitchelbv.thuis_c.views.freezer.item_list.FreezerItemElement -import com.mitchelbv.thuis_c.views.freezer.item_list.FreezerItemListViewModel +import com.mitchelbv.thuis_c.views.freezer.freezerUiState @Composable fun FreezerItemEditScreen( - freezerItemEditViewModel: FreezerItemEditViewModel = viewModel() + freezerItemEditViewModel: FreezerItemEditViewModel = viewModel(), + previousScreen: () -> Unit ) { val freezerItemUiState by freezerItemEditViewModel.uiState.collectAsStateWithLifecycle() - freezerItemUiState.item?.let { BuildEditView(freezerItem = it) } + if (freezerItemUiState.item != null && freezerItemUiState.freezers != null) { + BuildEditView( + freezerItem = freezerItemUiState.item!!, + freezerList = freezerItemUiState.freezers!!, + savePressed = { freezerItemEditViewModel.UpdateFreezerItem(it) }, + returnScreen = previousScreen, + modifier = Modifier + ) + } } @OptIn(ExperimentalMaterial3Api::class) @Composable -fun BuildEditView(freezerItem: FreezerItem) { - var itemText by rememberSaveable() { - mutableStateOf(freezerItem.item) +fun BuildEditView( + freezerItem: FreezerItem, + freezerList: List, + savePressed: (FreezerItem) -> Unit, + returnScreen: () -> Unit, + modifier: Modifier +) { + var expanded by remember { + mutableStateOf(false) } - Column(verticalArrangement = Arrangement.SpaceBetween) { + + var freezerItemLifeCycle by remember { + mutableStateOf(freezerItem) + } + + var freezerItemAmount by remember { + mutableStateOf("${freezerItem.amount}") + } + var freezerItemDrawer by remember { + mutableStateOf("${freezerItem.drawer}") + } + Column( + horizontalAlignment = Alignment.CenterHorizontally, + verticalArrangement = Arrangement.Top, + modifier = modifier + .fillMaxSize() + .padding(16.dp) + ) { TextField( label = { Text(stringResource(id = R.string.freezer_item_edit_description)) }, -// value = "${freezerItem.item}", - value = "${itemText}", - onValueChange = { - freezerItem.item = it - itemText = it - }) + value = "${freezerItemLifeCycle.item}", + onValueChange = { value -> + freezerItemLifeCycle = freezerItemLifeCycle.copy(item = value) + }, + maxLines = 2, + modifier = modifier.fillMaxWidth() + ) + Spacer(modifier = modifier.height(15.dp)) TextField( label = { Text(stringResource(id = R.string.freezer_item_edit_amount)) }, - value = "${freezerItem.amount}", + value = freezerItemAmount, onValueChange = { value -> - if (value.isDigitsOnly()) { - freezerItem.amount = value.toInt() + if (value.isBlank()) { + freezerItemAmount = "" + } + if (value.isDigitsOnly() && value.isNotBlank()) { + freezerItemAmount = value + freezerItemLifeCycle = freezerItemLifeCycle.copy(amount = value.toInt()) } }, - keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Number) + keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Number), + maxLines = 1, + modifier = modifier.fillMaxWidth() ) + Spacer(modifier = modifier.height(15.dp)) TextField( label = { Text(stringResource(id = R.string.freezer_item_edit_drawer)) }, - value = "${freezerItem.drawer}", - onValueChange = {}) + value = freezerItemDrawer, + onValueChange = { value -> + if (value.isBlank()) { + freezerItemDrawer = "" + } + if (value.isDigitsOnly() && value.isNotBlank()) { + freezerItemDrawer = value + freezerItemLifeCycle = freezerItemLifeCycle.copy(drawer = value.toInt()) + } + }, + keyboardOptions = KeyboardOptions(keyboardType = KeyboardType.Number), + maxLines = 1, + modifier = modifier.fillMaxWidth() + ) + Spacer(modifier = modifier.height(15.dp)) + ExposedDropdownMenuBox( + expanded = expanded, + onExpandedChange = { expanded = !expanded }, + modifier = modifier.fillMaxWidth() + ) { + TextField( + label = { Text(stringResource(id = R.string.freezer_item_edit_freezer)) }, + value = "${freezerList[freezerItemLifeCycle.freezerId?.minus(1)!!].name}", + onValueChange = {}, + readOnly = true, + modifier = modifier + .menuAnchor() + .fillMaxWidth(), + trailingIcon = { ExposedDropdownMenuDefaults.TrailingIcon(expanded = expanded) }, + maxLines = 1, + ) + ExposedDropdownMenu( + expanded = expanded, + onDismissRequest = { expanded = false }, + modifier = modifier.fillMaxWidth() + ) { + freezerList.forEach { freezer -> + DropdownMenuItem( + text = { freezer.name?.let { Text(it) } }, + onClick = { + freezerItemLifeCycle = + freezerItemLifeCycle.copy(freezerId = freezer.freezerId) + expanded = !expanded + }) + } + } + } + Spacer(modifier = modifier.height(15.dp)) + Row(modifier = modifier.fillMaxWidth(), horizontalArrangement = Arrangement.SpaceEvenly) { + Button(onClick = { + // Save and return to overview + returnScreen() + savePressed(freezerItemLifeCycle) + }) { + Text(stringResource(id = R.string.com_save)) + } + OutlinedButton(onClick = { + // Cancel all changes and return to last view + returnScreen() + }) { + Text(stringResource(id = R.string.com_cancel)) + } + } } } -@Preview +@Preview(showBackground = true) @Composable fun EditViewPreview() { val test = FreezerItem(freezerItemId = 1, item = "Kip", 5, 5, "12-01-01", 1) - BuildEditView(freezerItem = test) + val kaas = listOf( + Freezer(freezerId = 1, amountInFreezer = 5, name = "Keuken"), + Freezer(freezerId = 2, amountInFreezer = 5, name = "Berging") + ) + BuildEditView(freezerItem = test, kaas, {}, {}, Modifier) } \ No newline at end of file diff --git a/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/edit_item/FreezerItemEditViewModel.kt b/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/edit_item/FreezerItemEditViewModel.kt index 458cc9a..a337792 100644 --- a/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/edit_item/FreezerItemEditViewModel.kt +++ b/app/src/main/java/com/mitchelbv/thuis_c/views/freezer/item_list/edit_item/FreezerItemEditViewModel.kt @@ -1,12 +1,12 @@ package com.mitchelbv.thuis_c.views.freezer.item_list.edit_item -import androidx.lifecycle.MutableLiveData +import android.util.Log import androidx.lifecycle.SavedStateHandle import androidx.lifecycle.ViewModel import androidx.lifecycle.viewModelScope import com.mitchelbv.thuis_c.network.thuis.ThuisRetrofitHelper +import com.mitchelbv.thuis_c.network.thuis.responses.Freezer import com.mitchelbv.thuis_c.network.thuis.responses.FreezerItem -import com.mitchelbv.thuis_c.views.freezer.item_list.FreezerItemListUiState import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.flow.MutableStateFlow import kotlinx.coroutines.flow.StateFlow @@ -16,6 +16,9 @@ import java.net.ConnectException data class FreezerItemEditUiState( val item: FreezerItem? = null, + var freezerItemAmount: String? = null, + var freezerItemDrawer: String? = null, + val freezers: List? = null, var error: String = "" ) @@ -24,15 +27,23 @@ class FreezerItemEditViewModel(savedStateHandle: SavedStateHandle) : ViewModel() val uiState: StateFlow = _uiState.asStateFlow() init { - savedStateHandle.get("freezer_id")?.let { fillEditBoxes(it) } + savedStateHandle.get("freezer_id")?.let { PopulateUiState(it) } } - fun fillEditBoxes(freezer_id: Int) { + fun PopulateUiState(freezer_id: Int) { viewModelScope.launch(Dispatchers.IO) { try { - val apiResponse = + val getFreezers = ThuisRetrofitHelper.thuis.getFreezers() + if (freezer_id == 0) { + // This is when creating a new frezer item + _uiState.value = + FreezerItemEditUiState(item = FreezerItem(), freezers = getFreezers) + return@launch + } + val getFreezerItems = ThuisRetrofitHelper.thuis.getFreezerItem(id = freezer_id) - _uiState.value = FreezerItemEditUiState(item = apiResponse) + _uiState.value = + FreezerItemEditUiState(item = getFreezerItems, freezers = getFreezers) } catch (e: ConnectException) { // _uiState.value = FreezerItemListUiState(listOf(FreezerItem(item = ))) @@ -41,4 +52,18 @@ class FreezerItemEditViewModel(savedStateHandle: SavedStateHandle) : ViewModel() } } + fun UpdateFreezerItem(freezerItem: FreezerItem) { + Log.d("TESTINGGG", "hello ${freezerItem.item}") + viewModelScope.launch(Dispatchers.IO) { + try { + val putFreezerItem = ThuisRetrofitHelper.thuis.putFreezerItem( + id = freezerItem.freezerItemId!!, + freezerItem = freezerItem + ) + } catch (e: ConnectException) { + // Not sure yet.. + } + } + } + } \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index e2bb918..cf6482d 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -1,6 +1,11 @@ Thuis + + Connection error, try again later. + Save + Cancel + Matches Recipes Home @@ -18,4 +23,5 @@ Description Amount Drawer + Freezer \ No newline at end of file