Skip to content

Commit

Permalink
Merge "Updated ToggleButton and ToggleControls for M3" into androidx-…
Browse files Browse the repository at this point in the history
…main
  • Loading branch information
Ankit authored and Gerrit Code Review committed May 7, 2024
2 parents 474edff + 10a7b7a commit 49ddbbd
Show file tree
Hide file tree
Showing 16 changed files with 189 additions and 78 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -1123,6 +1123,8 @@ private fun ToggleButtonWithDefaults(
toggleControlWidth = selectionControlWidth,
toggleControlHeight = selectionControlHeight,
labelSpacerSize = 0.dp,
toggleControlSpacing = 6.dp,
iconSpacing = 6.dp,
ripple = EmptyIndication,
)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -189,6 +189,8 @@ fun ToggleButton(
toggleControlWidth: Dp,
toggleControlHeight: Dp,
labelSpacerSize: Dp,
toggleControlSpacing: Dp,
iconSpacing: Dp,
ripple: Indication
) {
// One and only one of toggleControl and selectionControl should be provided.
Expand Down Expand Up @@ -232,15 +234,18 @@ fun ToggleButton(
.padding(contentPadding),
verticalAlignment = Alignment.CenterVertically
) {
ToggleButtonIcon(content = icon)
ToggleButtonIcon(
spacerSize = iconSpacing,
content = icon
)
Labels(
label = label,
secondaryLabel = secondaryLabel,
spacerSize = labelSpacerSize
)
Spacer(
modifier = Modifier.size(
TOGGLE_CONTROL_SPACING
toggleControlSpacing
)
)
ToggleControl(
Expand Down Expand Up @@ -413,14 +418,15 @@ fun SplitToggleButton(

@Composable
private fun ToggleButtonIcon(
spacerSize: Dp,
content: @Composable (BoxScope.() -> Unit)? = null
) {
if (content != null) {
Box(
modifier = Modifier.wrapContentSize(align = Alignment.Center),
content = content
)
Spacer(modifier = Modifier.size(ICON_SPACING))
Spacer(modifier = Modifier.size(spacerSize))
}
}

Expand Down Expand Up @@ -472,5 +478,4 @@ private fun PaddingValues.splitHorizontally() =
)

private val TOGGLE_CONTROL_SPACING = 4.dp
private val ICON_SPACING = 6.dp
private val SPLIT_WIDTH = 52.dp
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,8 @@ public fun SelectableChip(
toggleControlHeight = SELECTABLE_CONTROL_HEIGHT,
toggleControlWidth = SELECTABLE_CONTROL_WIDTH,
labelSpacerSize = 0.dp,
toggleControlSpacing = TOGGLE_CONTROL_SPACING,
iconSpacing = ICON_SPACING,
ripple = rippleOrFallbackImplementation()
)

Expand Down Expand Up @@ -831,3 +833,5 @@ private class DefaultSplitSelectableChipColors(

private val SELECTABLE_CONTROL_HEIGHT = 24.dp
private val SELECTABLE_CONTROL_WIDTH = 24.dp
private val TOGGLE_CONTROL_SPACING = 4.dp
private val ICON_SPACING = 6.dp
Original file line number Diff line number Diff line change
Expand Up @@ -158,6 +158,8 @@ public fun ToggleChip(
toggleControlHeight = TOGGLE_CONTROL_HEIGHT,
toggleControlWidth = TOGGLE_CONTROL_WIDTH,
labelSpacerSize = 0.dp,
toggleControlSpacing = TOGGLE_CONTROL_SPACING,
iconSpacing = ICON_SPACING,
ripple = rippleOrFallbackImplementation()
)

Expand Down Expand Up @@ -1066,3 +1068,5 @@ private class DefaultSplitToggleChipColors(

private val TOGGLE_CONTROL_HEIGHT = 24.dp
private val TOGGLE_CONTROL_WIDTH = 24.dp
private val TOGGLE_CONTROL_SPACING = 4.dp
private val ICON_SPACING = 6.dp
4 changes: 2 additions & 2 deletions wear/compose/compose-material3/api/current.txt
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,7 @@ package androidx.wear.compose.material3 {
}

public final class CheckboxDefaults {
method @androidx.compose.runtime.Composable public androidx.wear.compose.material3.CheckboxColors colors(optional long checkedBoxColor, optional long checkedCheckmarkColor, optional long uncheckedBoxColor, optional long uncheckedCheckmarkColor);
method @androidx.compose.runtime.Composable public androidx.wear.compose.material3.CheckboxColors colors(optional long checkedBoxColor, optional long checkedCheckmarkColor, optional long uncheckedBoxColor, optional long uncheckedCheckmarkColor, optional long disabledCheckedBoxColor, optional long disabledCheckedCheckmarkColor, optional long disabledUncheckedBoxColor, optional long disabledUncheckedCheckmarkColor);
field public static final androidx.wear.compose.material3.CheckboxDefaults INSTANCE;
}

Expand Down Expand Up @@ -440,7 +440,7 @@ package androidx.wear.compose.material3 {
}

public final class RadioDefaults {
method @androidx.compose.runtime.Composable public androidx.wear.compose.material3.RadioColors colors(optional long selectedColor, optional long unselectedColor);
method @androidx.compose.runtime.Composable public androidx.wear.compose.material3.RadioColors colors(optional long selectedColor, optional long unselectedColor, optional long disabledSelectedColor, optional long disabledUnselectedColor);
field public static final androidx.wear.compose.material3.RadioDefaults INSTANCE;
}

Expand Down
4 changes: 2 additions & 2 deletions wear/compose/compose-material3/api/restricted_current.txt
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,7 @@ package androidx.wear.compose.material3 {
}

public final class CheckboxDefaults {
method @androidx.compose.runtime.Composable public androidx.wear.compose.material3.CheckboxColors colors(optional long checkedBoxColor, optional long checkedCheckmarkColor, optional long uncheckedBoxColor, optional long uncheckedCheckmarkColor);
method @androidx.compose.runtime.Composable public androidx.wear.compose.material3.CheckboxColors colors(optional long checkedBoxColor, optional long checkedCheckmarkColor, optional long uncheckedBoxColor, optional long uncheckedCheckmarkColor, optional long disabledCheckedBoxColor, optional long disabledCheckedCheckmarkColor, optional long disabledUncheckedBoxColor, optional long disabledUncheckedCheckmarkColor);
field public static final androidx.wear.compose.material3.CheckboxDefaults INSTANCE;
}

Expand Down Expand Up @@ -440,7 +440,7 @@ package androidx.wear.compose.material3 {
}

public final class RadioDefaults {
method @androidx.compose.runtime.Composable public androidx.wear.compose.material3.RadioColors colors(optional long selectedColor, optional long unselectedColor);
method @androidx.compose.runtime.Composable public androidx.wear.compose.material3.RadioColors colors(optional long selectedColor, optional long unselectedColor, optional long disabledSelectedColor, optional long disabledUnselectedColor);
field public static final androidx.wear.compose.material3.RadioDefaults INSTANCE;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,13 @@
package androidx.wear.compose.material3

import android.os.Build
import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Box
import androidx.compose.runtime.Composable
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.testutils.assertAgainstGolden
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.platform.LocalLayoutDirection
import androidx.compose.ui.platform.testTag
import androidx.compose.ui.test.captureToImage
Expand Down Expand Up @@ -229,7 +232,11 @@ class RadioButtonScreenshotTest {
) {
rule.setContentWithTheme {
CompositionLocalProvider(LocalLayoutDirection provides layoutDirection) {
content()
Box(
modifier = Modifier.background(Color.Black)
) {
content()
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -543,12 +543,21 @@ class RadioButtonTest {
}

@Test
fun radio_button_height_defaults_52dp() {
fun radio_button_height_defaults_52dp_with_secondary_label() {
rule.setContentWithThemeForSizeAssertions {
RadioButtonWithDefaults()
RadioButtonWithDefaults(
secondaryLabel = { Text("Secondary label") }
)
}.assertHeightIsEqualTo(52.dp)
}

@Test
fun radio_button_height_defaults_48dp_without_secondary_label() {
rule.setContentWithThemeForSizeAssertions {
RadioButtonWithDefaults()
}.assertHeightIsEqualTo(48.dp)
}

@Test
fun split_radio_button_height_defaults_52dp() {
rule.setContentWithThemeForSizeAssertions {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,13 @@
package androidx.wear.compose.material3

import android.os.Build
import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Box
import androidx.compose.runtime.Composable
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.testutils.assertAgainstGolden
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.platform.LocalLayoutDirection
import androidx.compose.ui.platform.testTag
import androidx.compose.ui.test.captureToImage
Expand Down Expand Up @@ -422,7 +425,11 @@ class ToggleButtonScreenshotTest {
) {
rule.setContentWithTheme {
CompositionLocalProvider(LocalLayoutDirection provides layoutDirection) {
content()
Box(
modifier = Modifier.background(Color.Black)
) {
content()
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -515,12 +515,21 @@ class ToggleButtonTest {
}

@Test
fun toggle_button_height_defaults_52dp() {
fun toggle_button_height_defaults_52dp_with_secondary_label() {
rule.setContentWithThemeForSizeAssertions {
ToggleButtonWithDefaults()
ToggleButtonWithDefaults(
secondaryLabel = { Text("Secondary label") }
)
}.assertHeightIsEqualTo(52.dp)
}

@Test
fun toggle_button_height_defaults_48dp_without_secondary_label() {
rule.setContentWithThemeForSizeAssertions {
ToggleButtonWithDefaults()
}.assertHeightIsEqualTo(48.dp)
}

@Test
fun split_toggle_button_height_defaults_52dp() {
rule.setContentWithThemeForSizeAssertions {
Expand Down Expand Up @@ -726,15 +735,11 @@ private fun ComposeContentTestRule.verifyToggleButtonColors(
var actualIconColor = Color.Transparent
var actualSecondaryLabelColor = Color.Transparent
setContentWithTheme {
expectedContainerColor = toggle_button_container_color(checked)
.withDisabledAlphaApplied(enabled = enabled)
expectedContainerColor = toggle_button_container_color(checked, enabled)
.compositeOver(testBackgroundColor)
expectedLabelColor = toggle_button_content_color(checked)
.withDisabledAlphaApplied(enabled = enabled)
expectedSecondaryLabelColor = toggle_button_secondary_label_color(checked)
.withDisabledAlphaApplied(enabled = enabled)
expectedIconColor = toggle_button_icon_color(checked)
.withDisabledAlphaApplied(enabled = enabled)
expectedLabelColor = toggle_button_content_color(checked, enabled)
expectedSecondaryLabelColor = toggle_button_secondary_label_color(checked, enabled)
expectedIconColor = toggle_button_icon_color(enabled)
Box(
Modifier
.fillMaxSize()
Expand Down Expand Up @@ -776,12 +781,12 @@ private fun ComposeContentTestRule.verifySplitToggleButtonColors(
var actualLabelColor = Color.Transparent
var actualSecondaryLabelColor = Color.Transparent
setContentWithTheme {
expectedContainerColor = toggle_button_container_color(checked)
expectedContainerColor = split_toggle_button_container_color(checked)
.withDisabledAlphaApplied(enabled = enabled)
.compositeOver(testBackgroundColor)
expectedLabelColor = toggle_button_content_color(checked)
expectedLabelColor = split_toggle_button_content_color(checked)
.withDisabledAlphaApplied(enabled = enabled)
expectedSecondaryLabelColor = toggle_button_secondary_label_color(checked)
expectedSecondaryLabelColor = split_toggle_button_secondary_label_color(checked)
.withDisabledAlphaApplied(enabled = enabled)
Box(
Modifier
Expand Down Expand Up @@ -813,34 +818,64 @@ private fun ComposeContentTestRule.verifySplitToggleButtonColors(

@Composable
private fun toggle_button_container_color(
checked: Boolean
checked: Boolean,
enabled: Boolean,
): Color {
return if (checked) MaterialTheme.colorScheme.primaryContainer
else MaterialTheme.colorScheme.surfaceContainer
return if (checked && enabled) MaterialTheme.colorScheme.primaryContainer
else if (!checked && enabled) MaterialTheme.colorScheme.surfaceContainer
else MaterialTheme.colorScheme.onSurface.toDisabledColor(disabledAlpha = 0.12f)
}

@Composable
private fun toggle_button_content_color(
checked: Boolean
checked: Boolean,
enabled: Boolean
): Color {
return if (checked) MaterialTheme.colorScheme.onPrimaryContainer
else MaterialTheme.colorScheme.onSurface
return if (checked && enabled) MaterialTheme.colorScheme.onPrimaryContainer
else if (!checked && enabled) MaterialTheme.colorScheme.onSurface
else MaterialTheme.colorScheme.onSurface.toDisabledColor(disabledAlpha = 0.38f)
}

@Composable
private fun toggle_button_secondary_label_color(
checked: Boolean
checked: Boolean,
enabled: Boolean
): Color {
return if (checked) MaterialTheme.colorScheme.onPrimaryContainer.copy(alpha = 0.8f)
else MaterialTheme.colorScheme.onSurfaceVariant
return if (checked && enabled) MaterialTheme.colorScheme.onPrimaryContainer.copy(alpha = 0.8f)
else if (!checked && enabled) MaterialTheme.colorScheme.onSurfaceVariant
else MaterialTheme.colorScheme.onSurface.toDisabledColor(disabledAlpha = 0.38f)
}

@Composable
private fun toggle_button_icon_color(
enabled: Boolean
): Color {
return if (enabled) MaterialTheme.colorScheme.primary
else MaterialTheme.colorScheme.onSurface.toDisabledColor(disabledAlpha = 0.38f)
}

@Composable
private fun split_toggle_button_container_color(
checked: Boolean
): Color {
return if (checked) MaterialTheme.colorScheme.primaryContainer
else MaterialTheme.colorScheme.surfaceContainer
}

@Composable
private fun split_toggle_button_content_color(
checked: Boolean
): Color {
return if (checked) MaterialTheme.colorScheme.onPrimaryContainer
else MaterialTheme.colorScheme.primary
else MaterialTheme.colorScheme.onSurface
}

@Composable
private fun split_toggle_button_secondary_label_color(
checked: Boolean
): Color {
return if (checked) MaterialTheme.colorScheme.onPrimaryContainer.copy(alpha = 0.8f)
else MaterialTheme.colorScheme.onSurfaceVariant
}

@Composable
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -132,7 +132,10 @@ fun RadioButton(
// Stadium/Pill shaped toggle button
Row(
modifier = modifier
.defaultMinSize(minHeight = MIN_HEIGHT)
.defaultMinSize(
minHeight = if (secondaryLabel == null) MIN_HEIGHT_WITHOUT_SECONDARY_LABEL
else MIN_HEIGHT
)
.height(IntrinsicSize.Min)
.width(IntrinsicSize.Max)
.clip(shape = shape)
Expand Down Expand Up @@ -514,7 +517,7 @@ object RadioButtonDefaults {

internal val LabelSpacerSize = 2.dp
private val HorizontalPadding = 14.dp
private val VerticalPadding = 6.dp
private val VerticalPadding = 8.dp

/**
* The default content padding used by [RadioButton]
Expand Down Expand Up @@ -542,20 +545,23 @@ object RadioButtonDefaults {
unselectedIconColor = fromToken(RadioButtonTokens.UnselectedIconColor),
disabledSelectedContainerColor =
fromToken(RadioButtonTokens.DisabledSelectedContainerColor)
.toDisabledColor(disabledAlpha = RadioButtonTokens.DisabledOpacity),
.toDisabledColor(
disabledAlpha = RadioButtonTokens.DisabledSelectedContainerOpacity
),
disabledSelectedContentColor =
fromToken(RadioButtonTokens.DisabledSelectedContentColor)
.toDisabledColor(disabledAlpha = RadioButtonTokens.DisabledOpacity),
disabledSelectedSecondaryContentColor =
fromToken(RadioButtonTokens.DisabledSelectedSecondaryLabelColor)
.copy(alpha = RadioButtonTokens.DisabledSelectedSecondaryLabelOpacity)
.toDisabledColor(disabledAlpha = RadioButtonTokens.DisabledOpacity),
disabledSelectedIconColor =
fromToken(RadioButtonTokens.DisabledSelectedIconColor)
.toDisabledColor(disabledAlpha = RadioButtonTokens.DisabledOpacity),
disabledUnselectedContainerColor =
fromToken(RadioButtonTokens.DisabledUnselectedContainerColor)
.toDisabledColor(disabledAlpha = RadioButtonTokens.DisabledOpacity),
.toDisabledColor(
disabledAlpha = RadioButtonTokens.DisabledUnselectedContainerOpacity
),
disabledUnselectedContentColor =
fromToken(RadioButtonTokens.DisabledUnselectedContentColor)
.toDisabledColor(disabledAlpha = RadioButtonTokens.DisabledOpacity),
Expand Down Expand Up @@ -1123,7 +1129,8 @@ private val COLOR_ANIMATION_SPEC: AnimationSpec<Color> =
tween(MotionTokens.DurationMedium1, 0, MotionTokens.EasingStandardDecelerate)
private val SELECTION_CONTROL_WIDTH = 32.dp
private val SELECTION_CONTROL_HEIGHT = 24.dp
private val SELECTION_CONTROL_SPACING = 4.dp
private val SELECTION_CONTROL_SPACING = 6.dp
private val ICON_SPACING = 6.dp
private val MIN_HEIGHT = 52.dp
private val MIN_HEIGHT_WITHOUT_SECONDARY_LABEL = 48.dp
private val SPLIT_WIDTH = 52.dp
Loading

0 comments on commit 49ddbbd

Please sign in to comment.