Hello as described in title, I have this problem only if I use Data Class for information exchange. Simplified code is as follows (in original code I have 3 OutlinedTextField):
data class ToolsStates(
val isDialog: Boolean = false,
val repair: String = "",
val repairErrText: String = "You need to enter at least 3 characters",
val isError: Boolean = false
)
sealed class DataExchange {
data class IsDialogChanged(val isDialog: Boolean): DataExchange()
data class RepairChanged(val repair: String): DataExchange()
}
class ViewModel {
private val _state = MutableStateFlow(ToolsStates())
val state: StateFlow<ToolsStates> = _state
fun onEvent(event: DataExchange) {
when (event) {
is DataExchange.IsDialogChanged -> { _state.value = _state.value.copy(isDialog = event.isDialog) }
is DataExchange.RepairChanged -> { _state.value = _state.value.copy(repair = event.repair) }
}
}
}
@Composable
fun MainView() {
// some long code
val viewModel by remember { ViewModel() }
val state by viewModel.state.collectAsState()
val dialogState = rememberDialogState(size = DpSize(550.dp, 500.dp))
DialogWindow(
onCloseRequest = { viewModel.onEvent(DataExchange.IsDialogChanged(false)) },
visible = state.isDialog,
state = dialogState,
title = "Tool repair"
) {
OutlinedTextField(
value = state.repair,
onValueChange = { viewModel.onEvent(DataExchange.RepairChanged(it)) },
label = { Text("New tool entry") },
supportingText = { Text(state.repairErrText) },
isError = state.isError
)
}
}
If i don't use Data Class, and use variables like this inside viewmodel:
class ViewModel {
val _repair = MutableStateFlow("")
val repair: StateFlow<String> = _repair
}
Everything works like it should, but it gets really messy if i would need 5-10 variables.
But it only returns cursor one position to the left when in a Dialog Window, I have 7 OutlinedTextField also in main window and data class backed, and there is no problem. Thanks for reply.
Ok, I found my answer, it's the problem of Flow.
If I want to synchronously update UI textfield, I cannot use Flow, because Flow is asynchronous and sometimes it returns previously typed character after the current character, and it looks like the cursor jumped one position to the left.
I can only use mutableStateOf.