0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Material 3 Expressive実装例 : Button group

Last updated at Posted at 2025-06-11

Material 3 Expressive の実装例の紹介シリーズです。
今回は新たに追加されたコンポーネントである Button group を紹介します。
(androidx.compose.material3:material3:1.4.0-alpha15 時点での内容になります。)

Button group とは

複数のボタンをグループ化し、ボタンの種類、幅、色を自由に組み合わせることで優先度であったり状態を視覚的に関連付けるコンポーネントです。
Standard と Connected の 2 パターンがあります。
また Expressive では Segmented button が Deprecated になり、置き換え先がこの Button group になっています。

実装

ButtonGroup

標準で ButtonGroup が用意されています。
コンテンツ部分には clickableItemtoggleableItemcustomItem の関数が用意されています。
標準の ButtonGroup ではボタン押下時のインタラクションの適用であったり、画面に入りきらないとき省略する機能があります。

ButtonGroup(
    overflowIndicator = { menuState ->
        FilledIconButton(
            onClick = {
                if (menuState.isExpanded) {
                    menuState.dismiss()
                } else {
                    menuState.show()
                }
            }
        ) {
            Icon(
                painter = painterResource(R.drawable.ic_more),
                contentDescription = "More options"
            )
        }
    },
) {
    clickableItem(
        onClick = {},
        label = "Edit"
    )
    clickableItem(
        onClick = {},
        icon = {
            Icon(
                painter = painterResource(R.drawable.ic_edit),
                contentDescription = null
            )
        },
        label = "Edit"
    )
    toggleableItem(
        checked = isChecked,
        onCheckedChange = { isChecked = it },
        label = "Favorited"
    )
    customItem(
        buttonGroupContent = {
            val interactionSource = remember {  MutableInteractionSource() }
            OutlinedIconButton(
                onClick = {},
                interactionSource = interactionSource,
                modifier = Modifier.animateWidth(interactionSource),
            ) {
                Icon(painterResource(R.drawable.ic_add), contentDescription = "Add")
            }
        },
        menuContent = {
            DropdownMenuItem(
                text = {
                    Text("Add")
                },
                onClick = {},
                leadingIcon = {
                    Icon(painterResource(R.drawable.ic_add), contentDescription = null)
                }
            )
        }
    )
}
標準 Overflow時
Screenshot_20250609_155612.png Screenshot_20250609_155625.png

Connected button group

Connected button group は ButtonGroup のような標準の実装は現時点で用意されていないため実装する必要があります。
Connected button group の Shape のみ標準で用意されているのでそれを適用する形になります。

Row(
    horizontalArrangement = Arrangement.spacedBy(ButtonGroupDefaults.ConnectedSpaceBetween),
) {
    options.forEachIndexed { index, option ->
        ToggleButton(
            checked = selectedIndex == index,
            onCheckedChange = { selectedIndex = index },
            modifier = Modifier.semantics { role = Role.RadioButton },
            shapes =
                when (index) {
                    0 -> ButtonGroupDefaults.connectedLeadingButtonShapes()
                    options.lastIndex -> ButtonGroupDefaults.connectedTrailingButtonShapes()
                    else -> ButtonGroupDefaults.connectedMiddleButtonShapes()
                }
        ) {
            Icon(
                painter = painterResource(option.icon),
                contentDescription = null
            )
            Spacer(Modifier.size(ToggleButtonDefaults.IconSpacing))
            Text(option.label)
        }
    }
}
0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?