Merge "Prevent keyguard from flashing after dismissing" into main
diff --git a/packages/SystemUI/multivalentTests/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractorTest.kt b/packages/SystemUI/multivalentTests/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractorTest.kt
index ebefb4d..b843fd5 100644
--- a/packages/SystemUI/multivalentTests/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractorTest.kt
+++ b/packages/SystemUI/multivalentTests/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractorTest.kt
@@ -225,6 +225,39 @@
         }
 
     @Test
+    fun dismissAlpha_onGlanceableHub_doesNotEmitWhenShadeResets() =
+        testScope.runTest {
+            val dismissAlpha by collectValues(underTest.dismissAlpha)
+            assertThat(dismissAlpha[0]).isEqualTo(1f)
+            assertThat(dismissAlpha.size).isEqualTo(1)
+
+            keyguardTransitionRepository.sendTransitionSteps(
+                from = KeyguardState.AOD,
+                to = KeyguardState.LOCKSCREEN,
+                testScope,
+            )
+
+            // User begins to swipe up
+            repository.setStatusBarState(StatusBarState.KEYGUARD)
+            repository.setKeyguardDismissible(true)
+            shadeRepository.setLegacyShadeExpansion(0.98f)
+
+            assertThat(dismissAlpha[1]).isGreaterThan(0.5f)
+            assertThat(dismissAlpha[1]).isLessThan(1f)
+            assertThat(dismissAlpha.size).isEqualTo(2)
+
+            keyguardTransitionRepository.sendTransitionSteps(
+                from = KeyguardState.LOCKSCREEN,
+                to = KeyguardState.GLANCEABLE_HUB,
+                testScope,
+            )
+
+            // Now reset the shade and verify we don't emit any new values
+            shadeRepository.setLegacyShadeExpansion(1f)
+            assertThat(dismissAlpha.size).isEqualTo(2)
+        }
+
+    @Test
     fun dismissAlpha_doesNotEmitWhileTransitioning() =
         testScope.runTest {
             val dismissAlpha by collectLastValue(underTest.dismissAlpha)
@@ -262,7 +295,7 @@
 
             configRepository.setDimensionPixelSize(
                 R.dimen.keyguard_translate_distance_on_swipe_up,
-                100
+                100,
             )
             configRepository.onAnyConfigurationChange()
 
@@ -284,7 +317,7 @@
 
             configRepository.setDimensionPixelSize(
                 R.dimen.keyguard_translate_distance_on_swipe_up,
-                100
+                100,
             )
             configRepository.onAnyConfigurationChange()
 
@@ -306,7 +339,7 @@
 
             configRepository.setDimensionPixelSize(
                 R.dimen.keyguard_translate_distance_on_swipe_up,
-                100
+                100,
             )
             configRepository.onAnyConfigurationChange()
 
@@ -328,7 +361,7 @@
 
             configRepository.setDimensionPixelSize(
                 R.dimen.keyguard_translate_distance_on_swipe_up,
-                100
+                100,
             )
             configRepository.onAnyConfigurationChange()
 
diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractor.kt b/packages/SystemUI/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractor.kt
index f6f0cc5..e444092 100644
--- a/packages/SystemUI/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractor.kt
+++ b/packages/SystemUI/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractor.kt
@@ -39,6 +39,7 @@
 import com.android.systemui.keyguard.shared.model.KeyguardState
 import com.android.systemui.keyguard.shared.model.KeyguardState.AOD
 import com.android.systemui.keyguard.shared.model.KeyguardState.DOZING
+import com.android.systemui.keyguard.shared.model.KeyguardState.GLANCEABLE_HUB
 import com.android.systemui.keyguard.shared.model.KeyguardState.GONE
 import com.android.systemui.keyguard.shared.model.KeyguardState.LOCKSCREEN
 import com.android.systemui.keyguard.shared.model.KeyguardState.OCCLUDED
@@ -167,10 +168,7 @@
      * but not vice-versa. Also accounts for [isDreamingWithOverlay]
      */
     val isDreaming: StateFlow<Boolean> =
-        merge(
-                repository.isDreaming,
-                repository.isDreamingWithOverlay,
-            )
+        merge(repository.isDreaming, repository.isDreamingWithOverlay)
             .stateIn(
                 scope = applicationScope,
                 started = SharingStarted.Eagerly,
@@ -242,7 +240,7 @@
                     .map { it == 1f }
                     .onStart { emit(false) }
                     .distinctUntilChanged(),
-                repository.topClippingBounds
+                repository.topClippingBounds,
             ) { isGone, topClippingBounds ->
                 if (!isGone) {
                     emit(topClippingBounds)
@@ -287,11 +285,10 @@
 
     /** Whether camera is launched over keyguard. */
     val isSecureCameraActive: Flow<Boolean> by lazy {
-        combine(
+        combine(isKeyguardVisible, primaryBouncerShowing, onCameraLaunchDetected) {
                 isKeyguardVisible,
-                primaryBouncerShowing,
-                onCameraLaunchDetected,
-            ) { isKeyguardVisible, isPrimaryBouncerShowing, cameraLaunchEvent ->
+                isPrimaryBouncerShowing,
+                cameraLaunchEvent ->
                 when {
                     isKeyguardVisible -> false
                     isPrimaryBouncerShowing -> false
@@ -328,15 +325,17 @@
                 keyguardTransitionInteractor.currentKeyguardState,
                 keyguardTransitionInteractor.transitionState,
                 isKeyguardDismissible,
+                keyguardTransitionInteractor.isFinishedIn(Scenes.Communal, GLANCEABLE_HUB),
             )
-            .filter { (_, _, _, step, _) -> !step.transitionState.isTransitioning() }
+            .filter { (_, _, _, step, _, _) -> !step.transitionState.isTransitioning() }
             .transform {
                 (
                     legacyShadeExpansion,
                     statusBarState,
                     currentKeyguardState,
                     step,
-                    isKeyguardDismissible) ->
+                    isKeyguardDismissible,
+                    onGlanceableHub) ->
                 if (
                     statusBarState == StatusBarState.KEYGUARD &&
                         isKeyguardDismissible &&
@@ -344,7 +343,9 @@
                         legacyShadeExpansion != 1f
                 ) {
                     emit(MathUtils.constrainedMap(0f, 1f, 0.95f, 1f, legacyShadeExpansion))
-                } else if (legacyShadeExpansion == 0f || legacyShadeExpansion == 1f) {
+                } else if (
+                    (legacyShadeExpansion == 0f || legacyShadeExpansion == 1f) && !onGlanceableHub
+                ) {
                     // Resets alpha state
                     emit(1f)
                 }
diff --git a/packages/SystemUI/tests/utils/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractorFactory.kt b/packages/SystemUI/tests/utils/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractorFactory.kt
index f5232ce..9593dfb 100644
--- a/packages/SystemUI/tests/utils/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractorFactory.kt
+++ b/packages/SystemUI/tests/utils/src/com/android/systemui/keyguard/domain/interactor/KeyguardInteractorFactory.kt
@@ -36,6 +36,7 @@
 import kotlinx.coroutines.flow.MutableSharedFlow
 import kotlinx.coroutines.flow.MutableStateFlow
 import kotlinx.coroutines.test.TestScope
+import org.mockito.kotlin.any
 
 /**
  * Simply put, I got tired of adding a constructor argument and then having to tweak dozens of
@@ -66,6 +67,7 @@
             mock<KeyguardTransitionInteractor>().also {
                 whenever(it.currentKeyguardState).thenReturn(currentKeyguardStateFlow)
                 whenever(it.transitionState).thenReturn(transitionStateFlow)
+                whenever(it.isFinishedIn(any(), any())).thenReturn(MutableStateFlow(false))
             }
         val configurationDimensionFlow = MutableSharedFlow<ConfigurationBasedDimensions>()
         configurationDimensionFlow.tryEmit(