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

Commit caf61553 authored by Sherry Zhou's avatar Sherry Zhou Committed by Android (Google) Code Review
Browse files

Merge "Update focal area bounds on large screen landscape" into main

parents b9d34127 3335973d
Loading
Loading
Loading
Loading
+4 −51
Original line number Diff line number Diff line
@@ -30,8 +30,6 @@ import com.android.systemui.kosmos.testScope
import com.android.systemui.res.R
import com.android.systemui.shade.data.repository.ShadeRepository
import com.android.systemui.shade.data.repository.shadeRepository
import com.android.systemui.statusbar.notification.data.repository.activeNotificationListRepository
import com.android.systemui.statusbar.notification.data.repository.setActiveNotifs
import com.android.systemui.statusbar.notification.domain.interactor.activeNotificationsInteractor
import com.android.systemui.testKosmos
import com.android.systemui.wallpapers.data.repository.fakeWallpaperFocalAreaRepository
@@ -110,7 +108,7 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
            )
            val bounds by collectLastValue(underTest.wallpaperFocalAreaBounds)
            kosmos.shadeRepository.setShadeLayoutWide(false)
            kosmos.activeNotificationListRepository.setActiveNotifs(0)

            kosmos.wallpaperFocalAreaRepository.setShortcutAbsoluteTop(1800F)
            kosmos.wallpaperFocalAreaRepository.setNotificationDefaultTop(400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationStackAbsoluteBottom(400F)
@@ -130,7 +128,6 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
            )
            val bounds by collectLastValue(underTest.wallpaperFocalAreaBounds)
            kosmos.shadeRepository.setShadeLayoutWide(false)
            kosmos.activeNotificationListRepository.setActiveNotifs(1)
            kosmos.wallpaperFocalAreaRepository.setShortcutAbsoluteTop(1800F)
            kosmos.wallpaperFocalAreaRepository.setNotificationDefaultTop(400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationStackAbsoluteBottom(600F)
@@ -139,27 +136,7 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
        }

    @Test
    fun focalAreaBounds_withNotifications_inUnfoldLandscape() =
        testScope.runTest {
            overrideMockedResources(
                OverrideResources(
                    screenWidth = 2000,
                    screenHeight = 1600,
                    centerAlignFocalArea = false,
                )
            )
            val bounds by collectLastValue(underTest.wallpaperFocalAreaBounds)
            kosmos.shadeRepository.setShadeLayoutWide(true)
            kosmos.activeNotificationListRepository.setActiveNotifs(1)
            kosmos.wallpaperFocalAreaRepository.setShortcutAbsoluteTop(1400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationDefaultTop(400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationStackAbsoluteBottom(600F)

            assertThat(bounds).isEqualTo(RectF(500f, 600F, 1000F, 1100F))
        }

    @Test
    fun focalAreaBounds_withoutNotifications_inUnfoldLandscape() =
    fun focalAreaBounds_inUnfoldLandscape() =
        testScope.runTest {
            overrideMockedResources(
                OverrideResources(
@@ -170,12 +147,11 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
            )
            val bounds by collectLastValue(underTest.wallpaperFocalAreaBounds)
            kosmos.shadeRepository.setShadeLayoutWide(true)
            kosmos.activeNotificationListRepository.setActiveNotifs(0)
            kosmos.wallpaperFocalAreaRepository.setShortcutAbsoluteTop(1400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationDefaultTop(400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationStackAbsoluteBottom(400F)

            assertThat(bounds).isEqualTo(RectF(1000f, 600F, 1500F, 1100F))
            assertThat(bounds).isEqualTo(RectF(600f, 600F, 1400F, 1100F))
        }

    @Test
@@ -190,7 +166,6 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
            )
            val bounds by collectLastValue(underTest.wallpaperFocalAreaBounds)
            kosmos.shadeRepository.setShadeLayoutWide(false)
            kosmos.activeNotificationListRepository.setActiveNotifs(1)
            kosmos.wallpaperFocalAreaRepository.setShortcutAbsoluteTop(1800F)
            kosmos.wallpaperFocalAreaRepository.setNotificationDefaultTop(400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationStackAbsoluteBottom(600F)
@@ -210,7 +185,6 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
            )
            val bounds by collectLastValue(underTest.wallpaperFocalAreaBounds)
            kosmos.shadeRepository.setShadeLayoutWide(false)
            kosmos.activeNotificationListRepository.setActiveNotifs(0)
            kosmos.wallpaperFocalAreaRepository.setShortcutAbsoluteTop(1800F)
            kosmos.wallpaperFocalAreaRepository.setNotificationDefaultTop(400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationStackAbsoluteBottom(600F)
@@ -219,7 +193,7 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
        }

    @Test
    fun focalAreaBounds_withNotifications_inTabletLandscape() =
    fun focalAreaBounds_inTabletLandscape() =
        testScope.runTest {
            overrideMockedResources(
                OverrideResources(
@@ -230,7 +204,6 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
            )
            val bounds by collectLastValue(underTest.wallpaperFocalAreaBounds)
            kosmos.shadeRepository.setShadeLayoutWide(true)
            kosmos.activeNotificationListRepository.setActiveNotifs(1)
            kosmos.wallpaperFocalAreaRepository.setShortcutAbsoluteTop(1800F)
            kosmos.wallpaperFocalAreaRepository.setNotificationDefaultTop(200F)
            kosmos.wallpaperFocalAreaRepository.setNotificationStackAbsoluteBottom(200F)
@@ -238,26 +211,6 @@ class WallpaperFocalAreaInteractorTest : SysuiTestCase() {
            assertThat(bounds).isEqualTo(RectF(1000f, 600F, 2000F, 1400F))
        }

    @Test
    fun focalAreaBounds_withoutNotifications_inTabletLandscape() =
        testScope.runTest {
            overrideMockedResources(
                OverrideResources(
                    screenWidth = 3000,
                    screenHeight = 2000,
                    centerAlignFocalArea = true,
                )
            )
            val bounds by collectLastValue(underTest.wallpaperFocalAreaBounds)
            kosmos.shadeRepository.setShadeLayoutWide(true)
            kosmos.activeNotificationListRepository.setActiveNotifs(0)
            kosmos.wallpaperFocalAreaRepository.setShortcutAbsoluteTop(1800F)
            kosmos.wallpaperFocalAreaRepository.setNotificationDefaultTop(400F)
            kosmos.wallpaperFocalAreaRepository.setNotificationStackAbsoluteBottom(400F)

            assertThat(bounds).isEqualTo(RectF(1000f, 600F, 2000F, 1400F))
        }

    @Test
    fun onTap_inFocalBounds() =
        testScope.runTest {
+18 −32
Original line number Diff line number Diff line
@@ -20,8 +20,8 @@ import android.content.Context
import android.content.res.Resources
import android.graphics.PointF
import android.graphics.RectF
import android.util.Log
import android.util.TypedValue
import androidx.annotation.VisibleForTesting
import com.android.app.animation.MathUtils
import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.dagger.qualifiers.Application
@@ -48,32 +48,16 @@ constructor(
    activeNotificationsInteractor: ActiveNotificationsInteractor,
    val wallpaperRepository: WallpaperRepository,
) {
    // When there's notifications in splitshade, the focal area should be left aligned
    @VisibleForTesting
    val notificationInShadeWideLayout: Flow<Boolean> =
        combine(
            shadeRepository.isShadeLayoutWide,
            activeNotificationsInteractor.areAnyNotificationsPresent,
        ) { isShadeLayoutWide, areAnyNotificationsPresent: Boolean ->
            when {
                !isShadeLayoutWide -> false
                !areAnyNotificationsPresent -> false
                else -> true
            }
        }

    val hasFocalArea = wallpaperRepository.shouldSendFocalArea

    val wallpaperFocalAreaBounds: Flow<RectF> =
        combine(
                shadeRepository.isShadeLayoutWide,
                notificationInShadeWideLayout,
                wallpaperFocalAreaRepository.notificationStackAbsoluteBottom,
                wallpaperFocalAreaRepository.shortcutAbsoluteTop,
                wallpaperFocalAreaRepository.notificationDefaultTop,
            ) {
                isShadeLayoutWide,
                notificationInShadeWideLayout,
                notificationStackAbsoluteBottom,
                shortcutAbsoluteTop,
                notificationDefaultTop ->
@@ -97,28 +81,21 @@ constructor(
                        screenBounds.centerY() + screenBounds.height() / 2F / wallpaperZoomedInScale,
                    )

                val focalAreaMaxWidthDp = getFocalAreaMaxWidthDp(context)
                val maxFocalAreaWidth =
                    TypedValue.applyDimension(
                        TypedValue.COMPLEX_UNIT_DIP,
                        FOCAL_AREA_MAX_WIDTH_DP.toFloat(),
                        focalAreaMaxWidthDp.toFloat(),
                        context.resources.displayMetrics,
                    )

                val (left, right) =
                // tablet landscape
                if (context.resources.getBoolean(R.bool.center_align_focal_area_shape)) {
                // Tablet & unfold foldable landscape
                if (isShadeLayoutWide) {
                        Pair(
                            scaledBounds.centerX() - maxFocalAreaWidth / 2F,
                            scaledBounds.centerX() + maxFocalAreaWidth / 2F,
                        )
                        // unfold foldable landscape
                    } else if (isShadeLayoutWide) {
                        if (notificationInShadeWideLayout) {
                            Pair(scaledBounds.left, scaledBounds.centerX())
                        } else {
                            Pair(scaledBounds.centerX(), scaledBounds.right)
                        }
                        // handheld / portrait
                    } else {
                        val focalAreaWidth = min(scaledBounds.width(), maxFocalAreaWidth)
                        Pair(
@@ -147,7 +124,7 @@ constructor(
                                wallpaperZoomedInScale
                    }
                val bottom = scaledBounds.bottom - scaledBottomMargin
                RectF(left, top, right, bottom)
                RectF(left, top, right, bottom).also { Log.d(TAG, "Focal area changes to $it") }
            }
            .distinctUntilChanged()

@@ -187,8 +164,17 @@ constructor(
            return if (scale == 0f) 1f else scale
        }

        // A max width for focal area shape effects bounds, to avoid
        // it becoming too large in large screen portrait mode
        const val FOCAL_AREA_MAX_WIDTH_DP = 500
        // A max width for focal area shape effects bounds, to avoid it becoming too large,
        // especially in portrait mode
        const val FOCAL_AREA_MAX_WIDTH_DP_TABLET = 500
        const val FOCAL_AREA_MAX_WIDTH_DP_FOLDABLE = 400

        fun getFocalAreaMaxWidthDp(context: Context): Int {
            return if (context.resources.getBoolean(R.bool.center_align_focal_area_shape))
                FOCAL_AREA_MAX_WIDTH_DP_TABLET
            else FOCAL_AREA_MAX_WIDTH_DP_FOLDABLE
        }

        private val TAG = WallpaperFocalAreaInteractor::class.simpleName
    }
}