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

Commit acfbe67e authored by Darrell Shi's avatar Darrell Shi
Browse files

Move CommunalLayoutLib to AOSP

For more about the library, see go/hm-24-layout.

Bug: 303317477
Fix: 303317477
Test: atest CommunalLayoutLibTests
Change-Id: I01e3813a6081a22208f64b2dbaec8dda66e58a93
parent f2a089d3
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -60,6 +60,7 @@ systemui_compose_java_defaults {
            // except for SystemUI-core.
            // Copied from compose/features/Android.bp.
            static_libs: [
                "CommunalLayoutLib",
                "PlatformComposeCore",

                "androidx.compose.runtime_runtime",
+35 −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 {
    default_applicable_licenses: ["frameworks_base_packages_SystemUI_license"],
}

android_library {
    name: "CommunalLayoutLib",
    srcs: [
        "src/**/*.kt",
    ],
    static_libs: [
        "androidx.arch.core_core-runtime",
        "androidx.compose.animation_animation-graphics",
        "androidx.compose.runtime_runtime",
        "androidx.compose.material3_material3",
        "jsr330",
        "kotlinx-coroutines-android",
        "kotlinx-coroutines-core",
    ],
    manifest: "AndroidManifest.xml",
    kotlincflags: ["-Xjvm-default=all"],
}
+18 −0
Original line number Diff line number Diff line
<?xml version="1.0" encoding="utf-8"?>

<!-- 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.
-->

<manifest package="com.android.systemui.communal.layout" />
+66 −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.communal.layout

import com.android.systemui.communal.layout.ui.compose.config.CommunalGridLayoutCard

/** Computes the arrangement of cards. */
class CommunalLayoutEngine {
    companion object {
        /**
         * Determines the size that each card should be rendered in, and distributes the cards into
         * columns.
         *
         * Returns a nested list where the outer list contains columns, and the inner list contains
         * cards in each column.
         *
         * Currently treats the first supported size as the size to be rendered in, ignoring other
         * supported sizes.
         */
        fun distributeCardsIntoColumns(
            cards: List<CommunalGridLayoutCard>,
        ): List<List<CommunalGridLayoutCardInfo>> {
            val result = ArrayList<ArrayList<CommunalGridLayoutCardInfo>>()

            var capacityOfLastColumn = 0
            for (card in cards) {
                val cardSize = card.supportedSizes.first()
                if (capacityOfLastColumn >= cardSize.value) {
                    // Card fits in last column
                    capacityOfLastColumn -= cardSize.value
                } else {
                    // Create a new column
                    result.add(arrayListOf())
                    capacityOfLastColumn = CommunalGridLayoutCard.Size.FULL.value - cardSize.value
                }

                result.last().add(CommunalGridLayoutCardInfo(card, cardSize))
            }

            return result
        }
    }

    /**
     * A data class that wraps around a [CommunalGridLayoutCard] and also contains the size that the
     * card should be rendered in.
     */
    data class CommunalGridLayoutCardInfo(
        val card: CommunalGridLayoutCard,
        val size: CommunalGridLayoutCard.Size,
    )
}
+64 −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.communal.layout.ui.compose

import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
import androidx.compose.foundation.layout.Row
import androidx.compose.foundation.layout.fillMaxSize
import androidx.compose.foundation.layout.height
import androidx.compose.foundation.layout.width
import androidx.compose.foundation.lazy.LazyRow
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import com.android.systemui.communal.layout.CommunalLayoutEngine
import com.android.systemui.communal.layout.ui.compose.config.CommunalGridLayoutCard
import com.android.systemui.communal.layout.ui.compose.config.CommunalGridLayoutConfig

/**
 * An arrangement of cards with a horizontal scroll, where each card is displayed in the right size
 * and follows a specific order based on its priority, ensuring a seamless layout without any gaps.
 */
@Composable
fun CommunalGridLayout(
    modifier: Modifier,
    layoutConfig: CommunalGridLayoutConfig,
    communalCards: List<CommunalGridLayoutCard>,
) {
    val columns = CommunalLayoutEngine.distributeCardsIntoColumns(communalCards)
    LazyRow(
        modifier = modifier.height(layoutConfig.gridHeight),
        horizontalArrangement = Arrangement.spacedBy(layoutConfig.gridGutter),
    ) {
        for (column in columns) {
            item {
                Column(
                    modifier = Modifier.width(layoutConfig.cardWidth),
                    verticalArrangement = Arrangement.spacedBy(layoutConfig.gridGutter),
                ) {
                    for (cardInfo in column) {
                        Row(
                            modifier = Modifier.height(layoutConfig.cardHeight(cardInfo.size)),
                        ) {
                            cardInfo.card.Content(Modifier.fillMaxSize())
                        }
                    }
                }
            }
        }
    }
}
Loading