androidx.wear.compose.foundation.rotary


Interfaces

RotaryBehavior

An interface for handling scroll events.

RotaryScrollableAdapter

An adapter which connects scrollableState to a rotary input for snapping scroll actions.

Objects

RotaryDefaults

Defaults for rotary modifiers

Extension functions summary

Modifier
Modifier.rotary(
    rotaryBehavior: RotaryBehavior,
    focusRequester: FocusRequester,
    reverseDirection: Boolean
)

A modifier which connects rotary events with scrollable containers such as Column, LazyList and others.

Extension functions

fun Modifier.rotary(
    rotaryBehavior: RotaryBehavior,
    focusRequester: FocusRequester,
    reverseDirection: Boolean = false
): Modifier

A modifier which connects rotary events with scrollable containers such as Column, LazyList and others. ScalingLazyColumn has a build-in rotary support, and accepts rotaryBehavior parameter directly.

This modifier supports rotary scrolling and snapping. The behaviour is configured by the provided RotaryBehavior: either provide RotaryDefaults.scrollBehavior for scrolling with/without fling or pass RotaryDefaults.snapBehavior when snap is required.

Example of scrolling with fling:

import androidx.compose.foundation.background
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.rememberLazyListState
import androidx.compose.foundation.text.BasicText
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.text.TextStyle
import androidx.wear.compose.foundation.rememberActiveFocusRequester
import androidx.wear.compose.foundation.rotary.RotaryDefaults
import androidx.wear.compose.foundation.rotary.rotary

val scrollableState = rememberLazyListState()
val focusRequester = rememberActiveFocusRequester()
LazyColumn(
    modifier = Modifier
        .fillMaxSize()
        .rotary(
            rotaryBehavior = RotaryDefaults.scrollBehavior(scrollableState),
            focusRequester = focusRequester
        ),
    horizontalAlignment = Alignment.CenterHorizontally,
    state = scrollableState
) {
    items(300) {
        BasicText(
            text = "item $it",
            modifier = Modifier.background(Color.Gray),
            style = TextStyle.Default.copy()
        )
    }
}

Example of scrolling with snap:

import androidx.compose.foundation.background
import androidx.compose.foundation.gestures.ScrollableState
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.lazy.LazyColumn
import androidx.compose.foundation.lazy.rememberLazyListState
import androidx.compose.foundation.text.BasicText
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.unit.dp
import androidx.compose.ui.util.fastSumBy
import androidx.wear.compose.foundation.rememberActiveFocusRequester
import androidx.wear.compose.foundation.rotary.RotaryDefaults
import androidx.wear.compose.foundation.rotary.RotaryScrollableAdapter
import androidx.wear.compose.foundation.rotary.rotary

val scrollableState = rememberLazyListState()
val focusRequester = rememberActiveFocusRequester()
LazyColumn(
    modifier = Modifier
        .fillMaxSize()
        .rotary(
            rotaryBehavior = RotaryDefaults.snapBehavior(
                // This sample has a custom implementation of RotaryScrollableAdapter,
                // which is required for snapping behavior. ScalingLazyColumn has it built-in,
                // so it's not required there.
                remember(scrollableState) {
                    object : RotaryScrollableAdapter {
                        override val scrollableState: ScrollableState = scrollableState

                        override fun averageItemSize(): Float {
                            val items = scrollableState.layoutInfo.visibleItemsInfo
                            return (items.fastSumBy { it.size } / items.size).toFloat()
                        }

                        override fun currentItemIndex(): Int =
                            scrollableState.firstVisibleItemIndex

                        override fun currentItemOffset(): Float =
                            scrollableState.firstVisibleItemScrollOffset.toFloat()

                        override fun totalItemsCount(): Int =
                            scrollableState.layoutInfo.totalItemsCount
                    }
                }
            ),
            focusRequester = focusRequester
        ),
    horizontalAlignment = Alignment.CenterHorizontally,
    state = scrollableState
) {
    items(300) {
        BasicText(
            text = "item $it",
            modifier = Modifier
                .background(Color.Gray)
                .height(30.dp)
        )
    }
}
Parameters
rotaryBehavior: RotaryBehavior

Specified RotaryBehavior for rotary handling with snap or fling.

focusRequester: FocusRequester

Used to request the focus for rotary input. Each composable with this modifier should have a separate focusRequester, and only one of them at a time can be active.

reverseDirection: Boolean = false

Reverse the direction of scrolling if required for consistency with the scrollable state passed via rotaryBehavior.