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

Commit ec1aafc4 authored by amehfooz's avatar amehfooz
Browse files

[SB][ComposeIcons] Move legacy SystemStatusIcons

Breaks out the android view for legacy status icons
into a public composable and uses that in the
ShadeHeader.
The SystemStatusIconsLegacy composable will also
be used in the DesktopStatusBar.

Bug: 408001821
Test: manual
Flag: com.android.systemui.status_bar_system_status_icons_in_compose
Change-Id: I8a6b3e866e486dd8843c1459b58a9645c993f57c
parent 1c5515d2
Loading
Loading
Loading
Loading
+20 −58
Original line number Diff line number Diff line
@@ -56,7 +56,6 @@ import androidx.compose.ui.layout.positionInWindow
import androidx.compose.ui.platform.LocalContext
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.platform.LocalLayoutDirection
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.unit.Constraints
import androidx.compose.ui.unit.Dp
import androidx.compose.ui.unit.IntOffset
@@ -103,6 +102,7 @@ import com.android.systemui.statusbar.pipeline.mobile.ui.viewmodel.composeWrappe
import com.android.systemui.statusbar.policy.Clock
import com.android.systemui.statusbar.systemstatusicons.SystemStatusIconsInCompose
import com.android.systemui.statusbar.systemstatusicons.ui.compose.SystemStatusIcons
import com.android.systemui.statusbar.systemstatusicons.ui.compose.SystemStatusIconsLegacy
import com.android.systemui.util.composable.kairos.ActivatedKairosSpec
import kotlin.math.max
import kotlin.math.roundToInt
@@ -719,15 +719,6 @@ private fun ContentScope.StatusIcons(
    val inverseColor =
        Utils.getColorAttrDefaultColor(themedContext, android.R.attr.textColorPrimaryInverse)

    val carrierIconSlots =
        listOf(
            stringResource(id = com.android.internal.R.string.status_bar_mobile),
            stringResource(id = com.android.internal.R.string.status_bar_stacked_mobile),
        )
    val cameraSlot = stringResource(id = com.android.internal.R.string.status_bar_camera)
    val micSlot = stringResource(id = com.android.internal.R.string.status_bar_microphone)
    val locationSlot = stringResource(id = com.android.internal.R.string.status_bar_location)

    val statusIconContext = LocalStatusIconContext.current
    val iconContainer = statusIconContext.iconContainer(contentKey)
    val iconManager = statusIconContext.iconManager(contentKey)
@@ -743,56 +734,27 @@ private fun ContentScope.StatusIcons(
                    Color(primaryColor)
                },
        )
        return
    }

    AndroidView(
        factory = {
            iconManager.setTint(primaryColor, inverseColor)
            viewModel.statusBarIconController.addIconGroup(iconManager)

            iconContainer
        },
        onRelease = { viewModel.statusBarIconController.removeIconGroup(iconManager) },
        update = { iconContainer ->
            iconContainer.setQsExpansionTransitioning(
                layoutState.isTransitioningBetween(Scenes.Shade, Scenes.QuickSettings)
            )
            if (viewModel.isSingleCarrier || !useExpandedFormat) {
                iconContainer.removeIgnoredSlots(carrierIconSlots)
            } else {
                iconContainer.addIgnoredSlots(carrierIconSlots)
            }

            if (viewModel.isPrivacyChipEnabled) {
                if (viewModel.isMicCameraIndicationEnabled) {
                    iconContainer.addIgnoredSlot(cameraSlot)
                    iconContainer.addIgnoredSlot(micSlot)
    } else {
                    iconContainer.removeIgnoredSlot(cameraSlot)
                    iconContainer.removeIgnoredSlot(micSlot)
                }
                if (viewModel.isLocationIndicationEnabled) {
                    iconContainer.addIgnoredSlot(locationSlot)
                } else {
                    iconContainer.removeIgnoredSlot(locationSlot)
                }
            } else {
                iconContainer.removeIgnoredSlot(cameraSlot)
                iconContainer.removeIgnoredSlot(micSlot)
                iconContainer.removeIgnoredSlot(locationSlot)
            }

            // TODO(b/397223606): Get the actual spec for this.
            if (isHighlighted) {
                iconManager.setTint(inverseColor, primaryColor)
            } else {
                iconManager.setTint(primaryColor, inverseColor)
            }
        },
        val foregroundColor = if (isHighlighted) inverseColor else primaryColor
        val backgroundColor = if (isHighlighted) primaryColor else inverseColor
        val isTransitioning = layoutState.isTransitioningBetween(Scenes.Shade, Scenes.QuickSettings)

        SystemStatusIconsLegacy(
            iconContainer = iconContainer,
            iconManager = iconManager,
            statusBarIconController = viewModel.statusBarIconController,
            useExpandedFormat = useExpandedFormat,
            isTransitioning = isTransitioning,
            foregroundColor = foregroundColor,
            backgroundColor = backgroundColor,
            isSingleCarrier = viewModel.isSingleCarrier,
            isMicCameraIndicationEnabled = viewModel.isMicCameraIndicationEnabled,
            isPrivacyChipEnabled = viewModel.isPrivacyChipVisible,
            isLocationIndicationEnabled = viewModel.isLocationIndicationEnabled,
            modifier = modifier,
        )
    }
}

@Composable
private fun ContentScope.PrivacyChip(
+89 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2025 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.statusbar.systemstatusicons.ui.compose

import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.viewinterop.AndroidView
import com.android.systemui.statusbar.phone.StatusIconContainer
import com.android.systemui.statusbar.phone.ui.StatusBarIconController
import com.android.systemui.statusbar.phone.ui.TintedIconManager

@Composable
fun SystemStatusIconsLegacy(
    statusBarIconController: StatusBarIconController,
    iconContainer: StatusIconContainer,
    iconManager: TintedIconManager,
    useExpandedFormat: Boolean,
    isTransitioning: Boolean,
    foregroundColor: Int,
    backgroundColor: Int,
    isSingleCarrier: Boolean,
    isMicCameraIndicationEnabled: Boolean,
    isPrivacyChipEnabled: Boolean,
    isLocationIndicationEnabled: Boolean,
    modifier: Modifier = Modifier,
) {
    val carrierIconSlots =
        listOf(
            stringResource(id = com.android.internal.R.string.status_bar_mobile),
            stringResource(id = com.android.internal.R.string.status_bar_stacked_mobile),
        )
    val cameraSlot = stringResource(id = com.android.internal.R.string.status_bar_camera)
    val micSlot = stringResource(id = com.android.internal.R.string.status_bar_microphone)
    val locationSlot = stringResource(id = com.android.internal.R.string.status_bar_location)

    AndroidView(
        factory = {
            statusBarIconController.addIconGroup(iconManager)
            iconContainer
        },
        onRelease = { statusBarIconController.removeIconGroup(iconManager) },
        update = { container ->
            container.setQsExpansionTransitioning(isTransitioning)

            if (isSingleCarrier || !useExpandedFormat) {
                container.removeIgnoredSlots(carrierIconSlots)
            } else {
                container.addIgnoredSlots(carrierIconSlots)
            }

            if (isPrivacyChipEnabled) {
                if (isMicCameraIndicationEnabled) {
                    container.addIgnoredSlot(cameraSlot)
                    container.addIgnoredSlot(micSlot)
                } else {
                    container.removeIgnoredSlot(cameraSlot)
                    container.removeIgnoredSlot(micSlot)
                }
                if (isLocationIndicationEnabled) {
                    container.addIgnoredSlot(locationSlot)
                } else {
                    container.removeIgnoredSlot(locationSlot)
                }
            } else {
                container.removeIgnoredSlot(cameraSlot)
                container.removeIgnoredSlot(micSlot)
                container.removeIgnoredSlot(locationSlot)
            }

            iconManager.setTint(foregroundColor, backgroundColor)
        },
        modifier = modifier,
    )
}