I'm working on a Jetpack Compose project and using the ModalBottomSheet from Material3 to display a bottom sheet when a FloatingActionButton is clicked. However, I'm experiencing issues with the sheet not animating smoothly when it appears or disappears. The animation seems to lag or isn't as fluid as expected.
Here's a summary of what I'm doing:
I have a MainScreen composable where the sheet visibility is controlled by a Boolean state. When the state is true, a custom bottom sheet (MyBottomSheet) is shown. The bottom sheet contains a TextField, and I'm trying to automatically focus on it when the sheet appears. The ModalBottomSheet is using a rememberModalBottomSheetState to manage its state. Despite following the standard implementation, the animation isn't smooth. I would greatly appreciate any advice on what might be causing this issue or how to improve the smoothness of the animations.
MyTextField.kt
@Composable
fun MyTextField(modifier: Modifier = Modifier) {
var text by remember { mutableStateOf("") }
val focusRequester = remember { FocusRequester() }
TextField(
value = text,
onValueChange = { text = it },
label = { Text("Label") },
modifier = modifier
.fillMaxWidth()
.focusRequester(focusRequester)
)
LaunchedEffect(Unit) {
focusRequester.requestFocus()
}
}
MyBottomSheet.kt
@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun MyBottomSheet(modifier: Modifier, onDismiss: () -> Unit) {
val modalBottomSheetState = rememberModalBottomSheetState()
val coroutineScope = rememberCoroutineScope()
LaunchedEffect(modalBottomSheetState.isVisible) {
if (modalBottomSheetState.isVisible) {
coroutineScope.launch {
modalBottomSheetState.show()
}
}
}
ModalBottomSheet(
onDismissRequest = { onDismiss() },
sheetState = modalBottomSheetState,
dragHandle = { BottomSheetDefaults.DragHandle() },
modifier = modifier,
content = {
MyTextField()
}
)
}
MainScreen.kt
@Preview(showBackground = true)
@Composable
fun MainScreen() {
var showSheet by remember { mutableStateOf(false) }
if (showSheet) {
MyBottomSheet(modifier = Modifier) {
showSheet = false
}
}
Box(
modifier = Modifier
.padding(all = 8.dp)
.fillMaxSize()
) {
MyFloatingActionButton(
onClick = {
showSheet = true
},
modifier = Modifier
.align(Alignment.BottomEnd)
.padding(bottom = 80.dp)
.padding(end = 10.dp)
)
}
}
I'm not sure if these changes will fix the issue because you didn't provide a complete example to test.
Since you're already controlling the bottom sheet's visibility with a state variable, you don't need to do it programmatically as well. You can remove or comment out that part of the code, like this:
@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun MyBottomSheet(modifier: Modifier, onDismiss: () -> Unit) {
val modalBottomSheetState = rememberModalBottomSheetState()
// val coroutineScope = rememberCoroutineScope()
//
// LaunchedEffect(modalBottomSheetState.isVisible) {
// if (modalBottomSheetState.isVisible) {
// coroutineScope.launch {
// modalBottomSheetState.show()
// }
// }
// }
ModalBottomSheet(
onDismissRequest = { onDismiss() },
sheetState = modalBottomSheetState,
//dragHandle = { BottomSheetDefaults.DragHandle() }, // Not needed, this is the default value
modifier = modifier,
content = {
MyTextField()
}
)
}
Another option to try is removing the auto-focus on the TextField. That might be causing the animation issue.
I hope this helps fix the problem.