summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
author Lucas Silva <lusilva@google.com> 2025-02-19 14:45:32 -0500
committer Lucas Silva <lusilva@google.com> 2025-02-20 08:27:46 -0500
commitfecfb9756dcebd824e74637a75bb623cc30846cc (patch)
tree7f72a49a06c79601a1e3fed1741cfea80f50a508
parent1be4df1376b354024cb723de8b6bc9cb26568293 (diff)
Fix swipe-to-bouncer on GH with face auth
When swiping up the bouncer on glanceable hub, if the user has a large number of notifications, the notification limit is taking effect mid-swipe and causing the bouncer to hide itself. This is because the bouncer/alternate bouncer states are considered "lockscreen" states, even if the bouncer is shown over the glanceable hub instead of over the lockscreen. This change does not consider the bouncer states as "lockscreen" if they are being shown over the glanceable hub. Fixes: 396689194 Test: atest SharedNotificationContainerViewModelTest Flag: com.android.systemui.glanceable_hub_v2 Change-Id: I8cfa5ff3074d7d34f06b7db5a1051e367e290889
-rw-r--r--packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModelTest.kt52
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModel.kt47
2 files changed, 74 insertions, 25 deletions
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModelTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModelTest.kt
index 21297e3e64b7..c630a1c1e006 100644
--- a/packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModelTest.kt
+++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModelTest.kt
@@ -17,14 +17,15 @@
package com.android.systemui.statusbar.notification.stack.ui.viewmodel
+import android.platform.test.annotations.EnableFlags
import android.platform.test.flag.junit.FlagsParameterization
import androidx.test.filters.SmallTest
-import com.android.compose.animation.scene.ObservableTransitionState
+import com.android.systemui.Flags.FLAG_GLANCEABLE_HUB_V2
import com.android.systemui.SysuiTestCase
import com.android.systemui.bouncer.data.repository.keyguardBouncerRepository
import com.android.systemui.common.shared.model.NotificationContainerBounds
import com.android.systemui.common.ui.data.repository.fakeConfigurationRepository
-import com.android.systemui.communal.data.repository.communalSceneRepository
+import com.android.systemui.communal.domain.interactor.communalSceneInteractor
import com.android.systemui.communal.shared.model.CommunalScenes
import com.android.systemui.coroutines.collectLastValue
import com.android.systemui.coroutines.collectValues
@@ -54,11 +55,14 @@ import com.android.systemui.keyguard.ui.viewmodel.AodBurnInViewModel
import com.android.systemui.keyguard.ui.viewmodel.ViewStateAccessor
import com.android.systemui.keyguard.ui.viewmodel.aodBurnInViewModel
import com.android.systemui.keyguard.ui.viewmodel.keyguardRootViewModel
+import com.android.systemui.kosmos.collectLastValue
+import com.android.systemui.kosmos.runTest
import com.android.systemui.kosmos.testScope
import com.android.systemui.res.R
import com.android.systemui.scene.data.repository.Idle
import com.android.systemui.scene.data.repository.Transition
import com.android.systemui.scene.data.repository.setTransition
+import com.android.systemui.scene.shared.flag.SceneContainerFlag
import com.android.systemui.scene.shared.model.Scenes
import com.android.systemui.shade.domain.interactor.enableDualShade
import com.android.systemui.shade.domain.interactor.enableSingleShade
@@ -125,7 +129,6 @@ class SharedNotificationContainerViewModelTest(flags: FlagsParameterization) : S
kosmos.sharedNotificationContainerInteractor
}
private val largeScreenHeaderHelper by lazy { kosmos.mockLargeScreenHeaderHelper }
- private val communalSceneRepository by lazy { kosmos.communalSceneRepository }
lateinit var underTest: SharedNotificationContainerViewModel
@@ -591,6 +594,25 @@ class SharedNotificationContainerViewModelTest(flags: FlagsParameterization) : S
}
@Test
+ @DisableSceneContainer
+ @EnableFlags(FLAG_GLANCEABLE_HUB_V2)
+ fun isOnLockscreenFalseWhenCommunalShowing() =
+ kosmos.runTest {
+ val isOnLockscreen by collectLastValue(underTest.isOnLockscreen)
+
+ setTransition(
+ sceneTransition = Idle(Scenes.Bouncer),
+ stateTransition = TransitionStep(from = LOCKSCREEN, to = PRIMARY_BOUNCER),
+ )
+ assertThat(isOnLockscreen).isTrue()
+
+ testScope.showCommunalScene()
+
+ // If bouncer is showing over the hub, it should not be considered on lockscreen
+ assertThat(isOnLockscreen).isFalse()
+ }
+
+ @Test
fun isOnLockscreenWithoutShade() =
testScope.runTest {
val isOnLockscreenWithoutShade by collectLastValue(underTest.isOnLockscreenWithoutShade)
@@ -1472,20 +1494,24 @@ class SharedNotificationContainerViewModelTest(flags: FlagsParameterization) : S
}
private fun TestScope.showCommunalScene() {
- val transitionState =
- MutableStateFlow<ObservableTransitionState>(
- ObservableTransitionState.Idle(CommunalScenes.Communal)
- )
- communalSceneRepository.setTransitionState(transitionState)
+ val targetScene =
+ if (SceneContainerFlag.isEnabled) {
+ Scenes.Communal
+ } else {
+ CommunalScenes.Communal
+ }
+ kosmos.communalSceneInteractor.changeScene(targetScene, "test")
runCurrent()
}
private fun TestScope.hideCommunalScene() {
- val transitionState =
- MutableStateFlow<ObservableTransitionState>(
- ObservableTransitionState.Idle(CommunalScenes.Blank)
- )
- communalSceneRepository.setTransitionState(transitionState)
+ val targetScene =
+ if (SceneContainerFlag.isEnabled) {
+ Scenes.Lockscreen
+ } else {
+ CommunalScenes.Blank
+ }
+ kosmos.communalSceneInteractor.changeScene(targetScene, "test")
runCurrent()
}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModel.kt b/packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModel.kt
index 5c81c8e22bfc..34b65603542c 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModel.kt
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/stack/ui/viewmodel/SharedNotificationContainerViewModel.kt
@@ -20,6 +20,7 @@ package com.android.systemui.statusbar.notification.stack.ui.viewmodel
import android.content.Context
import androidx.annotation.VisibleForTesting
import com.android.app.tracing.coroutines.flow.flowName
+import com.android.systemui.Flags.glanceableHubV2
import com.android.systemui.common.shared.model.NotificationContainerBounds
import com.android.systemui.common.ui.domain.interactor.ConfigurationInteractor
import com.android.systemui.communal.domain.interactor.CommunalSceneInteractor
@@ -87,7 +88,9 @@ import com.android.systemui.statusbar.notification.domain.interactor.HeadsUpNoti
import com.android.systemui.statusbar.notification.stack.domain.interactor.NotificationStackAppearanceInteractor
import com.android.systemui.statusbar.notification.stack.domain.interactor.SharedNotificationContainerInteractor
import com.android.systemui.unfold.domain.interactor.UnfoldTransitionInteractor
+import com.android.systemui.util.kotlin.BooleanFlowOperators.allOf
import com.android.systemui.util.kotlin.BooleanFlowOperators.anyOf
+import com.android.systemui.util.kotlin.BooleanFlowOperators.not
import com.android.systemui.util.kotlin.FlowDumperImpl
import com.android.systemui.util.kotlin.Utils.Companion.sample as sampleCombine
import com.android.systemui.util.kotlin.sample
@@ -299,20 +302,40 @@ constructor(
.distinctUntilChanged()
.dumpWhileCollecting("configurationBasedDimensions")
+ private val isOnAnyBouncer: Flow<Boolean> =
+ anyOf(
+ keyguardTransitionInteractor.transitionValue(ALTERNATE_BOUNCER).map { it > 0f },
+ keyguardTransitionInteractor
+ .transitionValue(
+ scene = Scenes.Bouncer,
+ stateWithoutSceneContainer = PRIMARY_BOUNCER,
+ )
+ .map { it > 0f },
+ )
+
/** If the user is visually on one of the unoccluded lockscreen states. */
val isOnLockscreen: Flow<Boolean> =
- anyOf(
- keyguardTransitionInteractor.transitionValue(AOD).map { it > 0f },
- keyguardTransitionInteractor.transitionValue(DOZING).map { it > 0f },
- keyguardTransitionInteractor.transitionValue(ALTERNATE_BOUNCER).map { it > 0f },
- keyguardTransitionInteractor
- .transitionValue(
- scene = Scenes.Bouncer,
- stateWithoutSceneContainer = PRIMARY_BOUNCER,
- )
- .map { it > 0f },
- keyguardTransitionInteractor.transitionValue(LOCKSCREEN).map { it > 0f },
- )
+ if (glanceableHubV2()) {
+ anyOf(
+ keyguardTransitionInteractor.transitionValue(AOD).map { it > 0f },
+ keyguardTransitionInteractor.transitionValue(DOZING).map { it > 0f },
+ keyguardTransitionInteractor.transitionValue(LOCKSCREEN).map { it > 0f },
+ allOf(
+ // Exclude bouncer showing over communal hub, as this should not be
+ // considered
+ // "lockscreen"
+ not(communalSceneInteractor.isCommunalVisible),
+ isOnAnyBouncer,
+ ),
+ )
+ } else {
+ anyOf(
+ keyguardTransitionInteractor.transitionValue(AOD).map { it > 0f },
+ keyguardTransitionInteractor.transitionValue(DOZING).map { it > 0f },
+ keyguardTransitionInteractor.transitionValue(LOCKSCREEN).map { it > 0f },
+ isOnAnyBouncer,
+ )
+ }
.flowName("isOnLockscreen")
.stateIn(
scope = applicationScope,