Jetpack Compose PointerInput State Hoisting

Viewed 967

I've been trying modify the Android Jetpack Compose official Documentation's example for gestures, so that State of the offset is hoisted in parent view.

The official example works properly, but the modified has lag and box returns to the previous position after the drag.

The modified version is almost similar to the original, except the state is hoisted.

@Composable
fun DragGesturesExampleWithHoistedState() {
    Box(
        modifier = Modifier
            .fillMaxSize()
            .background(Color.White)
    ) {
        var offsetX by remember { mutableStateOf(0f) }
        var offsetY by remember { mutableStateOf(0f) }

        DragGesturesBox(
            modifier = Modifier.offset {
                IntOffset(offsetX.roundToInt(), offsetY.roundToInt())
            },
            onDrag = {
                offsetX = it.x
                offsetY = it.y
            }
        )
    }
}

@Composable
fun DragGesturesBox(
    modifier: Modifier = Modifier,
    onDrag: (Offset) -> Unit
) {
    Box(
        modifier
            .background(Color.Blue)
            .size(50.dp)
            .pointerInput("my unique key") { // Does not work with Unit either
                detectDragGestures { change, dragAmount ->
                    change.consumeAllChanges()
                    onDrag(dragAmount)
                }
            }
    )
}


@Preview
@Composable
fun DragGesturesExampleWithHoistedStatePreview() {
    DragGesturesExampleWithHoistedState()
}

Is there anything I'm missing?

1 Answers

Change

onDrag = {
    offsetX = it.x
    offsetY = it.y
}

to

onDrag = {
    offsetX += it.x
    offsetY += it.y
}

and it'll work.

Related