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

Commit 867d604f authored by Ale Nijamkin's avatar Ale Nijamkin Committed by Android (Google) Code Review
Browse files

Merge changes I10c4cbc5,I1b4affba into main

* changes:
  [flexiglass] Adds horizontal spacing to status bar section.
  [flexiglass] Adds burn-in to smartspace section elements.
parents 37ad976c 0e2ae4ee
Loading
Loading
Loading
Loading
+6 −4
Original line number Diff line number Diff line
@@ -31,6 +31,7 @@ import androidx.compose.ui.viewinterop.AndroidView
import androidx.core.view.isVisible
import com.android.compose.animation.scene.SceneScope
import com.android.systemui.keyguard.qualifiers.KeyguardRootView
import com.android.systemui.keyguard.ui.viewmodel.KeyguardRootViewModel
import com.android.systemui.keyguard.ui.viewmodel.LockscreenSceneViewModel
import com.android.systemui.notifications.ui.composable.NotificationStack
import com.android.systemui.res.R
@@ -47,8 +48,9 @@ import javax.inject.Inject
class ViewBasedLockscreenContent
@Inject
constructor(
    private val viewModel: LockscreenSceneViewModel,
    private val lockscreenSceneViewModel: LockscreenSceneViewModel,
    @KeyguardRootView private val viewProvider: () -> @JvmSuppressWildcards View,
    private val keyguardRootViewModel: KeyguardRootViewModel,
) {
    @Composable
    fun SceneScope.Content(
@@ -59,7 +61,7 @@ constructor(
        }

        LockscreenLongPress(
            viewModel = viewModel.longPress,
            viewModel = lockscreenSceneViewModel.longPress,
            modifier = modifier,
        ) { onSettingsMenuPlaced ->
            AndroidView(
@@ -74,7 +76,7 @@ constructor(
            )

            val notificationStackPosition by
                viewModel.keyguardRoot.notificationBounds.collectAsState()
                keyguardRootViewModel.notificationBounds.collectAsState()

            Layout(
                modifier =
@@ -92,7 +94,7 @@ constructor(
                    },
                content = {
                    NotificationStack(
                        viewModel = viewModel.notifications,
                        viewModel = lockscreenSceneViewModel.notifications,
                        isScrimVisible = false,
                    )
                }
+94 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2023 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.ui.composable.blueprint

import androidx.compose.foundation.layout.WindowInsets
import androidx.compose.foundation.layout.displayCutout
import androidx.compose.foundation.layout.systemBars
import androidx.compose.foundation.layout.union
import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.ui.platform.LocalDensity
import com.android.systemui.keyguard.domain.interactor.KeyguardClockInteractor
import com.android.systemui.keyguard.ui.viewmodel.BurnInParameters
import com.android.systemui.plugins.clocks.ClockController
import kotlin.math.min
import kotlin.math.roundToInt

/** Produces a [BurnInState] that can be used to query the `LockscreenBurnInViewModel` flows. */
@Composable
fun rememberBurnIn(
    clockInteractor: KeyguardClockInteractor,
): BurnInState {
    val clock by clockInteractor.currentClock.collectAsState()

    val (smartspaceTop, onSmartspaceTopChanged) = remember { mutableStateOf<Float?>(null) }
    val (smallClockTop, onSmallClockTopChanged) = remember { mutableStateOf<Float?>(null) }

    val topmostTop =
        when {
            smartspaceTop != null && smallClockTop != null -> min(smartspaceTop, smallClockTop)
            smartspaceTop != null -> smartspaceTop
            smallClockTop != null -> smallClockTop
            else -> 0f
        }.roundToInt()

    val params = rememberBurnInParameters(clock, topmostTop)

    return remember(params, onSmartspaceTopChanged, onSmallClockTopChanged) {
        BurnInState(
            parameters = params,
            onSmartspaceTopChanged = onSmartspaceTopChanged,
            onSmallClockTopChanged = onSmallClockTopChanged,
        )
    }
}

@Composable
private fun rememberBurnInParameters(
    clock: ClockController?,
    topmostTop: Int,
): BurnInParameters {
    val density = LocalDensity.current
    val topInset = WindowInsets.systemBars.union(WindowInsets.displayCutout).getTop(density)

    return remember(clock, topInset, topmostTop) {
        BurnInParameters(
            clockControllerProvider = { clock },
            topInset = topInset,
            statusViewTop = topmostTop,
        )
    }
}

data class BurnInState(
    /** Parameters for use with the `LockscreenBurnInViewModel. */
    val parameters: BurnInParameters,
    /**
     * Callback to invoke when the top coordinate of the smartspace element is updated, pass `null`
     * when the element is not shown.
     */
    val onSmartspaceTopChanged: (Float?) -> Unit,
    /**
     * Callback to invoke when the top coordinate of the small clock element is updated, pass `null`
     * when the element is not shown.
     */
    val onSmallClockTopChanged: (Float?) -> Unit,
)
+16 −2
Original line number Diff line number Diff line
@@ -24,6 +24,7 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.layout.Layout
import androidx.compose.ui.unit.IntRect
import com.android.compose.animation.scene.SceneScope
import com.android.systemui.keyguard.domain.interactor.KeyguardClockInteractor
import com.android.systemui.keyguard.ui.composable.LockscreenLongPress
import com.android.systemui.keyguard.ui.composable.section.AmbientIndicationSection
import com.android.systemui.keyguard.ui.composable.section.BottomAreaSection
@@ -55,6 +56,7 @@ constructor(
    private val ambientIndicationSection: AmbientIndicationSection,
    private val bottomAreaSection: BottomAreaSection,
    private val settingsMenuSection: SettingsMenuSection,
    private val clockInteractor: KeyguardClockInteractor,
) : LockscreenSceneBlueprint {

    override val id: String = "default"
@@ -62,6 +64,7 @@ constructor(
    @Composable
    override fun SceneScope.Content(modifier: Modifier) {
        val isUdfpsVisible = viewModel.isUdfpsVisible
        val burnIn = rememberBurnIn(clockInteractor)

        LockscreenLongPress(
            viewModel = viewModel.longPress,
@@ -74,8 +77,19 @@ constructor(
                        modifier = Modifier.fillMaxWidth(),
                    ) {
                        with(statusBarSection) { StatusBar(modifier = Modifier.fillMaxWidth()) }
                        with(clockSection) { SmallClock(modifier = Modifier.fillMaxWidth()) }
                        with(smartSpaceSection) { SmartSpace(modifier = Modifier.fillMaxWidth()) }
                        with(clockSection) {
                            SmallClock(
                                onTopChanged = burnIn.onSmallClockTopChanged,
                                modifier = Modifier.fillMaxWidth(),
                            )
                        }
                        with(smartSpaceSection) {
                            SmartSpace(
                                burnInParams = burnIn.parameters,
                                onTopChanged = burnIn.onSmartspaceTopChanged,
                                modifier = Modifier.fillMaxWidth(),
                            )
                        }
                        with(clockSection) { LargeClock(modifier = Modifier.fillMaxWidth()) }
                        with(notificationSection) {
                            Notifications(modifier = Modifier.fillMaxWidth().weight(1f))
+16 −2
Original line number Diff line number Diff line
@@ -24,6 +24,7 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.layout.Layout
import androidx.compose.ui.unit.IntRect
import com.android.compose.animation.scene.SceneScope
import com.android.systemui.keyguard.domain.interactor.KeyguardClockInteractor
import com.android.systemui.keyguard.ui.composable.LockscreenLongPress
import com.android.systemui.keyguard.ui.composable.section.AmbientIndicationSection
import com.android.systemui.keyguard.ui.composable.section.BottomAreaSection
@@ -55,6 +56,7 @@ constructor(
    private val ambientIndicationSection: AmbientIndicationSection,
    private val bottomAreaSection: BottomAreaSection,
    private val settingsMenuSection: SettingsMenuSection,
    private val clockInteractor: KeyguardClockInteractor,
) : LockscreenSceneBlueprint {

    override val id: String = "shortcuts-besides-udfps"
@@ -62,6 +64,7 @@ constructor(
    @Composable
    override fun SceneScope.Content(modifier: Modifier) {
        val isUdfpsVisible = viewModel.isUdfpsVisible
        val burnIn = rememberBurnIn(clockInteractor)

        LockscreenLongPress(
            viewModel = viewModel.longPress,
@@ -74,8 +77,19 @@ constructor(
                        modifier = Modifier.fillMaxWidth(),
                    ) {
                        with(statusBarSection) { StatusBar(modifier = Modifier.fillMaxWidth()) }
                        with(clockSection) { SmallClock(modifier = Modifier.fillMaxWidth()) }
                        with(smartSpaceSection) { SmartSpace(modifier = Modifier.fillMaxWidth()) }
                        with(clockSection) {
                            SmallClock(
                                onTopChanged = burnIn.onSmallClockTopChanged,
                                modifier = Modifier.fillMaxWidth(),
                            )
                        }
                        with(smartSpaceSection) {
                            SmartSpace(
                                burnInParams = burnIn.parameters,
                                onTopChanged = burnIn.onSmartspaceTopChanged,
                                modifier = Modifier.fillMaxWidth(),
                            )
                        }
                        with(clockSection) { LargeClock(modifier = Modifier.fillMaxWidth()) }
                        with(notificationSection) {
                            Notifications(modifier = Modifier.fillMaxWidth().weight(1f))
+68 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2023 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.ui.composable.modifier

import androidx.compose.runtime.Composable
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.graphicsLayer
import androidx.compose.ui.layout.boundsInWindow
import androidx.compose.ui.layout.onPlaced
import com.android.systemui.keyguard.ui.viewmodel.AodBurnInViewModel
import com.android.systemui.keyguard.ui.viewmodel.BurnInParameters
import com.android.systemui.keyguard.ui.viewmodel.BurnInScaleViewModel

/**
 * Modifies the composable to account for anti-burn in translation, alpha, and scaling.
 *
 * Please override [isClock] as `true` if the composable is an element that's part of a clock.
 */
@Composable
fun Modifier.burnInAware(
    viewModel: AodBurnInViewModel,
    params: BurnInParameters,
    isClock: Boolean = false,
): Modifier {
    val translationX by viewModel.translationX(params).collectAsState(initial = 0f)
    val translationY by viewModel.translationY(params).collectAsState(initial = 0f)
    val alpha by viewModel.alpha.collectAsState(initial = 1f)
    val scaleViewModel by viewModel.scale(params).collectAsState(initial = BurnInScaleViewModel())

    return this.graphicsLayer {
        val scale =
            when {
                scaleViewModel.scaleClockOnly && isClock -> scaleViewModel.scale
                !scaleViewModel.scaleClockOnly -> scaleViewModel.scale
                else -> 1f
            }

        this.translationX = translationX
        this.translationY = translationY
        this.alpha = alpha
        this.scaleX = scale
        this.scaleY = scale
    }
}

/** Reports the "top" coordinate of the modified composable to the given [consumer]. */
@Composable
fun Modifier.onTopPlacementChanged(
    consumer: (Float) -> Unit,
): Modifier {
    return onPlaced { coordinates -> consumer(coordinates.boundsInWindow().top) }
}
Loading