Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 5bebc55f authored by George Lin's avatar George Lin Committed by Android (Google) Code Review
Browse files

Merge "Preview quick affordances" into main

parents 3ba79d2f ab24674c
Loading
Loading
Loading
Loading
+10 −3
Original line number Diff line number Diff line
@@ -18,10 +18,17 @@
package com.android.systemui.shared.quickaffordance.shared.model

object KeyguardPreviewConstants {
    const val MESSAGE_ID_DEFAULT_PREVIEW = 707
    const val MESSAGE_ID_HIDE_SMART_SPACE = 1111
    const val KEY_HIDE_SMART_SPACE = "hide_smart_space"
    const val MESSAGE_ID_PREVIEW_QUICK_AFFORDANCE_SELECTED = 1988
    const val MESSAGE_ID_SLOT_SELECTED = 1337
    const val KEY_SLOT_ID = "slot_id"
    const val KEY_INITIALLY_SELECTED_SLOT_ID = "initially_selected_slot_id"
    const val MESSAGE_ID_START_CUSTOMIZING_QUICK_AFFORDANCES = 214

    const val KEY_HIDE_SMART_SPACE = "hide_smart_space"
    const val KEY_HIGHLIGHT_QUICK_AFFORDANCES = "highlight_quick_affordances"
    const val KEY_INITIALLY_SELECTED_SLOT_ID = "initially_selected_slot_id"
    const val KEY_QUICK_AFFORDANCE_ID = "quick_affordance_id"
    const val KEY_SLOT_ID = "slot_id"

    const val KEYGUARD_QUICK_AFFORDANCE_ID_NONE = "none"
}
+9 −0
Original line number Diff line number Diff line
@@ -308,6 +308,15 @@ class KeyguardQuickAffordanceRepositoryTest : SysuiTestCase() {
            )
        }

    @Test
    fun getConfig() =
        testScope.runTest {
            assertThat(underTest.getConfig(FakeCustomizationProviderClient.AFFORDANCE_1))
                .isEqualTo(config1)
            assertThat(underTest.getConfig(FakeCustomizationProviderClient.AFFORDANCE_2))
                .isEqualTo(config2)
        }

    private fun assertSelections(
        observed: Map<String, List<KeyguardQuickAffordanceConfig>>?,
        expected: Map<String, List<KeyguardQuickAffordanceConfig>>,
+58 −0
Original line number Diff line number Diff line
@@ -425,6 +425,64 @@ class KeyguardQuickAffordanceInteractorTest : SysuiTestCase() {
            assertThat(visibleModel.activationState).isEqualTo(ActivationState.Active)
        }

    @Test
    fun quickAffordanceAlwaysVisible_withNonNullOverrideKeyguardQuickAffordanceId() =
        testScope.runTest {
            quickAccessWallet.setState(
                KeyguardQuickAffordanceConfig.LockScreenState.Visible(
                    icon = ICON,
                    activationState = ActivationState.Active,
                )
            )
            homeControls.setState(
                KeyguardQuickAffordanceConfig.LockScreenState.Visible(
                    icon = ICON,
                    activationState = ActivationState.Active,
                )
            )

            // The default case
            val collectedValue =
                collectLastValue(
                    underTest.quickAffordanceAlwaysVisible(
                        KeyguardQuickAffordancePosition.BOTTOM_START,
                    )
                )
            assertThat(collectedValue())
                .isInstanceOf(KeyguardQuickAffordanceModel.Visible::class.java)
            val visibleModel = collectedValue() as KeyguardQuickAffordanceModel.Visible
            assertThat(visibleModel.configKey)
                .isEqualTo(
                    "${KeyguardQuickAffordanceSlots.SLOT_ID_BOTTOM_START}::${homeControls.key}"
                )
            assertThat(visibleModel.icon).isEqualTo(ICON)
            assertThat(visibleModel.icon.contentDescription)
                .isEqualTo(ContentDescription.Resource(res = CONTENT_DESCRIPTION_RESOURCE_ID))
            assertThat(visibleModel.activationState).isEqualTo(ActivationState.Active)

            // With override
            val collectedValueWithOverride =
                collectLastValue(
                    underTest.quickAffordanceAlwaysVisible(
                        position = KeyguardQuickAffordancePosition.BOTTOM_START,
                        overrideQuickAffordanceId =
                            BuiltInKeyguardQuickAffordanceKeys.QUICK_ACCESS_WALLET,
                    )
                )
            assertThat(collectedValueWithOverride())
                .isInstanceOf(KeyguardQuickAffordanceModel.Visible::class.java)
            val visibleModelWithOverride =
                collectedValueWithOverride() as KeyguardQuickAffordanceModel.Visible
            assertThat(visibleModelWithOverride.configKey)
                .isEqualTo(
                    "${KeyguardQuickAffordanceSlots.SLOT_ID_BOTTOM_START}::${quickAccessWallet.key}"
                )
            assertThat(visibleModelWithOverride.icon).isEqualTo(ICON)
            assertThat(visibleModelWithOverride.icon.contentDescription)
                .isEqualTo(ContentDescription.Resource(res = CONTENT_DESCRIPTION_RESOURCE_ID))
            assertThat(visibleModelWithOverride.activationState).isEqualTo(ActivationState.Active)
        }

    @Test
    fun select() =
        testScope.runTest {
+29 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2024 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package com.android.systemui.keyguard

import com.android.systemui.Flags

/** Helper for reading or using the new picker UI flag. */
@Suppress("NOTHING_TO_INLINE")
object NewPickerUiKeyguardPreview {

    /** Is the new picker UI enabled */
    @JvmStatic
    inline val isEnabled
        get() = Flags.newPickerUi()
}
+13 −5
Original line number Diff line number Diff line
@@ -22,7 +22,6 @@ import android.content.Intent
import android.os.UserHandle
import android.util.LayoutDirection
import com.android.systemui.Dumpable
import com.android.systemui.res.R
import com.android.systemui.common.coroutine.ChannelExt.trySendWithFailureLogging
import com.android.systemui.common.coroutine.ConflatedCallbackFlow
import com.android.systemui.dagger.SysUISingleton
@@ -35,6 +34,7 @@ import com.android.systemui.keyguard.data.quickaffordance.KeyguardQuickAffordanc
import com.android.systemui.keyguard.data.quickaffordance.KeyguardQuickAffordanceSelectionManager
import com.android.systemui.keyguard.shared.model.KeyguardQuickAffordancePickerRepresentation
import com.android.systemui.keyguard.shared.model.KeyguardSlotPickerRepresentation
import com.android.systemui.res.R
import com.android.systemui.settings.UserTracker
import java.io.PrintWriter
import javax.inject.Inject
@@ -61,10 +61,13 @@ constructor(
    private val remoteUserSelectionManager: KeyguardQuickAffordanceRemoteUserSelectionManager,
    private val userTracker: UserTracker,
    legacySettingSyncer: KeyguardQuickAffordanceLegacySettingSyncer,
    private val configs: Set<@JvmSuppressWildcards KeyguardQuickAffordanceConfig>,
    configs: Set<@JvmSuppressWildcards KeyguardQuickAffordanceConfig>,
    dumpManager: DumpManager,
    userHandle: UserHandle,
) {
    // Configs for all keyguard quick affordances, mapped by the quick affordance ID as key
    private val configsByAffordanceId: Map<String, KeyguardQuickAffordanceConfig> =
        configs.associateBy { it.key }
    private val userId: Flow<Int> =
        ConflatedCallbackFlow.conflatedCallbackFlow {
            val callback =
@@ -126,7 +129,7 @@ constructor(
     */
    fun getCurrentSelections(slotId: String): List<KeyguardQuickAffordanceConfig> {
        val selections = selectionManager.value.getSelections().getOrDefault(slotId, emptyList())
        return configs.filter { selections.contains(it.key) }
        return configsByAffordanceId.values.filter { selections.contains(it.key) }
    }

    /**
@@ -159,7 +162,7 @@ constructor(
     */
    suspend fun getAffordancePickerRepresentations():
        List<KeyguardQuickAffordancePickerRepresentation> {
        return configs
        return configsByAffordanceId.values
            .associateWith { config -> config.getPickerScreenState() }
            .filterNot { (_, pickerState) ->
                pickerState is KeyguardQuickAffordanceConfig.PickerScreenState.UnavailableOnDevice
@@ -226,6 +229,11 @@ constructor(
        }
    }

    /** Get the config of a quick affordance. */
    fun getConfig(quickAffordanceId: String): KeyguardQuickAffordanceConfig? {
        return configsByAffordanceId[quickAffordanceId]
    }

    private inner class Dumpster : Dumpable {
        override fun dump(pw: PrintWriter, args: Array<out String>) {
            val slotPickerRepresentations = getSlotPickerRepresentations()
@@ -246,7 +254,7 @@ constructor(
                pw.println("    $slotId$selectionText (capacity = $capacity)")
            }
            pw.println("Available affordances on device:")
            configs.forEach { config ->
            configsByAffordanceId.values.forEach { config ->
                pw.println("    ${config.key} (\"${config.pickerName()}\")")
            }
        }
Loading