نقل CoorditorLayout إلى أداة "Compose"

إنّ CoordinatorLayout هو عنصر ViewGroup يتيح التنسيقات المعقدة والمتداخلة والمدمجة. ويتم استخدامها كحاوية لتمكين تفاعلات نظام Material Design، مثل توسيع/تصغير أشرطة الأدوات والأوراق السفلية، لطرق العرض الموجودة بداخلها.

في Compose، أقرب مكافئ لـ CoordinatorLayout هو Scaffold. توفر Scaffold خانات محتوى لدمج "المكوّنات المادية" في أنماط وتفاعلات الشاشة الشائعة. توضّح هذه الصفحة كيفية نقل تنفيذ CoordinatorLayout لاستخدام Scaffold في Compose.

خطوات نقل البيانات

لنقل بيانات CoordinatorLayout إلى Scaffold، اتّبِع الخطوات التالية:

  1. في المقتطف أدناه، يحتوي CoordinatorLayout على AppBarLayout لأنه يشتمل على ToolBar وViewPager وFloatingActionButton. يمكنك التعليق على CoordinatorLayout وعناصرها الثانوية من التدرّج الهرمي لواجهة المستخدم وإضافة 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. في الجزء أو النشاط، عليك الحصول على إشارة إلى ComposeView الذي أضفته للتو واستدعاء طريقة setContent فيه. في نص الطريقة، اضبط Scaffold كمحتوى لها:

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

  3. أضِف المحتوى الأساسي لشاشتك إليه في محتوى "Scaffold". بما أنّ المحتوى الأساسي في ملف XML أعلاه هو ViewPager2، سنستخدم علامة HorizontalPager، وهي المكافئة له في ما يخصّ ميزة Compose. وتتلقّى أيضًا دالة lambda content لـ 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 لإضافة المزيد من عناصر الشاشة ونقل المشاهدات الفرعية المتبقية. يمكنك استخدام الخانة 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 في العرض المرتبط القابل للتمرير (مثل 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 للحصول على مثال على الرمز البرمجي.

الأدراج

من خلال طرق العرض، يتم تنفيذ قائمة التنقّل باستخدام DrawerLayout كعرض الجذر. وبالتالي، فإن CoordinatorLayout هو عرض فرعي لـ DrawerLayout. تحتوي DrawerLayout أيضًا على طريقة عرض فرعية أخرى، مثل NavigationView، لعرض خيارات التنقّل في الدرج.

في Compose، يمكنك تنفيذ درج تنقُّل باستخدام عنصر ModalNavigationDrawer القابل للإنشاء. يوفّر ModalNavigationDrawer فتحة drawerContent للدرج ومنفذ content لمحتوى الشاشة.

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

راجِع الأدراج لمعرفة مزيد من المعلومات.

أشرطة إعلام منبثقة

توفّر Scaffold خانة snackbarHost التي يمكنها قبول SnackbarHost قابلة للإنشاء لعرض 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
    // ...
}

يمكنك الاطّلاع على Snackbars للحصول على مزيد من المعلومات.

مزيد من المعلومات

لمزيد من المعلومات حول نقل CoordinatorLayout إلى Compose، اطّلِع على المراجع التالية: