PickerGroup

Functions summary

Unit
@Composable
PickerGroup(
    modifier: Modifier,
    selectedPickerState: PickerState?,
    autoCenter: Boolean,
    propagateMinConstraints: Boolean,
    content: @Composable PickerGroupScope.() -> Unit
)

A group of Pickers to build components where multiple pickers are required to be combined together.

Functions

@Composable
fun PickerGroup(
    modifier: Modifier = Modifier,
    selectedPickerState: PickerState? = null,
    autoCenter: Boolean = true,
    propagateMinConstraints: Boolean = false,
    content: @Composable PickerGroupScope.() -> Unit
): Unit

A group of Pickers to build components where multiple pickers are required to be combined together. At most one Picker can be selected at a time. When touch exploration services are enabled, the focus moves to the picker which is clicked.

It is recommended to ensure that a Picker in non read only mode should have user scroll enabled when touch exploration services are running.

Example of a sample picker group with an hour and minute picker (24 hour format):

import androidx.compose.animation.AnimatedContent
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.size
import androidx.compose.runtime.mutableIntStateOf
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
import androidx.wear.compose.material3.PickerGroup
import androidx.wear.compose.material3.Text
import androidx.wear.compose.material3.rememberPickerState

var selectedPickerIndex by remember { mutableIntStateOf(0) }
val pickerStateHour = rememberPickerState(initialNumberOfOptions = 24)
val pickerStateMinute = rememberPickerState(initialNumberOfOptions = 60)
Column(
    modifier = Modifier.fillMaxWidth(),
    verticalArrangement = Arrangement.Center,
    horizontalAlignment = Alignment.CenterHorizontally,
) {
    Spacer(modifier = Modifier.size(30.dp))
    val label = if (selectedPickerIndex == 0) "Hours" else "Minutes"
    AnimatedContent(targetState = label) { targetText -> Text(text = targetText) }
    Spacer(modifier = Modifier.size(10.dp))
    PickerGroup(
        selectedPickerState =
            if (selectedPickerIndex == 0) pickerStateHour else pickerStateMinute,
        autoCenter = false,
    ) {
        PickerGroupItem(
            pickerState = pickerStateHour,
            selected = selectedPickerIndex == 0,
            onSelected = { selectedPickerIndex = 0 },
            option = { optionIndex, _ -> Text(text = "%02d".format(optionIndex)) },
            contentDescription = { "Hours" },
            modifier = Modifier.size(80.dp, 100.dp),
        )

        PickerGroupItem(
            pickerState = pickerStateMinute,
            selected = selectedPickerIndex == 1,
            onSelected = { selectedPickerIndex = 1 },
            option = { optionIndex, _ -> Text(text = "%02d".format(optionIndex)) },
            contentDescription = { "Minutes" },
            modifier = Modifier.size(80.dp, 100.dp),
        )
    }
}

Example of an auto centering picker group where the total width exceeds screen's width:

import androidx.compose.animation.AnimatedContent
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Spacer
import androidx.compose.foundation.layout.fillMaxWidth
import androidx.compose.foundation.layout.size
import androidx.compose.runtime.mutableIntStateOf
import androidx.compose.runtime.remember
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.unit.dp
import androidx.wear.compose.material3.PickerGroup
import androidx.wear.compose.material3.Text
import androidx.wear.compose.material3.rememberPickerState

var selectedPickerIndex by remember { mutableIntStateOf(0) }
val pickerStateHour = rememberPickerState(initialNumberOfOptions = 24)
val pickerStateMinute = rememberPickerState(initialNumberOfOptions = 60)
val pickerStateSeconds = rememberPickerState(initialNumberOfOptions = 60)
val pickerStateMilliSeconds = rememberPickerState(initialNumberOfOptions = 1000)
val pickerStates = remember {
    arrayOf(pickerStateHour, pickerStateMinute, pickerStateSeconds, pickerStateMilliSeconds)
}

Column(
    modifier = Modifier.fillMaxWidth(),
    verticalArrangement = Arrangement.Center,
    horizontalAlignment = Alignment.CenterHorizontally,
) {
    val headingText = mapOf(0 to "Hours", 1 to "Minutes", 2 to "Seconds", 3 to "Milli")
    Spacer(modifier = Modifier.size(30.dp))
    AnimatedContent(targetState = headingText[selectedPickerIndex]!!) { targetText ->
        Text(text = targetText)
    }
    Spacer(modifier = Modifier.size(10.dp))
    PickerGroup(selectedPickerState = pickerStates[selectedPickerIndex], autoCenter = true) {
        PickerGroupItem(
            pickerState = pickerStateHour,
            selected = selectedPickerIndex == 0,
            onSelected = { selectedPickerIndex = 0 },
            option = { optionIndex, _ -> Text(text = "%02d".format(optionIndex)) },
            contentDescription = { "Hours" },
            modifier = Modifier.size(80.dp, 100.dp),
        )
        PickerGroupItem(
            pickerState = pickerStateMinute,
            selected = selectedPickerIndex == 1,
            onSelected = { selectedPickerIndex = 1 },
            option = { optionIndex, _ -> Text(text = "%02d".format(optionIndex)) },
            contentDescription = { "Minutes" },
            modifier = Modifier.size(80.dp, 100.dp),
        )
        PickerGroupItem(
            pickerState = pickerStateSeconds,
            selected = selectedPickerIndex == 2,
            onSelected = { selectedPickerIndex = 2 },
            option = { optionIndex, _ -> Text(text = "%02d".format(optionIndex)) },
            contentDescription = { "Seconds" },
            modifier = Modifier.size(80.dp, 100.dp),
        )
        PickerGroupItem(
            pickerState = pickerStateMilliSeconds,
            selected = selectedPickerIndex == 3,
            onSelected = { selectedPickerIndex = 3 },
            option = { optionIndex, _ -> Text(text = "%03d".format(optionIndex)) },
            contentDescription = { "Milliseconds" },
            modifier = Modifier.size(80.dp, 100.dp),
        )
    }
}
Parameters
modifier: Modifier = Modifier

Modifier to be applied to the PickerGroup.

selectedPickerState: PickerState? = null

The PickerState of the Picker that is selected. Null value means that no Picker is selected.

autoCenter: Boolean = true

Indicates whether the selected Picker should be centered on the screen. It is recommended to set this as true when all the pickers cannot be fit into the screen. Or provide a mechanism to navigate to pickers which are not visible on screen. If false, the whole row containing pickers would be centered.

propagateMinConstraints: Boolean = false

Whether the incoming min constraints should be passed to content.

content: @Composable PickerGroupScope.() -> Unit

The content of the PickerGroup as a container of Pickers.