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

Commit 26528230 authored by Shawn Lee's avatar Shawn Lee Committed by Android (Google) Code Review
Browse files

Merge "[Flexiglass] Base NSSL alpha off bouncer transition, and INVISIBLE when occluded" into main

parents b48c6ee6 62ced44a
Loading
Loading
Loading
Loading
+80 −0
Original line number Diff line number Diff line
@@ -20,6 +20,7 @@ import android.content.testableContext
import android.provider.Settings.Global.ONE_HANDED_KEYGUARD_SIDE
import androidx.test.ext.junit.runners.AndroidJUnit4
import androidx.test.filters.SmallTest
import com.android.compose.animation.scene.ObservableTransitionState
import com.android.internal.logging.uiEventLoggerFake
import com.android.systemui.SysuiTestCase
import com.android.systemui.authentication.data.repository.FakeAuthenticationRepository
@@ -39,13 +40,22 @@ import com.android.systemui.flags.EnableSceneContainer
import com.android.systemui.flags.Flags.FULL_SCREEN_USER_SWITCHER
import com.android.systemui.flags.fakeFeatureFlagsClassic
import com.android.systemui.keyguard.data.repository.fakeDeviceEntryFaceAuthRepository
import com.android.systemui.kosmos.collectLastValue
import com.android.systemui.kosmos.runCurrent
import com.android.systemui.kosmos.runTest
import com.android.systemui.kosmos.testScope
import com.android.systemui.power.data.repository.fakePowerRepository
import com.android.systemui.res.R
import com.android.systemui.scene.data.repository.sceneContainerRepository
import com.android.systemui.scene.shared.model.Overlays
import com.android.systemui.scene.shared.model.Scenes
import com.android.systemui.scene.transitionState
import com.android.systemui.testKosmos
import com.android.systemui.util.settings.fakeGlobalSettings
import com.google.common.truth.Truth.assertThat
import kotlin.time.Duration.Companion.seconds
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.flowOf
import kotlinx.coroutines.test.advanceTimeBy
import kotlinx.coroutines.test.runCurrent
import kotlinx.coroutines.test.runTest
@@ -368,6 +378,76 @@ class BouncerInteractorTest : SysuiTestCase() {
            testableResources.removeOverride(R.bool.can_use_one_handed_bouncer)
        }

    @Test
    fun bouncerExpansion_lockscreenToBouncer() =
        kosmos.runTest {
            val bouncerExpansion by collectLastValue(underTest.bouncerExpansion)

            val progress = MutableStateFlow(0f)
            kosmos.sceneContainerRepository.setTransitionState(transitionState)
            transitionState.value =
                ObservableTransitionState.Transition.showOverlay(
                    overlay = Overlays.Bouncer,
                    fromScene = Scenes.Lockscreen,
                    currentOverlays = flowOf(emptySet()),
                    progress = progress,
                    isInitiatedByUserInput = false,
                    isUserInputOngoing = flowOf(false),
                )

            assertThat(bouncerExpansion).isEqualTo(0f)

            progress.value = 1f
            assertThat(bouncerExpansion).isEqualTo(1f)
        }

    @Test
    fun bouncerExpansion_BouncerToLockscreen() =
        kosmos.runTest {
            val bouncerExpansion by collectLastValue(underTest.bouncerExpansion)

            val progress = MutableStateFlow(0f)
            kosmos.sceneContainerRepository.setTransitionState(transitionState)
            transitionState.value =
                ObservableTransitionState.Transition.hideOverlay(
                    overlay = Overlays.Bouncer,
                    toScene = Scenes.Lockscreen,
                    currentOverlays = flowOf(emptySet()),
                    progress = progress,
                    isInitiatedByUserInput = false,
                    isUserInputOngoing = flowOf(false),
                )

            assertThat(bouncerExpansion).isEqualTo(1f)

            progress.value = 1f
            assertThat(bouncerExpansion).isEqualTo(0f)
        }

    @Test
    fun bouncerExpansion_shadeToLockscreenUnderBouncer() =
        kosmos.runTest {
            val bouncerExpansion by collectLastValue(underTest.bouncerExpansion)

            val progress = MutableStateFlow(0f)
            kosmos.sceneContainerRepository.setTransitionState(transitionState)
            transitionState.value =
                ObservableTransitionState.Transition(
                    fromScene = Scenes.Shade,
                    toScene = Scenes.Lockscreen,
                    currentScene = flowOf(Scenes.Lockscreen),
                    progress = progress,
                    isInitiatedByUserInput = false,
                    isUserInputOngoing = flowOf(false),
                    currentOverlays = setOf(Overlays.Bouncer),
                )

            assertThat(bouncerExpansion).isEqualTo(1f)

            progress.value = 1f
            assertThat(bouncerExpansion).isEqualTo(1f)
        }

    companion object {
        private const val MESSAGE_ENTER_YOUR_PIN = "Enter your PIN"
        private const val MESSAGE_ENTER_YOUR_PASSWORD = "Enter your password"
+33 −0
Original line number Diff line number Diff line
@@ -17,7 +17,9 @@
package com.android.systemui.bouncer.domain.interactor

import android.app.StatusBarManager.SESSION_KEYGUARD
import com.android.app.tracing.FlowTracing.traceAsCounter
import com.android.app.tracing.coroutines.asyncTraced as async
import com.android.compose.animation.scene.ObservableTransitionState
import com.android.compose.animation.scene.SceneKey
import com.android.internal.logging.UiEventLogger
import com.android.systemui.authentication.domain.interactor.AuthenticationInteractor
@@ -38,9 +40,12 @@ import com.android.systemui.deviceentry.domain.interactor.DeviceEntryFaceAuthInt
import com.android.systemui.log.SessionTracker
import com.android.systemui.power.domain.interactor.PowerInteractor
import com.android.systemui.scene.domain.interactor.SceneBackInteractor
import com.android.systemui.scene.domain.interactor.SceneInteractor
import com.android.systemui.scene.shared.flag.SceneContainerFlag
import com.android.systemui.scene.shared.model.Overlays
import com.android.systemui.scene.shared.model.Scenes
import com.android.systemui.shade.ShadeDisplayAware
import com.android.systemui.utils.coroutines.flow.flatMapLatestConflated
import javax.inject.Inject
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.flow.Flow
@@ -49,7 +54,9 @@ import kotlinx.coroutines.flow.SharedFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.asStateFlow
import kotlinx.coroutines.flow.combine
import kotlinx.coroutines.flow.distinctUntilChanged
import kotlinx.coroutines.flow.filter
import kotlinx.coroutines.flow.flowOf
import kotlinx.coroutines.flow.map

/** Encapsulates business logic and application state accessing use-cases. */
@@ -65,6 +72,7 @@ constructor(
    private val powerInteractor: PowerInteractor,
    private val uiEventLogger: UiEventLogger,
    private val sessionTracker: SessionTracker,
    sceneInteractor: SceneInteractor,
    sceneBackInteractor: SceneBackInteractor,
    @ShadeDisplayAware private val configurationInteractor: ConfigurationInteractor,
) {
@@ -149,6 +157,31 @@ constructor(
    val dismissDestination: Flow<SceneKey> =
        sceneBackInteractor.backScene.map { it ?: Scenes.Lockscreen }

    /** The amount [0-1] that the Bouncer Overlay has been transitioned to. */
    val bouncerExpansion: Flow<Float> =
        if (SceneContainerFlag.isEnabled) {
                sceneInteractor.transitionState.flatMapLatestConflated { state ->
                    when (state) {
                        is ObservableTransitionState.Idle ->
                            flowOf(if (Overlays.Bouncer in state.currentOverlays) 1f else 0f)
                        is ObservableTransitionState.Transition ->
                            if (state.toContent == Overlays.Bouncer) {
                                state.progress
                            } else if (state.fromContent == Overlays.Bouncer) {
                                state.progress.map { progress -> 1 - progress }
                            } else {
                                state.currentOverlays().map {
                                    if (Overlays.Bouncer in it) 1f else 0f
                                }
                            }
                    }
                }
            } else {
                flowOf()
            }
            .distinctUntilChanged()
            .traceAsCounter("bouncer_expansion") { (it * 100f).toInt() }

    /** Notifies that the user has places down a pointer, not necessarily dragging just yet. */
    fun onDown() {
        falsingInteractor.avoidGesture()
+1 −1
Original line number Diff line number Diff line
@@ -334,7 +334,7 @@ constructor(
                        } else if (state.fromContent == overlay) {
                            state.progress.map { progress -> 1 - progress }
                        } else {
                            flowOf(0f)
                            state.currentOverlays().map { if (overlay in it) 1f else 0f }
                        }
                }
            }
+8 −0
Original line number Diff line number Diff line
@@ -1225,6 +1225,14 @@ public class NotificationStackScrollLayout
        mController.setMaxAlphaFromView(alpha);
    }

    @Override
    public void setOccluded(boolean isOccluded) {
        if (SceneContainerFlag.isUnexpectedlyInLegacyMode()) {
            return;
        }
        this.setVisibility(isOccluded ? View.INVISIBLE : View.VISIBLE);
    }

    @Override
    public void setScrollState(@NonNull ShadeScrollState scrollState) {
        if (SceneContainerFlag.isUnexpectedlyInLegacyMode()) {
+3 −0
Original line number Diff line number Diff line
@@ -49,6 +49,9 @@ interface NotificationScrollView {
    /** Max alpha for this view */
    fun setMaxAlpha(alpha: Float)

    /** Set whether this view is occluded by something else. */
    fun setOccluded(isOccluded: Boolean)

    /** Sets a clipping shape, which defines the drawable area of this view. */
    fun setClippingShape(shape: ShadeScrimShape?)

Loading