@@ -30,46 +30,49 @@ import androidx.compose.ui.graphics.graphicsLayer
3030import androidx.compose.ui.res.painterResource
3131import androidx.compose.ui.res.stringResource
3232import androidx.compose.ui.text.style.TextAlign
33+ import androidx.navigation3.runtime.NavKey
34+ import androidx.navigation3.runtime.entryProvider
35+ import androidx.navigation3.runtime.rememberNavBackStack
36+ import androidx.navigation3.ui.NavDisplay
3337import androidx.wear.compose.foundation.lazy.TransformingLazyColumn
3438import androidx.wear.compose.foundation.lazy.rememberTransformingLazyColumnState
3539import androidx.wear.compose.material3.AlertDialog
3640import androidx.wear.compose.material3.AlertDialogDefaults
3741import androidx.wear.compose.material3.AppScaffold
3842import androidx.wear.compose.material3.Button
43+ import androidx.wear.compose.material3.ButtonDefaults
3944import androidx.wear.compose.material3.ButtonGroup
4045import androidx.wear.compose.material3.EdgeButton
4146import androidx.wear.compose.material3.EdgeButtonSize
4247import androidx.wear.compose.material3.FilledIconButton
4348import androidx.wear.compose.material3.Icon
4449import androidx.wear.compose.material3.IconButtonDefaults
4550import androidx.wear.compose.material3.ListHeader
51+ import androidx.wear.compose.material3.ListHeaderDefaults
4652import androidx.wear.compose.material3.MaterialTheme
4753import androidx.wear.compose.material3.ScreenScaffold
4854import androidx.wear.compose.material3.SurfaceTransformation
4955import androidx.wear.compose.material3.Text
5056import androidx.wear.compose.material3.TitleCard
5157import androidx.wear.compose.material3.lazy.rememberTransformationSpec
5258import androidx.wear.compose.material3.lazy.transformedHeight
53- import androidx.wear.compose.navigation.SwipeDismissableNavHost
54- import androidx.wear.compose.navigation.composable
55- import androidx.wear.compose.navigation.rememberSwipeDismissableNavController
59+ import androidx.wear.compose.navigation3.rememberSwipeDismissableSceneStrategy
5660import androidx.wear.compose.ui.tooling.preview.WearPreviewDevices
5761import androidx.wear.compose.ui.tooling.preview.WearPreviewFontScales
5862import com.example.android.wearable.composestarter.R
5963import com.example.android.wearable.composestarter.presentation.theme.AppCardDefaults
6064import com.example.android.wearable.composestarter.presentation.theme.WearAppTheme
61- import com.google.android.horologist.compose.layout.ColumnItemType
62- import com.google.android.horologist.compose.layout.rememberResponsiveColumnPadding
65+ import kotlinx.serialization.Serializable
6366
6467/* *
6568 * Simple "Hello, World" app meant as a starting point for a new project using Compose for Wear OS.
6669 *
6770 * Displays a centered [Text] composable and a list built with [TransformingLazyColumn].
6871 *
6972 * Use the Wear version of Compose Navigation. You can carry
70- * over your knowledge from mobile and it supports the swipe-to-dismiss gesture (Wear OS's
73+ * over your knowledge from mobile, and it supports the swipe-to-dismiss gesture (Wear OS's
7174 * back action). For more information, go here:
72- * https://developer.android.com/reference/kotlin/androidx/wear/compose/navigation /package-summary
75+ * https://developer.android.com/reference/kotlin/androidx/wear/compose/navigation3 /package-summary
7376 */
7477class MainActivity : ComponentActivity () {
7578 override fun onCreate (savedInstanceState : Bundle ? ) {
@@ -81,23 +84,43 @@ class MainActivity : ComponentActivity() {
8184 }
8285}
8386
87+ @Serializable
88+ sealed interface AppKey : NavKey
89+
90+ @Serializable
91+ data object MenuScreen : AppKey
92+
93+ @Serializable
94+ data object ListNavScreen : AppKey
95+
8496@Composable
8597fun WearApp () {
86- val navController = rememberSwipeDismissableNavController( )
98+ val backStack = rememberNavBackStack( MenuScreen )
8799
88100 WearAppTheme {
89101 AppScaffold {
90- SwipeDismissableNavHost (navController = navController, startDestination = " menu" ) {
91- composable(" menu" ) {
92- GreetingScreen (
93- " Android" ,
94- onShowList = { navController.navigate(" list" ) }
95- )
96- }
97- composable(" list" ) {
98- ListScreen ()
102+ val entryProvider =
103+ remember {
104+ entryProvider<NavKey > {
105+ entry<MenuScreen > {
106+ GreetingScreen (
107+ " Android" ,
108+ onShowList = { backStack.add(ListNavScreen ) }
109+ )
110+ }
111+ entry<ListNavScreen > {
112+ ListScreen ()
113+ }
114+ }
99115 }
100- }
116+
117+ val swipeDismissableSceneStrategy = rememberSwipeDismissableSceneStrategy<NavKey >()
118+
119+ NavDisplay (
120+ backStack = backStack,
121+ entryProvider = entryProvider,
122+ sceneStrategies = listOf (swipeDismissableSceneStrategy)
123+ )
101124 }
102125 }
103126}
@@ -123,49 +146,41 @@ fun GreetingScreen(
123146 ) {
124147 Text (stringResource(R .string.show_list))
125148 }
126- },
127- // The bottom padding value is always ignored when using EdgeButton because this button is
128- // always placed at the end of the screen.
129- // The `ScreenScaffold` parameter `edgeButtonSpacing` can be used to specify the
130- // gap between edgeButton and content.
131- contentPadding =
132- rememberResponsiveColumnPadding(
133- first = ColumnItemType .ListHeader
134- )
149+ // The `ScreenScaffold` parameter `edgeButtonSpacing` can be used to specify the
150+ // gap between edgeButton and content.
151+ }
135152 ) { contentPadding ->
136- // Use workaround from Horologist for padding or wait until fix lands
137153 TransformingLazyColumn (
138154 state = scrollState,
139155 contentPadding = contentPadding
140156 ) {
141- item { Greeting (greetingName = greetingName, modifier = modifier.fillMaxSize()) }
157+ item {
158+ Greeting (
159+ greetingName = greetingName,
160+ modifier =
161+ modifier
162+ .fillMaxSize()
163+ .minimumVerticalContentPadding(
164+ ListHeaderDefaults .minimumTopListContentPadding
165+ )
166+ )
167+ }
142168 }
143169 }
144170}
145171
146172@Composable
147173fun ListScreen (modifier : Modifier = Modifier ) {
148174 var showDialog by remember { mutableStateOf(false ) }
149-
150- /*
151- * Specifying the types of items that appear at the start and end of the list ensures that the
152- * appropriate padding is used.
153- */
154175 val listState = rememberTransformingLazyColumnState()
155176 val transformationSpec = rememberTransformationSpec()
156177
157178 ScreenScaffold (
158- scrollState = listState,
179+ scrollState = listState
159180 /*
160181 * TransformingLazyColumn takes care of the horizontal and vertical
161182 * padding for the list and handles scrolling.
162- * Use workaround from Horologist for padding or wait until fix lands
163183 */
164- contentPadding =
165- rememberResponsiveColumnPadding(
166- first = ColumnItemType .ListHeader ,
167- last = ColumnItemType .IconButton
168- )
169184 ) { contentPadding ->
170185 TransformingLazyColumn (
171186 state = listState,
@@ -176,7 +191,10 @@ fun ListScreen(modifier: Modifier = Modifier) {
176191 modifier =
177192 Modifier
178193 .fillMaxWidth()
179- .transformedHeight(this , transformationSpec),
194+ .transformedHeight(this , transformationSpec)
195+ .minimumVerticalContentPadding(
196+ ListHeaderDefaults .minimumTopListContentPadding
197+ ),
180198 transformation = SurfaceTransformation (transformationSpec)
181199 ) { Text (text = " Header" ) }
182200 }
@@ -223,6 +241,9 @@ fun ListScreen(modifier: Modifier = Modifier) {
223241 applyContainerTransformation(scrollProgress)
224242 }
225243 }.transformedHeight(this , transformationSpec)
244+ .minimumVerticalContentPadding(
245+ ButtonDefaults .minimumVerticalListContentPadding
246+ )
226247 ) {
227248 FilledIconButton (
228249 onClick = { showDialog = true },
0 commit comments