summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--packages/SystemUI/multivalentTests/src/com/android/systemui/qs/external/ui/viewmodel/TileRequestDialogViewModelTest.kt6
-rw-r--r--packages/SystemUI/multivalentTests/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiStateTest.kt43
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/BounceableInfo.kt2
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/QuickQuickSettings.kt26
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/CommonTile.kt10
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/EditTile.kt55
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/InfiniteGridLayout.kt23
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/Tile.kt63
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiState.kt5
9 files changed, 155 insertions, 78 deletions
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/qs/external/ui/viewmodel/TileRequestDialogViewModelTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/qs/external/ui/viewmodel/TileRequestDialogViewModelTest.kt
index 369975a95579..3029928f070f 100644
--- a/packages/SystemUI/multivalentTests/src/com/android/systemui/qs/external/ui/viewmodel/TileRequestDialogViewModelTest.kt
+++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/qs/external/ui/viewmodel/TileRequestDialogViewModelTest.kt
@@ -89,7 +89,7 @@ class TileRequestDialogViewModelTest : SysuiTestCase() {
expect.that(state).isEqualTo(expectedState.state)
expect.that(handlesLongClick).isFalse()
expect.that(handlesSecondaryClick).isFalse()
- expect.that(icon.get()).isEqualTo(defaultIcon)
+ expect.that(icon).isEqualTo(defaultIcon)
expect.that(sideDrawable).isNull()
expect.that(accessibilityUiState).isEqualTo(expectedState.accessibilityUiState)
}
@@ -112,7 +112,7 @@ class TileRequestDialogViewModelTest : SysuiTestCase() {
expect.that(state).isEqualTo(expectedState.state)
expect.that(handlesLongClick).isFalse()
expect.that(handlesSecondaryClick).isFalse()
- expect.that(icon.get()).isEqualTo(QSTileImpl.DrawableIcon(loadedDrawable))
+ expect.that(icon).isEqualTo(QSTileImpl.DrawableIcon(loadedDrawable))
expect.that(sideDrawable).isNull()
expect.that(accessibilityUiState).isEqualTo(expectedState.accessibilityUiState)
}
@@ -135,7 +135,7 @@ class TileRequestDialogViewModelTest : SysuiTestCase() {
underTest.activateIn(testScope)
runCurrent()
- assertThat(underTest.uiState.icon.get()).isEqualTo(defaultIcon)
+ assertThat(underTest.uiState.icon).isEqualTo(defaultIcon)
}
companion object {
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiStateTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiStateTest.kt
index b144f0678471..9c8e3225f3a4 100644
--- a/packages/SystemUI/multivalentTests/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiStateTest.kt
+++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiStateTest.kt
@@ -18,6 +18,7 @@ package com.android.systemui.qs.panels.ui.viewmodel
import android.content.res.Resources
import android.content.res.mainResources
+import android.graphics.drawable.TestStubDrawable
import android.service.quicksettings.Tile
import android.widget.Button
import android.widget.Switch
@@ -26,9 +27,12 @@ import androidx.test.ext.junit.runners.AndroidJUnit4
import androidx.test.filters.SmallTest
import com.android.systemui.SysuiTestCase
import com.android.systemui.plugins.qs.QSTile
+import com.android.systemui.qs.tileimpl.QSTileImpl
+import com.android.systemui.qs.tileimpl.QSTileImpl.ResourceIcon
import com.android.systemui.res.R
import com.android.systemui.testKosmos
import com.google.common.truth.Truth.assertThat
+import java.util.function.Supplier
import org.junit.Test
import org.junit.runner.RunWith
@@ -263,6 +267,45 @@ class TileUiStateTest : SysuiTestCase() {
.contains(resources.getString(R.string.tile_unavailable))
}
+ @Test
+ fun iconAndSupplier_prefersIcon() {
+ val state =
+ QSTile.State().apply {
+ icon = ResourceIcon.get(R.drawable.android)
+ iconSupplier = Supplier { QSTileImpl.DrawableIcon(TestStubDrawable()) }
+ }
+ val uiState = state.toUiState()
+
+ assertThat(uiState.icon).isEqualTo(state.icon)
+ }
+
+ @Test
+ fun iconOnly_hasIcon() {
+ val state = QSTile.State().apply { icon = ResourceIcon.get(R.drawable.android) }
+ val uiState = state.toUiState()
+
+ assertThat(uiState.icon).isEqualTo(state.icon)
+ }
+
+ @Test
+ fun supplierOnly_hasIcon() {
+ val state =
+ QSTile.State().apply {
+ iconSupplier = Supplier { ResourceIcon.get(R.drawable.android) }
+ }
+ val uiState = state.toUiState()
+
+ assertThat(uiState.icon).isEqualTo(state.iconSupplier.get())
+ }
+
+ @Test
+ fun noIconOrSupplier_iconNull() {
+ val state = QSTile.State()
+ val uiState = state.toUiState()
+
+ assertThat(uiState.icon).isNull()
+ }
+
private fun QSTile.State.toUiState() = toUiState(resources)
}
diff --git a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/BounceableInfo.kt b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/BounceableInfo.kt
index b9994d7bb821..c9d767e6d152 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/BounceableInfo.kt
+++ b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/BounceableInfo.kt
@@ -16,6 +16,7 @@
package com.android.systemui.qs.panels.ui.compose
+import android.processor.immutability.Immutable
import com.android.compose.animation.Bounceable
import com.android.systemui.qs.panels.shared.model.SizedTile
import com.android.systemui.qs.panels.ui.model.GridCell
@@ -23,6 +24,7 @@ import com.android.systemui.qs.panels.ui.model.TileGridCell
import com.android.systemui.qs.panels.ui.viewmodel.BounceableTileViewModel
import com.android.systemui.qs.panels.ui.viewmodel.TileViewModel
+@Immutable
data class BounceableInfo(
val bounceable: BounceableTileViewModel,
val previousTile: Bounceable?,
diff --git a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/QuickQuickSettings.kt b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/QuickQuickSettings.kt
index 2928ad117922..8fda23d54625 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/QuickQuickSettings.kt
+++ b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/QuickQuickSettings.kt
@@ -20,6 +20,7 @@ import androidx.compose.foundation.layout.Box
import androidx.compose.runtime.Composable
import androidx.compose.runtime.DisposableEffect
import androidx.compose.runtime.getValue
+import androidx.compose.runtime.key
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Modifier
@@ -67,17 +68,20 @@ fun SceneScope.QuickQuickSettings(
val it = sizedTiles[spanIndex]
val column = cellIndex % columns
cellIndex += it.width
- Tile(
- tile = it.tile,
- iconOnly = it.isIcon,
- modifier = Modifier.element(it.tile.spec.toElementKey(spanIndex)),
- squishiness = { squishiness },
- coroutineScope = scope,
- bounceableInfo = bounceables.bounceableInfo(it, spanIndex, column, columns),
- tileHapticsViewModelFactoryProvider = viewModel.tileHapticsViewModelFactoryProvider,
- // There should be no QuickQuickSettings when the details view is enabled.
- detailsViewModel = null,
- )
+ key(it.tile.spec) {
+ Tile(
+ tile = it.tile,
+ iconOnly = it.isIcon,
+ modifier = Modifier.element(it.tile.spec.toElementKey(spanIndex)),
+ squishiness = { squishiness },
+ coroutineScope = scope,
+ bounceableInfo = bounceables.bounceableInfo(it, spanIndex, column, columns),
+ tileHapticsViewModelFactoryProvider =
+ viewModel.tileHapticsViewModelFactoryProvider,
+ // There should be no QuickQuickSettings when the details view is enabled.
+ detailsViewModel = null,
+ )
+ }
}
}
}
diff --git a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/CommonTile.kt b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/CommonTile.kt
index d72d5f127bba..85658bb71c8b 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/CommonTile.kt
+++ b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/CommonTile.kt
@@ -16,6 +16,7 @@
package com.android.systemui.qs.panels.ui.compose.infinitegrid
+import android.content.Context
import android.graphics.drawable.Animatable
import android.graphics.drawable.AnimatedVectorDrawable
import android.graphics.drawable.Drawable
@@ -83,7 +84,7 @@ private const val TEST_TAG_TOGGLE = "qs_tile_toggle_target"
fun LargeTileContent(
label: String,
secondaryLabel: String?,
- icon: Icon,
+ iconProvider: Context.() -> Icon,
sideDrawable: Drawable?,
colors: TileColors,
squishiness: () -> Float,
@@ -129,7 +130,7 @@ fun LargeTileContent(
}
) {
SmallTileContent(
- icon = icon,
+ iconProvider = iconProvider,
color = colors.icon,
size = { CommonTileDefaults.LargeTileIconSize },
modifier = Modifier.align(Alignment.Center),
@@ -194,14 +195,15 @@ fun LargeTileLabels(
@Composable
fun SmallTileContent(
modifier: Modifier = Modifier,
- icon: Icon,
+ iconProvider: Context.() -> Icon,
color: Color,
size: () -> Dp = { CommonTileDefaults.IconSize },
animateToEnd: Boolean = false,
) {
+ val context = LocalContext.current
+ val icon = iconProvider(context)
val animatedColor by animateColorAsState(color, label = "QSTileIconColor")
val iconModifier = modifier.size({ size().roundToPx() }, { size().roundToPx() })
- val context = LocalContext.current
val loadedDrawable =
remember(icon, context) {
when (icon) {
diff --git a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/EditTile.kt b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/EditTile.kt
index d975f104d538..d2ee126ace91 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/EditTile.kt
+++ b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/EditTile.kt
@@ -19,7 +19,6 @@
package com.android.systemui.qs.panels.ui.compose.infinitegrid
import androidx.compose.animation.AnimatedContent
-import androidx.compose.animation.AnimatedVisibility
import androidx.compose.animation.animateContentSize
import androidx.compose.animation.core.LinearEasing
import androidx.compose.animation.core.animateDpAsState
@@ -76,6 +75,7 @@ import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.runtime.derivedStateOf
import androidx.compose.runtime.getValue
+import androidx.compose.runtime.key
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
@@ -460,29 +460,34 @@ private fun AvailableTileGrid(
Modifier.fillMaxWidth().wrapContentHeight().testTag(AVAILABLE_TILES_GRID_TEST_TAG),
) {
groupedTiles.forEach { (category, tiles) ->
- Text(
- text = category.label.load() ?: "",
- fontSize = 20.sp,
- color = labelColors.label,
- modifier = Modifier.fillMaxWidth().padding(start = 16.dp, bottom = 8.dp, top = 8.dp),
- )
- tiles.chunked(columns).forEach { row ->
- Row(
- horizontalArrangement = spacedBy(TileArrangementPadding),
- modifier = Modifier.fillMaxWidth().height(IntrinsicSize.Max),
- ) {
- row.forEachIndexed { index, tileGridCell ->
- AvailableTileGridCell(
- cell = tileGridCell,
- index = index,
- dragAndDropState = dragAndDropState,
- selectionState = selectionState,
- modifier = Modifier.weight(1f).fillMaxHeight(),
- )
- }
+ key(category) {
+ Text(
+ text = category.label.load() ?: "",
+ fontSize = 20.sp,
+ color = labelColors.label,
+ modifier =
+ Modifier.fillMaxWidth().padding(start = 16.dp, bottom = 8.dp, top = 8.dp),
+ )
+ tiles.chunked(columns).forEach { row ->
+ Row(
+ horizontalArrangement = spacedBy(TileArrangementPadding),
+ modifier = Modifier.fillMaxWidth().height(IntrinsicSize.Max),
+ ) {
+ row.forEachIndexed { index, tileGridCell ->
+ key(tileGridCell.tile.tileSpec) {
+ AvailableTileGridCell(
+ cell = tileGridCell,
+ index = index,
+ dragAndDropState = dragAndDropState,
+ selectionState = selectionState,
+ modifier = Modifier.weight(1f).fillMaxHeight(),
+ )
+ }
+ }
- // Spacers for incomplete rows
- repeat(columns - row.size) { Spacer(modifier = Modifier.weight(1f)) }
+ // Spacers for incomplete rows
+ repeat(columns - row.size) { Spacer(modifier = Modifier.weight(1f)) }
+ }
}
}
}
@@ -711,7 +716,7 @@ private fun AvailableTileGridCell(
) {
// Icon
SmallTileContent(
- icon = cell.tile.icon,
+ iconProvider = { cell.tile.icon },
color = colors.icon,
animateToEnd = true,
modifier = Modifier.align(Alignment.Center),
@@ -781,7 +786,7 @@ fun EditTile(
// Icon
Box(Modifier.size(ToggleTargetSize)) {
SmallTileContent(
- icon = tile.icon,
+ iconProvider = { tile.icon },
color = colors.icon,
animateToEnd = true,
size = { CommonTileDefaults.IconSize - iconSizeDiff * progress() },
diff --git a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/InfiniteGridLayout.kt b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/InfiniteGridLayout.kt
index 8fd99a52eceb..66961b6efe46 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/InfiniteGridLayout.kt
+++ b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/InfiniteGridLayout.kt
@@ -19,6 +19,7 @@ package com.android.systemui.qs.panels.ui.compose.infinitegrid
import androidx.compose.runtime.Composable
import androidx.compose.runtime.DisposableEffect
import androidx.compose.runtime.getValue
+import androidx.compose.runtime.key
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.Modifier
@@ -94,16 +95,18 @@ constructor(
val it = sizedTiles[spanIndex]
val column = cellIndex % columns
cellIndex += it.width
- Tile(
- tile = it.tile,
- iconOnly = iconTilesViewModel.isIconTile(it.tile.spec),
- modifier = Modifier.element(it.tile.spec.toElementKey(spanIndex)),
- squishiness = { squishiness },
- tileHapticsViewModelFactoryProvider = tileHapticsViewModelFactoryProvider,
- coroutineScope = scope,
- bounceableInfo = bounceables.bounceableInfo(it, spanIndex, column, columns),
- detailsViewModel = detailsViewModel,
- )
+ key(it.tile.spec) {
+ Tile(
+ tile = it.tile,
+ iconOnly = iconTilesViewModel.isIconTile(it.tile.spec),
+ modifier = Modifier.element(it.tile.spec.toElementKey(spanIndex)),
+ squishiness = { squishiness },
+ tileHapticsViewModelFactoryProvider = tileHapticsViewModelFactoryProvider,
+ coroutineScope = scope,
+ bounceableInfo = bounceables.bounceableInfo(it, spanIndex, column, columns),
+ detailsViewModel = detailsViewModel,
+ )
+ }
}
}
diff --git a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/Tile.kt b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/Tile.kt
index 13b331163d44..47238d176b36 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/Tile.kt
+++ b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/compose/infinitegrid/Tile.kt
@@ -18,6 +18,7 @@
package com.android.systemui.qs.panels.ui.compose.infinitegrid
+import android.content.Context
import android.content.res.Resources
import android.service.quicksettings.Tile.STATE_ACTIVE
import android.service.quicksettings.Tile.STATE_INACTIVE
@@ -45,7 +46,10 @@ import androidx.compose.foundation.shape.RoundedCornerShape
import androidx.compose.material3.MaterialTheme
import androidx.compose.runtime.Composable
import androidx.compose.runtime.ReadOnlyComposable
+import androidx.compose.runtime.State
+import androidx.compose.runtime.derivedStateOf
import androidx.compose.runtime.getValue
+import androidx.compose.runtime.produceState
import androidx.compose.runtime.remember
import androidx.compose.runtime.rememberUpdatedState
import androidx.compose.ui.Alignment
@@ -65,7 +69,6 @@ import androidx.compose.ui.semantics.toggleableState
import androidx.compose.ui.unit.Density
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.dp
-import androidx.lifecycle.compose.collectAsStateWithLifecycle
import com.android.app.tracing.coroutines.launchTraced as launch
import com.android.compose.animation.Expandable
import com.android.compose.animation.bounceable
@@ -90,7 +93,6 @@ import com.android.systemui.qs.panels.ui.viewmodel.toUiState
import com.android.systemui.qs.tileimpl.QSTileImpl
import com.android.systemui.qs.ui.compose.borderOnFocus
import com.android.systemui.res.R
-import java.util.function.Supplier
import kotlinx.coroutines.CoroutineScope
private const val TEST_TAG_SMALL = "qs_tile_small"
@@ -126,10 +128,19 @@ fun Tile(
modifier: Modifier = Modifier,
detailsViewModel: DetailsViewModel?,
) {
- val state: QSTile.State by tile.state.collectAsStateWithLifecycle(tile.currentState)
val currentBounceableInfo by rememberUpdatedState(bounceableInfo)
val resources = resources()
- val uiState = remember(state, resources) { state.toUiState(resources) }
+
+ /*
+ * Use produce state because [QSTile.State] doesn't have well defined equals (due to
+ * inheritance). This way, even if tile.state changes, uiState may not change and lead to
+ * recomposition.
+ */
+ val uiState by
+ produceState(tile.currentState.toUiState(resources), tile, resources) {
+ tile.state.collect { value = it.toUiState(resources) }
+ }
+
val colors = TileDefaults.getColorForState(uiState, iconOnly)
val hapticsViewModel: TileHapticsViewModel? =
rememberViewModel(traceName = "TileHapticsViewModel") {
@@ -137,7 +148,7 @@ fun Tile(
}
// TODO(b/361789146): Draw the shapes instead of clipping
- val tileShape = TileDefaults.animateTileShape(uiState.state)
+ val tileShape by TileDefaults.animateTileShapeAsState(uiState.state)
val animatedColor by animateColorAsState(colors.background, label = "QSTileBackgroundColor")
TileExpandable(
@@ -187,15 +198,15 @@ fun Tile(
uiState = uiState,
iconOnly = iconOnly,
) {
- val icon = getTileIcon(icon = uiState.icon)
+ val iconProvider: Context.() -> Icon = { getTileIcon(icon = uiState.icon) }
if (iconOnly) {
SmallTileContent(
- icon = icon,
+ iconProvider = iconProvider,
color = colors.icon,
modifier = Modifier.align(Alignment.Center),
)
} else {
- val iconShape = TileDefaults.animateIconShape(uiState.state)
+ val iconShape by TileDefaults.animateIconShapeAsState(uiState.state)
val secondaryClick: (() -> Unit)? =
{
hapticsViewModel?.setTileInteractionState(
@@ -207,7 +218,7 @@ fun Tile(
LargeTileContent(
label = uiState.label,
secondaryLabel = uiState.secondaryLabel,
- icon = icon,
+ iconProvider = iconProvider,
sideDrawable = uiState.sideDrawable,
colors = colors,
iconShape = iconShape,
@@ -269,7 +280,7 @@ fun LargeStaticTile(uiState: TileUiState, modifier: Modifier = Modifier) {
Box(
modifier
- .clip(TileDefaults.animateTileShape(state = uiState.state))
+ .clip(TileDefaults.animateTileShapeAsState(state = uiState.state).value)
.background(colors.background)
.height(TileHeight)
.tilePadding()
@@ -277,7 +288,7 @@ fun LargeStaticTile(uiState: TileUiState, modifier: Modifier = Modifier) {
LargeTileContent(
label = uiState.label,
secondaryLabel = "",
- icon = getTileIcon(icon = uiState.icon),
+ iconProvider = { getTileIcon(icon = uiState.icon) },
sideDrawable = null,
colors = colors,
squishiness = { 1f },
@@ -285,14 +296,12 @@ fun LargeStaticTile(uiState: TileUiState, modifier: Modifier = Modifier) {
}
}
-@Composable
-private fun getTileIcon(icon: Supplier<QSTile.Icon?>): Icon {
- val context = LocalContext.current
- return icon.get()?.let {
+private fun Context.getTileIcon(icon: QSTile.Icon?): Icon {
+ return icon?.let {
if (it is QSTileImpl.ResourceIcon) {
Icon.Resource(it.resId, null)
} else {
- Icon.Loaded(it.getDrawable(context), null)
+ Icon.Loaded(it.getDrawable(this), null)
}
} ?: Icon.Resource(R.drawable.ic_error_outline, null)
}
@@ -348,6 +357,7 @@ private object TileDefaults {
/** An active tile without dual target uses the active color as background */
@Composable
+ @ReadOnlyComposable
fun activeTileColors(): TileColors =
TileColors(
background = MaterialTheme.colorScheme.primary,
@@ -359,6 +369,7 @@ private object TileDefaults {
/** An active tile with dual target only show the active color on the icon */
@Composable
+ @ReadOnlyComposable
fun activeDualTargetTileColors(): TileColors =
TileColors(
background = MaterialTheme.colorScheme.surfaceVariant,
@@ -369,6 +380,7 @@ private object TileDefaults {
)
@Composable
+ @ReadOnlyComposable
fun inactiveDualTargetTileColors(): TileColors =
TileColors(
background = MaterialTheme.colorScheme.surfaceVariant,
@@ -379,6 +391,7 @@ private object TileDefaults {
)
@Composable
+ @ReadOnlyComposable
fun inactiveTileColors(): TileColors =
TileColors(
background = MaterialTheme.colorScheme.surfaceVariant,
@@ -389,6 +402,7 @@ private object TileDefaults {
)
@Composable
+ @ReadOnlyComposable
fun unavailableTileColors(): TileColors =
TileColors(
background = MaterialTheme.colorScheme.surface,
@@ -399,6 +413,7 @@ private object TileDefaults {
)
@Composable
+ @ReadOnlyComposable
fun getColorForState(uiState: TileUiState, iconOnly: Boolean): TileColors {
return when (uiState.state) {
STATE_ACTIVE -> {
@@ -422,8 +437,8 @@ private object TileDefaults {
}
@Composable
- fun animateIconShape(state: Int): RoundedCornerShape {
- return animateShape(
+ fun animateIconShapeAsState(state: Int): State<RoundedCornerShape> {
+ return animateShapeAsState(
state = state,
activeCornerRadius = ActiveIconCornerRadius,
label = "QSTileCornerRadius",
@@ -431,8 +446,8 @@ private object TileDefaults {
}
@Composable
- fun animateTileShape(state: Int): RoundedCornerShape {
- return animateShape(
+ fun animateTileShapeAsState(state: Int): State<RoundedCornerShape> {
+ return animateShapeAsState(
state = state,
activeCornerRadius = ActiveTileCornerRadius,
label = "QSTileIconCornerRadius",
@@ -440,7 +455,11 @@ private object TileDefaults {
}
@Composable
- fun animateShape(state: Int, activeCornerRadius: Dp, label: String): RoundedCornerShape {
+ fun animateShapeAsState(
+ state: Int,
+ activeCornerRadius: Dp,
+ label: String,
+ ): State<RoundedCornerShape> {
val animatedCornerRadius by
animateDpAsState(
targetValue =
@@ -459,7 +478,7 @@ private object TileDefaults {
}
}
}
- return RoundedCornerShape(corner)
+ return remember { derivedStateOf { RoundedCornerShape(corner) } }
}
}
diff --git a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiState.kt b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiState.kt
index 2fc7f0f9d67b..19e542e6a21e 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiState.kt
+++ b/packages/SystemUI/src/com/android/systemui/qs/panels/ui/viewmodel/TileUiState.kt
@@ -27,7 +27,6 @@ import androidx.compose.ui.state.ToggleableState
import com.android.systemui.plugins.qs.QSTile
import com.android.systemui.qs.tileimpl.SubtitleArrayMapping
import com.android.systemui.res.R
-import java.util.function.Supplier
@Immutable
data class TileUiState(
@@ -36,7 +35,7 @@ data class TileUiState(
val state: Int,
val handlesLongClick: Boolean,
val handlesSecondaryClick: Boolean,
- val icon: Supplier<QSTile.Icon?>,
+ val icon: QSTile.Icon?,
val sideDrawable: Drawable?,
val accessibilityUiState: AccessibilityUiState,
)
@@ -91,7 +90,7 @@ fun QSTile.State.toUiState(resources: Resources): TileUiState {
state = if (disabledByPolicy) Tile.STATE_UNAVAILABLE else state,
handlesLongClick = handlesLongClick,
handlesSecondaryClick = handlesSecondaryClick,
- icon = icon?.let { Supplier { icon } } ?: iconSupplier ?: Supplier { null },
+ icon = icon ?: iconSupplier?.get(),
sideDrawable = sideViewCustomDrawable,
AccessibilityUiState(
contentDescription?.toString() ?: "",