use Jetpack Compose ModalBottomSheet: The offset was read before being initialized – Android

by
Ali Hasan
android android-jetpack-compose gradle-kotlin-dsl

Quick Fix: Utilize a DisposableEffect to guarantee showModal and closeModal functions are only called after the layout phase.

The Solutions:

Solution 1: Ensure showModal and closeModal are called after layout phase

You can use a `DisposableEffect` to ensure that the `showModal` and `closeModal` functions are called only after the layout phase. Here’s how you can do it:

@OptIn(ExperimentalMaterial3Api::class)
class SageSheetState(
    private val coroutineScope: CoroutineScope,
    val sheetState: SheetState,
    openBottomSheet: Boolean = false
) {
    var openBottomSheet by mutableStateOf(openBottomSheet)
        private set

    fun showModal() {
        coroutineScope.launch {
            openBottomSheet = true
            sheetState.collapse()
        }
    }

    fun closeModal() {
        coroutineScope.launch {
            sheetState.hide()
            openBottomSheet = false
        }
    }
}

@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun Modal(
    modalState: SageSheetState
) {
    DisposableEffect(modalState.openBottomSheet) {
        onDispose { }
    }

    // Sheet content
    if (modalState.openBottomSheet) {
        ModalBottomSheet(
            onDismissRequest = { modalState.closeModal() },
            sheetState = modalState.sheetState,
        ) {
            Text("Hello")
        }
    }
}

This solution ensures that the showModal and closeModal functions are called after the layout phase, which prevents the "offset was read before being initialized" error.

Q&A

When I click on the Show Modal button, it goes wrong?

You can use a DisposableEffect to ensure that the showModal and closeModal functions are called only after the layout phase.

What is the working code?

Check out the provided code snippet.

Will this work if I use a custom component as the content of the ModalBottomSheet?

Yes, it should work as long as the custom component is properly recomposed when the openBottomSheet state changes.