fun TextFieldWithIconsAndErrorLabel(
text: String,
charLimit: Int = Int.MAX_VALUE,
keyboardType: KeyboardType = KeyboardType.Text,
onValueChange: (String) -> Unit,
) {
val keyboardController = LocalSoftwareKeyboardController.current
var shouldShowMaxCharLimitError by remember { mutableStateOf(false) }
BasicTextField(
modifier = Modifier
.fillMaxWidth(),
value = text,
onValueChange = { newInput ->
if (newInput.length > charLimit) {
shouldShowMaxCharLimitError = true
} else {
shouldShowMaxCharLimitError = false
onValueChange(newInput)
}
},
keyboardOptions = KeyboardOptions(
imeAction = ImeAction.Done,
keyboardType = keyboardType,
),
singleLine = true,
keyboardActions = KeyboardActions(
onDone = {
keyboardController?.hide()
onValueChange(text)
shouldShowMaxCharLimitError = false
}
),
)
if (shouldShowMaxCharLimitError) {
Text(
modifier = Modifier
.fillMaxWidth(),
text = "Max character limit exceeded",
style = TextStyle(
fontFamily = PoppinsFamily,
fontWeight = FontWeight.Medium,
fontSize = 12.sp,
color = Color.Red,
textAlign = TextAlign.Start
),
)
}
}
In the above code, onValueChange
is called multiple times and immediately resets the boolean.
For every text input, this lambda get invoked twice.
onValueChange = { newInput ->
if (newInput.length > charLimit) {
shouldShowMaxCharLimitError = true
} else {
shouldShowMaxCharLimitError = false
onValueChange(newInput)
}
}
2
Answers
change your onValueChange to this
and remove the call to onValueChange(text) inside the onDone callback
You should add
result: