Home > Blockchain >  how do I pass cursor from one textfield to other textfield in jetpack compose?
how do I pass cursor from one textfield to other textfield in jetpack compose?

Time:02-02

I have two textfields and the user will enter their weight and target weight. When the user clicks on the target weight, a picker appears and the user chooses his weight from there. If user selects his weight and presses the OK button, I want it to automatically switch to the target weight textfield.

hear is my code

I am sharing example textfield

 Column(modifier = Modifier.fillMaxWidth()) {

        TextField(
            value = viewModel.defaultWeightValue.value ,
            modifier = Modifier
                .fillMaxWidth()
                .padding(5.dp),
            onValueChange = { viewModel.currentWeight.value = it },
            label = { Text(text = "current weight (kg)") },
            shape = RoundedCornerShape(5.dp),
            colors = TextFieldDefaults.textFieldColors(
                textColor = Grey2,
                disabledTextColor = Color.Transparent,
                backgroundColor = Grey3,
                focusedIndicatorColor = Color.Transparent,
                unfocusedIndicatorColor = Color.Transparent,
                disabledIndicatorColor = Color.Transparent,
            ),
            interactionSource = remember { MutableInteractionSource() }
                .also { interactionSource ->
                    LaunchedEffect(interactionSource) {
                        interactionSource.interactions.collect {
                            if (it is PressInteraction.Press) {
                                // works like onClick
                                viewModel.isUserClickTxtField.value = true
                            }
                        }
                    }
                }
        )
        TextField(
            value = viewModel.targetWeight.value,
            modifier = Modifier
                .fillMaxWidth()
                .padding(5.dp),
            onValueChange = { viewModel.targetWeight.value = it },
            label = { Text(text = "target weight (kg)") },
            shape = RoundedCornerShape(5.dp),
            colors = TextFieldDefaults.textFieldColors(
                textColor = Grey2,
                disabledTextColor = Color.Transparent,
                backgroundColor = Grey3,
                focusedIndicatorColor = Color.Transparent,
                unfocusedIndicatorColor = Color.Transparent,
                disabledIndicatorColor = Color.Transparent,
                focusedLabelColor = DefaultDYTColor
            )
        )
    }
    DYTLoginAndContinueButton(
        text = "continue",
        navController,
        Screen.SignUpFourthScreen.route
    )
}



 if (viewModel.isUserClickTxtField.value) {
            Column(
                modifier = Modifier.fillMaxSize(),
                verticalArrangement = Arrangement.Bottom
            ) {
                Row(
                    modifier = Modifier
                        .fillMaxWidth()
                        .background(Color.Gray),
                    horizontalArrangement = Arrangement.Center,
                    verticalAlignment = Alignment.CenterVertically
                ) {
                    InfiniteNumberPicker(
                        modifier = Modifier.width(60.dp),
                        list = viewModel.weight,
                        firstIndex = 0,
                        onSelect = {
                            viewModel.weightPickerState.value = it
                        }
                    )
                    Text(text = "kg")
                    InfiniteNumberPicker(
                        modifier = Modifier.width(60.dp),
                        list = viewModel.gram,
                        firstIndex = 0,
                        onSelect = {
                            viewModel.grPickerState.value = it
                        }
                    )
                    Text(text = "gram")
                }
                Row(
                    modifier = Modifier
                        .fillMaxWidth()
                        .height(IntrinsicSize.Min)
                        .background(Color.Gray)
                        .padding(start = 0.dp, top = 15.dp, end = 0.dp, bottom = 15.dp),
                    horizontalArrangement = Arrangement.Center,
                    verticalAlignment = Alignment.CenterVertically
                ) {
                    Text(
                        text = "cancel",
                        fontSize = 16.sp,
                        fontWeight = FontWeight.Bold,
                        color = DefaultDYTColor,
                        modifier = Modifier
                            .padding(8.dp)
                            .clickable {
                                viewModel.isUserClickTxtField.value = false
                            })
                    Divider(
                        color = Color.White,
                        modifier = Modifier
                            .padding(8.dp)
                            .fillMaxHeight()  //fill the max height
                            .width(1.dp)
                    )
    
                  TextButton(onClick = {
                      viewModel.isUserClickTxtField.value = false
                      viewModel.defaultWeightValue.value = "${viewModel.weightPickerState.value}  ${viewModel.grPickerState.value}"
                  }) {
                      Text(
                          text = "Okey",
                          fontSize = 16.sp,
                          fontWeight = FontWeight.Bold,
                          color = DefaultDYTColor,
                          modifier = Modifier.padding(8.dp))
                  }
                }
            }
        }

if user click textfield viewModel.isUserClickTxtField.value is true and picker pops up for user. if user click Okey button in picker that means user selected his weight on picker. I want to switch other textfield automatically how can I do that ?

CodePudding user response:

Create and remember FocusRequester:

val focusRequester = remember { FocusRequester() }

Add this FocusRequester to the target TextField with modifier:

modifier = Modifier.focusRequester(focusRequester)

Use this code to request focus (cursor):

focusRequester.requestFocus()

CodePudding user response:

You can use the solution provided by @bylazy or you can use the focusProperties modifier to specify the next/previous item for each TextField or composable in your screen

Then simply use the focusManager.moveFocus method to move the focus:

focusManager.moveFocus(FocusDirection.Next)

Something like:

    val (item1, item2) = remember { FocusRequester.createRefs() }
    val focusManager = LocalFocusManager.current

    TextField(
        value = text,
        onValueChange = {text = it},
        Modifier
            .focusRequester(item1)
            .focusProperties {
                next = item2
                right = item2
            }
    )

    Button(
        onClick = { focusManager.moveFocus(FocusDirection.Next) }
    ) { Text("OK") }

    TextField(
        value = text,
        onValueChange = {text = it},
        Modifier
            .focusRequester(item2)
    )

In your 1st TextField you can also add the keyboardActions attribute to move the focus clicking Done in the field.

   TextField(
        value = text,
        onValueChange = {text = it},
        Modifier
            .focusRequester(item1)
            .focusProperties {
                next = item2
                right = item2
            },
        keyboardOptions = KeyboardOptions.Default.copy(imeAction = ImeAction.Done),
        keyboardActions = KeyboardActions(
            onDone = { focusManager.moveFocus(FocusDirection.Next) }
        )
    )
  • Related