ย้ายข้อมูล CoordinatorLayout ไปยังเขียน

CoordinatorLayout คือ ViewGroup ที่ช่วยให้สร้างเลย์เอาต์ที่ซับซ้อน ซ้อนทับ และ ซ้อนกันได้ โดยใช้เป็นคอนเทนเนอร์เพื่อเปิดใช้การโต้ตอบ Material Design ที่เฉพาะเจาะจง เช่น การขยาย/ยุบแถบเครื่องมือและชีตด้านล่าง สำหรับ View ที่อยู่ในนั้น

ในฟีเจอร์เขียน อีเมลที่เทียบเท่ากับ CoordinatorLayout มากที่สุดคือ Scaffold Scaffoldมีช่องเนื้อหาสำหรับรวม Material Components เข้ากับรูปแบบหน้าจอและการโต้ตอบทั่วไป หน้านี้จะอธิบายวิธี ย้ายข้อมูลการติดตั้งใช้งาน CoordinatorLayout เพื่อใช้ Scaffold ใน Compose

ขั้นตอนการย้ายข้อมูล

หากต้องการย้ายข้อมูล CoordinatorLayout ไปยัง Scaffold ให้ทำตามขั้นตอนต่อไปนี้

  1. ในข้อมูลโค้ดด้านล่าง CoordinatorLayout มี AppBarLayout สำหรับ มี ToolBar, ViewPager และ FloatingActionButton แสดงความคิดเห็น เกี่ยวกับ CoordinatorLayout และองค์ประกอบย่อยจากลำดับชั้น UI แล้วเพิ่ม ComposeView เพื่อแทนที่

    <!--  <androidx.coordinatorlayout.widget.CoordinatorLayout-->
    <!--      android:id="@+id/coordinator_layout"-->
    <!--      android:layout_width="match_parent"-->
    <!--      android:layout_height="match_parent"-->
    <!--      android:fitsSystemWindows="true">-->
    
    <!--    <androidx.compose.ui.platform.ComposeView-->
    <!--        android:id="@+id/compose_view"-->
    <!--        android:layout_width="match_parent"-->
    <!--        android:layout_height="match_parent"-->
    <!--        app:layout_behavior="@string/appbar_scrolling_view_behavior" />-->
    
    <!--    <com.google.android.material.appbar.AppBarLayout-->
    <!--        android:id="@+id/app_bar_layout"-->
    <!--        android:layout_width="match_parent"-->
    <!--        android:layout_height="wrap_content"-->
    <!--        android:fitsSystemWindows="true"-->
    <!--        android:theme="@style/Theme.Sunflower.AppBarOverlay">-->
    
        <!-- AppBarLayout contents here -->
    
    <!--    </com.google.android.material.appbar.AppBarLayout>-->
    
    <!--  </androidx.coordinatorlayout.widget.CoordinatorLayout>-->
    
    <androidx.compose.ui.platform.ComposeView
        android:id="@+id/compose_view"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />
    
  2. ใน Fragment หรือ Activity ให้รับการอ้างอิงถึง ComposeView ที่คุณเพิ่งเพิ่ม และเรียกใช้เมธอด setContent ในออบเจ็กต์นั้น ในส่วนเนื้อหาของเมธอด ให้ตั้งค่า Scaffold เป็นเนื้อหาของเมธอด

    composeView.setContent {
        Scaffold(Modifier.fillMaxSize()) { contentPadding ->
            // Scaffold contents
            // ...
        }
    }

  3. ในเนื้อหาของ Scaffold ให้เพิ่มเนื้อหาหลักของหน้าจอภายใน เนื่องจากเนื้อหาหลักใน XML ด้านบนคือ ViewPager2 เราจึงจะใช้ HorizontalPager ซึ่งเป็นฟังก์ชัน Compose ที่เทียบเท่ากับเนื้อหาดังกล่าว content Lambda ของ Scaffold จะได้รับอินสแตนซ์ของ PaddingValues ซึ่งควร ใช้กับรูทเนื้อหาด้วย คุณสามารถใช้ Modifier.padding เพื่อใช้PaddingValues เดียวกันกับHorizontalPager ได้

    composeView.setContent {
        Scaffold(Modifier.fillMaxSize()) { contentPadding ->
            val pagerState = rememberPagerState {
                10
            }
            HorizontalPager(
                state = pagerState,
                modifier = Modifier.padding(contentPadding)
            ) { /* Page contents */ }
        }
    }

  4. ใช้ช่องเนื้อหาอื่นๆ ที่ Scaffold มีให้เพื่อเพิ่มองค์ประกอบบนหน้าจอ และย้ายข้อมูล View ย่อยที่เหลือ คุณใช้ช่อง topBar เพื่อเพิ่มTopAppBar และใช้ช่อง floatingActionButton เพื่อระบุFloatingActionButton ได้

    composeView.setContent {
        Scaffold(
            Modifier.fillMaxSize(),
            topBar = {
                TopAppBar(
                    title = {
                        Text("My App")
                    }
                )
            },
            floatingActionButton = {
                FloatingActionButton(
                    onClick = { /* Handle click */ }
                ) {
                    Icon(
                        Icons.Filled.Add,
                        contentDescription = "Add Button"
                    )
                }
            }
        ) { contentPadding ->
            val pagerState = rememberPagerState {
                10
            }
            HorizontalPager(
                state = pagerState,
                modifier = Modifier.padding(contentPadding)
            ) { /* Page contents */ }
        }
    }

กรณีการใช้งานทั่วไป

ยุบและขยายแถบเครื่องมือ

ในระบบมุมมอง เพื่อยุบและขยายแถบเครื่องมือด้วย CoordinatorLayout, คุณจะใช้ AppBarLayout เป็นคอนเทนเนอร์สำหรับแถบเครื่องมือ จากนั้นคุณสามารถระบุ Behavior ผ่าน layout_behavior ใน XML บน View ที่เลื่อนได้ที่เชื่อมโยง (เช่น RecyclerView หรือ NestedScrollView) เพื่อประกาศวิธีที่แถบเครื่องมือ ยุบ/ขยายเมื่อคุณเลื่อน

ใน Compose คุณสามารถสร้างเอฟเฟกต์ที่คล้ายกันได้ผ่าน TopAppBarScrollBehavior เช่น หากต้องการใช้แถบเครื่องมือที่ยุบ/ขยายได้เพื่อให้แถบเครื่องมือปรากฏเมื่อคุณเลื่อนขึ้น ให้ทำตามขั้นตอนต่อไปนี้

  1. โทรหา TopAppBarDefaults.enterAlwaysScrollBehavior() เพื่อสร้าง TopAppBarScrollBehavior
  2. ส่ง TopAppBarScrollBehavior ที่สร้างขึ้นให้ TopAppBar
  3. เชื่อมต่อ NestedScrollConnection ผ่าน Modifier.nestedScroll ใน Scaffold เพื่อให้ Scaffold รับเหตุการณ์การเลื่อนที่ซ้อนกันได้เมื่อเนื้อหาที่เลื่อนได้เลื่อนขึ้น/ลง ด้วยวิธีนี้ แถบแอปที่อยู่ในคอนเทนเนอร์จะ ยุบ/ขยายได้อย่างเหมาะสมเมื่อเนื้อหาเลื่อน

    // 1. Create the TopAppBarScrollBehavior
    val scrollBehavior = TopAppBarDefaults.enterAlwaysScrollBehavior()
    
    Scaffold(
        topBar = {
            TopAppBar(
                title = {
                    Text("My App")
                },
                // 2. Provide scrollBehavior to TopAppBar
                scrollBehavior = scrollBehavior
            )
        },
        // 3. Connect the scrollBehavior.nestedScrollConnection to the Scaffold
        modifier = Modifier
            .fillMaxSize()
            .nestedScroll(scrollBehavior.nestedScrollConnection)
    ) { contentPadding ->
        /* Contents */
        // ...
    }

ปรับแต่งเอฟเฟกต์การเลื่อนแบบยุบ/ขยาย

คุณระบุพารามิเตอร์หลายรายการสำหรับ enterAlwaysScrollBehavior เพื่อ ปรับแต่งเอฟเฟกต์ภาพเคลื่อนไหวการยุบ/ขยายได้ TopAppBarDefaults ยังมี TopAppBarScrollBehavior อื่นๆ เช่น exitUntilCollapsedScrollBehavior ซึ่งจะขยายแถบแอปเมื่อ เลื่อนเนื้อหาลงไปจนสุดเท่านั้น

หากต้องการสร้างเอฟเฟกต์ที่กำหนดเองทั้งหมด (เช่น เอฟเฟกต์ภาพเคลื่อนไหวแบบพารัลแลกซ์) คุณสามารถสร้าง NestedScrollConnection ของคุณเองและออฟเซ็ตแถบเครื่องมือด้วยตนเองเมื่อเนื้อหาเลื่อน ดูตัวอย่างโค้ดได้ที่ตัวอย่างการเลื่อนที่ซ้อนกันใน AOSP

ตู้ลิ้นชัก

ใน Views คุณจะใช้ navigation drawer โดยใช้ DrawerLayout เป็นรูทวิว ในทางกลับกัน CoordinatorLayout จะเป็น มุมมองย่อยของ DrawerLayout DrawerLayout ยังมีมุมมองขององค์ประกอบย่อยอื่นๆ เช่น NavigationView เพื่อแสดงตัวเลือกการนำทางใน ลิ้นชัก

ใน Compose คุณสามารถใช้แถบนำทางด้านข้างได้โดยใช้ Composable ModalNavigationDrawer ModalNavigationDrawer มีช่อง drawerContent สำหรับลิ้นชักและช่อง content สำหรับเนื้อหาของหน้าจอ

ModalNavigationDrawer(
    drawerContent = {
        ModalDrawerSheet {
            Text("Drawer title", modifier = Modifier.padding(16.dp))
            HorizontalDivider()
            NavigationDrawerItem(
                label = { Text(text = "Drawer Item") },
                selected = false,
                onClick = { /*TODO*/ }
            )
            // ...other drawer items
        }
    }
) {
    Scaffold(Modifier.fillMaxSize()) { contentPadding ->
        // Scaffold content
        // ...
    }
}

ดูข้อมูลเพิ่มเติมได้ที่ลิ้นชัก

แถบแสดงข้อความ

Scaffold มีsnackbarHostช่องที่รับ SnackbarHost Composable เพื่อแสดง Snackbar

val scope = rememberCoroutineScope()
val snackbarHostState = remember { SnackbarHostState() }
Scaffold(
    snackbarHost = {
        SnackbarHost(hostState = snackbarHostState)
    },
    floatingActionButton = {
        ExtendedFloatingActionButton(
            text = { Text("Show snackbar") },
            icon = { Icon(Icons.Filled.Image, contentDescription = "") },
            onClick = {
                scope.launch {
                    snackbarHostState.showSnackbar("Snackbar")
                }
            }
        )
    }
) { contentPadding ->
    // Screen content
    // ...
}

ดูข้อมูลเพิ่มเติมได้ที่แถบข้อความ

ดูข้อมูลเพิ่มเติม

ดูข้อมูลเพิ่มเติมเกี่ยวกับการย้ายข้อมูล CoordinatorLayout ไปยัง Compose ได้ที่แหล่งข้อมูลต่อไปนี้