Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Current scroll position value in pixels in LazyColumn Jetpack Compose

I want to have the total scroll position in px in LazyColumn. The column itself has a ScrollState which has a value (Described in the document as the current scroll position value in pixels), But LazyColumn ScrollState hasn't this field, I want the exact equivalent of Column ScrollState scroll position value for LazyColumn, How I can achieve that with the help of LazyScrollState?

like image 330
Hamidreza Sahraei Avatar asked Jan 28 '26 21:01

Hamidreza Sahraei


2 Answers

It is not possible to know the exact scroll position, but we can try!

@Composable
fun rememberCurrentOffset(state: LazyListState): androidx.compose.runtime.State<Int> {
    val position = remember { derivedStateOf { state.firstVisibleItemIndex } }
    val itemOffset = remember { derivedStateOf { state.firstVisibleItemScrollOffset } }
    val lastPosition = rememberPrevious(position.value)
    val lastItemOffset = rememberPrevious(itemOffset.value)
    val currentOffset = remember { mutableStateOf(0) }

    LaunchedEffect(position.value, itemOffset.value) {
        if (lastPosition == null || position.value == 0) {
            currentOffset.value = itemOffset.value
        } else if (lastPosition == position.value) {
            currentOffset.value += (itemOffset.value - (lastItemOffset ?: 0))
        } else if (lastPosition > position.value) {
            currentOffset.value -= (lastItemOffset ?: 0)
        } else { // lastPosition.value < position.value
            currentOffset.value += itemOffset.value
        }
    }

    return currentOffset
}

Using the rememberPrevious from Get previous value of state in Composable - Jetpack Compose solution also.

How to use

val scroll = rememberLazyListState()
val offset = rememberCurrentOffset(scroll)

// do any thing with the offset state

LazyColumn(
    state = scroll,
    modifier = Modifier.fillMaxSize()
) {
    ....
}
like image 158
José Braz Avatar answered Jan 30 '26 12:01

José Braz


The scroll amount can be obtained, no calculation required, in the items themselves, by attaching an onGloballyPosition{ it.positionInParent()} modifier to one or more items.

Then, the items can do what they need to do with their own scroll position, such as offsetting some screen-drawing y coordinate.

Or, if you need the scroll offset in the parent LazyColumn, you could have one item (perhaps an item with zero height, though I've not tested that) at the very top of your list of items, that reports back its position to the parent (perhaps by updating a mutableState that was passed to the item by the parent) whenever it moves.

I had the same need and onGloballyPosition{ it.positionInParent()} addressed it very nicely.

like image 40
John Avatar answered Jan 30 '26 12:01

John



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!