Introduce communal tutorial content
This change allows the communal hub to show placeholder tutorial content
when user enters the hub for the first time.
Test: verified locally that tutorial content is shown
Bug: 303506432
Fix: 303506432
Change-Id: I8f4843c9a8588c8a1f4b0f1e590cc79449c2a839
diff --git a/packages/SystemUI/compose/facade/disabled/src/com/android/systemui/compose/ComposeFacade.kt b/packages/SystemUI/compose/facade/disabled/src/com/android/systemui/compose/ComposeFacade.kt
index 3d670b8..c6e429a 100644
--- a/packages/SystemUI/compose/facade/disabled/src/com/android/systemui/compose/ComposeFacade.kt
+++ b/packages/SystemUI/compose/facade/disabled/src/com/android/systemui/compose/ComposeFacade.kt
@@ -22,6 +22,7 @@
import android.view.WindowInsets
import androidx.activity.ComponentActivity
import androidx.lifecycle.LifecycleOwner
+import com.android.systemui.communal.ui.viewmodel.CommunalViewModel
import com.android.systemui.people.ui.viewmodel.PeopleViewModel
import com.android.systemui.qs.footer.ui.viewmodel.FooterActionsViewModel
import com.android.systemui.scene.shared.model.Scene
@@ -66,6 +67,7 @@
override fun createCommunalView(
context: Context,
+ viewModel: CommunalViewModel,
): View {
throwComposeUnavailableError()
}
diff --git a/packages/SystemUI/compose/facade/enabled/src/com/android/systemui/compose/ComposeFacade.kt b/packages/SystemUI/compose/facade/enabled/src/com/android/systemui/compose/ComposeFacade.kt
index 7b11ac7..1722685 100644
--- a/packages/SystemUI/compose/facade/enabled/src/com/android/systemui/compose/ComposeFacade.kt
+++ b/packages/SystemUI/compose/facade/enabled/src/com/android/systemui/compose/ComposeFacade.kt
@@ -31,6 +31,7 @@
import com.android.systemui.common.ui.compose.windowinsets.DisplayCutout
import com.android.systemui.common.ui.compose.windowinsets.DisplayCutoutProvider
import com.android.systemui.communal.ui.compose.CommunalHub
+import com.android.systemui.communal.ui.viewmodel.CommunalViewModel
import com.android.systemui.people.ui.compose.PeopleScreen
import com.android.systemui.people.ui.viewmodel.PeopleViewModel
import com.android.systemui.qs.footer.ui.compose.FooterActions
@@ -96,8 +97,11 @@
override fun createCommunalView(
context: Context,
+ viewModel: CommunalViewModel,
): View {
- return ComposeView(context).apply { setContent { PlatformTheme { CommunalHub() } } }
+ return ComposeView(context).apply {
+ setContent { PlatformTheme { CommunalHub(viewModel = viewModel) } }
+ }
}
// TODO(b/298525212): remove once Compose exposes window inset bounds.
diff --git a/packages/SystemUI/compose/features/Android.bp b/packages/SystemUI/compose/features/Android.bp
index 796abf4b..16c2437 100644
--- a/packages/SystemUI/compose/features/Android.bp
+++ b/packages/SystemUI/compose/features/Android.bp
@@ -31,6 +31,7 @@
],
static_libs: [
+ "CommunalLayoutLib",
"SystemUI-core",
"PlatformComposeCore",
"PlatformComposeSceneTransitionLayout",
diff --git a/packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/CommunalHub.kt b/packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/CommunalHub.kt
index 4d2978d..3d827fb 100644
--- a/packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/CommunalHub.kt
+++ b/packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/CommunalHub.kt
@@ -3,20 +3,63 @@
import androidx.compose.foundation.background
import androidx.compose.foundation.layout.Box
import androidx.compose.foundation.layout.fillMaxSize
-import androidx.compose.material3.Text
+import androidx.compose.material3.Card
import androidx.compose.runtime.Composable
+import androidx.compose.runtime.collectAsState
+import androidx.compose.runtime.getValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.graphics.Color
+import androidx.compose.ui.res.dimensionResource
+import androidx.compose.ui.res.integerResource
+import com.android.systemui.communal.layout.ui.compose.CommunalGridLayout
+import com.android.systemui.communal.layout.ui.compose.config.CommunalGridLayoutCard
+import com.android.systemui.communal.layout.ui.compose.config.CommunalGridLayoutConfig
+import com.android.systemui.communal.ui.viewmodel.CommunalViewModel
+import com.android.systemui.res.R
@Composable
-fun CommunalHub(modifier: Modifier = Modifier) {
+fun CommunalHub(
+ modifier: Modifier = Modifier,
+ viewModel: CommunalViewModel,
+) {
+ val showTutorial by viewModel.showTutorialContent.collectAsState(initial = false)
Box(
modifier = modifier.fillMaxSize().background(Color.White),
) {
- Text(
- modifier = Modifier.align(Alignment.Center),
- text = "Hello Communal!",
+ CommunalGridLayout(
+ modifier = Modifier.align(Alignment.CenterStart),
+ layoutConfig =
+ CommunalGridLayoutConfig(
+ gridColumnSize = dimensionResource(R.dimen.communal_grid_column_size),
+ gridGutter = dimensionResource(R.dimen.communal_grid_gutter_size),
+ gridHeight = dimensionResource(R.dimen.communal_grid_height),
+ gridColumnsPerCard = integerResource(R.integer.communal_grid_columns_per_card),
+ ),
+ communalCards = if (showTutorial) tutorialContent else emptyList(),
)
}
}
+
+private val tutorialContent =
+ listOf(
+ tutorialCard(CommunalGridLayoutCard.Size.FULL),
+ tutorialCard(CommunalGridLayoutCard.Size.THIRD),
+ tutorialCard(CommunalGridLayoutCard.Size.THIRD),
+ tutorialCard(CommunalGridLayoutCard.Size.THIRD),
+ tutorialCard(CommunalGridLayoutCard.Size.HALF),
+ tutorialCard(CommunalGridLayoutCard.Size.HALF),
+ tutorialCard(CommunalGridLayoutCard.Size.HALF),
+ tutorialCard(CommunalGridLayoutCard.Size.HALF),
+ )
+
+private fun tutorialCard(size: CommunalGridLayoutCard.Size): CommunalGridLayoutCard {
+ return object : CommunalGridLayoutCard() {
+ override val supportedSizes = listOf(size)
+
+ @Composable
+ override fun Content(modifier: Modifier) {
+ Card(modifier = modifier, content = {})
+ }
+ }
+}
diff --git a/packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/CommunalScene.kt b/packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/CommunalScene.kt
index d1c12ac..f3bef7b 100644
--- a/packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/CommunalScene.kt
+++ b/packages/SystemUI/compose/features/src/com/android/systemui/communal/ui/compose/CommunalScene.kt
@@ -19,6 +19,7 @@
import androidx.compose.runtime.Composable
import androidx.compose.ui.Modifier
import com.android.compose.animation.scene.SceneScope
+import com.android.systemui.communal.ui.viewmodel.CommunalViewModel
import com.android.systemui.dagger.SysUISingleton
import com.android.systemui.scene.shared.model.Direction
import com.android.systemui.scene.shared.model.SceneKey
@@ -32,7 +33,11 @@
/** The communal scene shows glanceable hub when the device is locked and docked. */
@SysUISingleton
-class CommunalScene @Inject constructor() : ComposableScene {
+class CommunalScene
+@Inject
+constructor(
+ private val viewModel: CommunalViewModel,
+) : ComposableScene {
override val key = SceneKey.Communal
override val destinationScenes: StateFlow<Map<UserAction, SceneModel>> =
@@ -45,6 +50,6 @@
@Composable
override fun SceneScope.Content(modifier: Modifier) {
- CommunalHub(modifier)
+ CommunalHub(modifier, viewModel)
}
}
diff --git a/packages/SystemUI/res/values/dimens.xml b/packages/SystemUI/res/values/dimens.xml
index 6377df3..4be648d 100644
--- a/packages/SystemUI/res/values/dimens.xml
+++ b/packages/SystemUI/res/values/dimens.xml
@@ -1661,6 +1661,15 @@
<!-- Height percentage of the parent container occupied by the communal view -->
<item name="communal_source_height_percentage" format="float" type="dimen">0.80</item>
+ <!-- Size of each communal grid column -->
+ <dimen name="communal_grid_column_size">64dp</dimen>
+ <!-- Size of each communal grid gutter between columns -->
+ <dimen name="communal_grid_gutter_size">16dp</dimen>
+ <!-- Height of the communal grid layout -->
+ <dimen name="communal_grid_height">630dp</dimen>
+ <!-- Number of columns for each communal card -->
+ <integer name="communal_grid_columns_per_card">6</integer>
+
<dimen name="drag_and_drop_icon_size">70dp</dimen>
<dimen name="qs_tile_service_request_dialog_width">304dp</dimen>
diff --git a/packages/SystemUI/src/com/android/systemui/communal/dagger/CommunalModule.kt b/packages/SystemUI/src/com/android/systemui/communal/dagger/CommunalModule.kt
new file mode 100644
index 0000000..b8e2de4
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/communal/dagger/CommunalModule.kt
@@ -0,0 +1,32 @@
+/*
+ * 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.dagger
+
+import com.android.systemui.communal.data.repository.CommunalRepositoryModule
+import com.android.systemui.communal.data.repository.CommunalTutorialRepositoryModule
+import com.android.systemui.communal.data.repository.CommunalWidgetRepositoryModule
+import dagger.Module
+
+@Module(
+ includes =
+ [
+ CommunalRepositoryModule::class,
+ CommunalTutorialRepositoryModule::class,
+ CommunalWidgetRepositoryModule::class,
+ ]
+)
+class CommunalModule
diff --git a/packages/SystemUI/src/com/android/systemui/communal/ui/view/layout/sections/DefaultCommunalHubSection.kt b/packages/SystemUI/src/com/android/systemui/communal/ui/view/layout/sections/DefaultCommunalHubSection.kt
index 932dbfb..ad02f62 100644
--- a/packages/SystemUI/src/com/android/systemui/communal/ui/view/layout/sections/DefaultCommunalHubSection.kt
+++ b/packages/SystemUI/src/com/android/systemui/communal/ui/view/layout/sections/DefaultCommunalHubSection.kt
@@ -2,6 +2,7 @@
import androidx.constraintlayout.widget.ConstraintLayout
import androidx.constraintlayout.widget.ConstraintSet
+import com.android.systemui.communal.ui.viewmodel.CommunalViewModel
import com.android.systemui.compose.ComposeFacade
import com.android.systemui.keyguard.shared.model.KeyguardSection
import com.android.systemui.keyguard.ui.view.layout.sections.removeView
@@ -9,14 +10,20 @@
import javax.inject.Inject
/** A keyguard section that hosts the communal hub. */
-class DefaultCommunalHubSection @Inject constructor() : KeyguardSection() {
+class DefaultCommunalHubSection
+@Inject
+constructor(
+ private val viewModel: CommunalViewModel,
+) : KeyguardSection() {
private val communalHubViewId = R.id.communal_hub
override fun addViews(constraintLayout: ConstraintLayout) {
constraintLayout.addView(
- ComposeFacade.createCommunalView(constraintLayout.context).apply {
- id = communalHubViewId
- },
+ ComposeFacade.createCommunalView(
+ context = constraintLayout.context,
+ viewModel = viewModel,
+ )
+ .apply { id = communalHubViewId },
)
}
diff --git a/packages/SystemUI/src/com/android/systemui/communal/ui/viewmodel/CommunalViewModel.kt b/packages/SystemUI/src/com/android/systemui/communal/ui/viewmodel/CommunalViewModel.kt
new file mode 100644
index 0000000..ddeb1d6
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/communal/ui/viewmodel/CommunalViewModel.kt
@@ -0,0 +1,32 @@
+/*
+ * 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.ui.viewmodel
+
+import com.android.systemui.communal.domain.interactor.CommunalTutorialInteractor
+import com.android.systemui.dagger.SysUISingleton
+import javax.inject.Inject
+import kotlinx.coroutines.flow.Flow
+
+@SysUISingleton
+class CommunalViewModel
+@Inject
+constructor(
+ tutorialInteractor: CommunalTutorialInteractor,
+) {
+ /** Whether communal hub should show tutorial content. */
+ val showTutorialContent: Flow<Boolean> = tutorialInteractor.isTutorialAvailable
+}
diff --git a/packages/SystemUI/src/com/android/systemui/compose/BaseComposeFacade.kt b/packages/SystemUI/src/com/android/systemui/compose/BaseComposeFacade.kt
index 5c1539a..9221832b 100644
--- a/packages/SystemUI/src/com/android/systemui/compose/BaseComposeFacade.kt
+++ b/packages/SystemUI/src/com/android/systemui/compose/BaseComposeFacade.kt
@@ -22,6 +22,7 @@
import android.view.WindowInsets
import androidx.activity.ComponentActivity
import androidx.lifecycle.LifecycleOwner
+import com.android.systemui.communal.ui.viewmodel.CommunalViewModel
import com.android.systemui.people.ui.viewmodel.PeopleViewModel
import com.android.systemui.qs.footer.ui.viewmodel.FooterActionsViewModel
import com.android.systemui.scene.shared.model.Scene
@@ -73,8 +74,9 @@
sceneByKey: Map<SceneKey, Scene>,
): View
- /** Create a [View] that represents the communal hub. */
+ /** Create a [View] to represent [viewModel] on screen. */
fun createCommunalView(
context: Context,
+ viewModel: CommunalViewModel,
): View
}
diff --git a/packages/SystemUI/src/com/android/systemui/dagger/SystemUIModule.java b/packages/SystemUI/src/com/android/systemui/dagger/SystemUIModule.java
index 7d4e1a1..f0d7592 100644
--- a/packages/SystemUI/src/com/android/systemui/dagger/SystemUIModule.java
+++ b/packages/SystemUI/src/com/android/systemui/dagger/SystemUIModule.java
@@ -42,6 +42,7 @@
import com.android.systemui.classifier.FalsingModule;
import com.android.systemui.clipboardoverlay.dagger.ClipboardOverlayModule;
import com.android.systemui.common.ui.data.repository.CommonRepositoryModule;
+import com.android.systemui.communal.dagger.CommunalModule;
import com.android.systemui.complication.dagger.ComplicationComponent;
import com.android.systemui.controls.dagger.ControlsModule;
import com.android.systemui.dagger.qualifiers.Main;
@@ -170,6 +171,7 @@
ClipboardOverlayModule.class,
ClockRegistryModule.class,
CommonRepositoryModule.class,
+ CommunalModule.class,
ConnectivityModule.class,
ControlsModule.class,
CoroutinesModule.class,
diff --git a/packages/SystemUI/src/com/android/systemui/keyguard/dagger/KeyguardModule.java b/packages/SystemUI/src/com/android/systemui/keyguard/dagger/KeyguardModule.java
index 081edd1..019d428 100644
--- a/packages/SystemUI/src/com/android/systemui/keyguard/dagger/KeyguardModule.java
+++ b/packages/SystemUI/src/com/android/systemui/keyguard/dagger/KeyguardModule.java
@@ -38,9 +38,6 @@
import com.android.systemui.broadcast.BroadcastDispatcher;
import com.android.systemui.classifier.FalsingCollector;
import com.android.systemui.classifier.FalsingModule;
-import com.android.systemui.communal.data.repository.CommunalRepositoryModule;
-import com.android.systemui.communal.data.repository.CommunalTutorialRepositoryModule;
-import com.android.systemui.communal.data.repository.CommunalWidgetRepositoryModule;
import com.android.systemui.dagger.SysUISingleton;
import com.android.systemui.dagger.qualifiers.Main;
import com.android.systemui.dagger.qualifiers.UiBackground;
@@ -96,9 +93,6 @@
KeyguardStatusViewComponent.class,
KeyguardUserSwitcherComponent.class},
includes = {
- CommunalRepositoryModule.class,
- CommunalTutorialRepositoryModule.class,
- CommunalWidgetRepositoryModule.class,
FalsingModule.class,
KeyguardDataQuickAffordanceModule.class,
KeyguardRepositoryModule.class,