אתם יכולים להגדיר הגדרות של מאגר Grid כדי ליצור פריסות גמישות שמותאמות לגדלים שונים של מסכים ולסוגים שונים של תוכן. בדף הזה נסביר איך:
- הגדרת רשת: הגדרת המבנה הבסיסי של שורות ועמודות.
- מיקום פריטים ברשת: הסבר על האופן שבו פריטים ממוקמים בתאים ברשת ואיך משנים את כיוון הזרימה.
- ניהול גודל הרצועה: אפשר להשתמש בגודל קבוע, באחוזים, בגודל גמיש ובגודל מהותי כדי להגדיר את גודל הרצועה.
- הגדרת רווחים: ניהול הרווחים בין השורות והעמודות.
הגדרת רשת
רשת מורכבת מעמודות ומשורות.
לרכיב Grid יש פרמטר config שמקבל פונקציית lambda להגדרת העמודות והשורות בתוך GridConfigurationScope.
בדוגמה הבאה מוגדרת רשת עם שלוש שורות ושתי עמודות, שלכל אחת מהן גודל קבוע שמוגדר ב-Dp:
Grid( config = { repeat(2) { column(160.dp) } repeat(3) { row(90.dp) } } ) { }
הצבת פריטים ברשת
Grid לוקח את רכיבי ממשק המשתמש ב-lambda content ומציב אותם בתאים של הרשת.
הפריטים בפריסת הרשת מוצגים בלי קשר לשאלה אם הגדרתם באופן מפורש את השורות והעמודות.
כברירת מחדל,
Grid מנסה למקם רכיב בממשק המשתמש בתא הזמין ברשת בשורה. אם הוא לא מצליח, הוא ממקם אותו בתא הזמין ברשת בשורה הבאה.
אם אין תאים ריקים, Grid יוצר שורה חדשה.
בדוגמה הבאה, הרשת כוללת שישה תאים, ובכל אחד מהם מוצב כרטיס (איור 1).
כל תא ברשת הוא 160dp x 90dp,
כך שהגודל הכולל של הרשת הוא 320dp x 270dp.
Grid( config = { repeat(2) { column(160.dp) } repeat(3) { row(90.dp) } } ) { Card1() Card2() Card3() Card4() Card5() Card6() }
כדי לשנות את התנהגות ברירת המחדל הזו למילוי לפי עמודה, צריך להגדיר את המאפיין flow לערך GridFlow.Column.
Grid( config = { repeat(2) { column(160.dp) } repeat(3) { row(90.dp) } gap(8.dp) flow = GridFlow.Column // Grid tries to place items to fill the column }, ) { Card1() Card2() Card3() Card4() Card5() Card6() }
GridFlow.Row (שמאל) ו-GridFlow.Column (ימין).
ניהול הגודל של רצועת השמע
המונח grid track מתייחס לשורות ולעמודות ביחד. אפשר לציין את הגודל של רצועת רשת באחת מהשיטות הבאות:
- קבוע (
Dp): הקצאת גודל ספציפי (לדוגמה,column(180.dp)). - אחוז (
Float): מקצה אחוז מהשטח הכולל שזמין מ-0.0fעד1.0f(למשל,row(0.5f)ל-50%). - גמיש (
Fr): המערכת מחלקת את השטח שנותר באופן יחסי אחרי חישוב של רצועות קבועות ורצועות באחוזים. לדוגמה, אם שתי שורות מוגדרות ל-1.frול-3.fr, השורה השנייה מקבלת 75% מהגובה שנותר. - פנימי: גודל הרצועה נקבע לפי התוכן שמופיע בתוכה. מידע נוסף זמין במאמר בנושא קביעת גודל הרצועה של רשת באופן פנימי.
בדוגמה הבאה נעשה שימוש באפשרויות השונות של גודל הרצועה כדי להגדיר את גובה השורה:
Grid( config = { column(1f) row(100.dp) row(0.2f) row(1.fr) row(GridTrackSize.Auto) }, modifier = Modifier.height(480.dp) ) { PastelRedCard("Fixed(100.dp)") PastelGreenCard("Percentage(0.2f)") PastelBlueCard("Flex(1.fr)") PastelYellowCard("Auto") }
Grid.
הגדרת הגודל המינימלי של רכיבי grid גמישים
כשאין יותר מקום בפריט Grid, אפשר לכווץ מסלול גמיש רגיל ל-0.dp.
כדי למנוע את זה ולוודא שהתוכן לא יידחס, צריך להשתמש ב-GridTrackSize.MinMax כדי לאכוף גודל מינימלי מפורש, תוך שמירה על גמישות של רצועת העריכה.
בדוגמה הבאה, לפחות 100.dp מוקצים לשורה הראשונה:
Grid( config = { column(1f) // The first row has a minimum height of 100.dp and can expand to // the half of the remaining space. row(GridTrackSize.MinMax(100.dp, 1.fr)) // The second row takes the half of the remaining space. row(1.fr) // The third row has a fixed height of 200.dp. row(200.dp) }, modifier = Modifier.size(360.dp) // Total grid height is 360.dp ) { PastelRedCard("MinMax(100.dp, 1.fr)") PastelGreenCard("Flex(1.fr)") PastelBlueCard("Fixed(200.dp)") }
100.dp.
הגדרת הגודל המינימלי של קווי הרשת כדי למקם רשימות עצלות
במסלולים גמישים רגילים, המערכת שולחת באופן אוטומטי שאילתות לגבי הגדלים הפנימיים של רכיבי הצאצא כדי לקבוע גודל בסיסי.
עם זאת, ב-Jetpack Compose אי אפשר לבצע שאילתות לגבי הגדלים הפנימיים של SubcomposeLayout, שמשמשים כבסיס לרכיבים כמו LazyColumn ו-LazyRow.
הצבת רשימה עצלה בתוך רצועה גמישה רגילה גורמת לקריסה של IllegalStateException.
כדי למקם בבטחה רשימות של טעינה עצלה בתוך רצועת רשת גמישה, צריך להשתמש ב-MinMax עם גודל מינימלי מוגדר (כמו 0.dp) כדי לעקוף את שלב המדידה המובנה.
Grid( config = { column(1f) // The first row's height is determined by the height of the Text composable. row(GridTrackSize.Auto) // The second row occupies the remaining space, allowing the LazyColumn to scroll. row(GridTrackSize.MinMax(0.dp, 1.fr)) gap(8.dp) }, modifier = Modifier.size(width = 170.dp, height = 240.dp) ) { Text("LazyColumn in a Grid") // The LazyColumn is placed in the second row, filling the remaining space. LazyColumn(verticalArrangement = Arrangement.spacedBy(4.dp)) { items(100) { number -> PastelGreenCard("Card $number") } } }
LazyColumn בתא רשת.
קביעת גודל של טראק ברשת באופן פנימי
אפשר להשתמש בגודל טבעי עבור Grid
כשרוצים שהפריסה תותאם לתוכן, ולא לכפות אותה על מאגר קבוע.
גודל הרצועה ברשת נקבע לפי הערכים הבאים:
-
GridTrackSize.MaxContent: שימוש בגודל המקסימלי של התוכן (למשל, הרוחב נקבע לפי האורך המלא של הטקסט בבלוק טקסט ללא גלישת שורות). -
GridTrackSize.MinContent: שימוש בגודל המינימלי המובנה של התוכן (למשל, הרוחב נקבע לפי המילה הארוכה ביותר בבלוק טקסט). -
GridTrackSize.Auto: שימוש בגודל גמיש לטראק שמותאם לפי המקום הפנוי. ההתנהגות שלו דומה ל-MaxContentכברירת מחדל, אבל הוא מתכווץ ועוטף את התוכן שלו כדי להתאים למאגר האב.
בדוגמה הבאה, שני הטקסטים מוצבים זה לצד זה. גודל העמודה של הטקסט הראשון נקבע לפי הרוחב המינימלי הנדרש להצגת הטקסט, ורוחב העמודה השנייה תלוי ברוחב המקסימלי הנדרש של הטקסט.
Grid( config = { column(GridTrackSize.MinContent) column(GridTrackSize.MaxContent) row(1.0f) }, modifier = Modifier.width(480.dp) ) { Text("Lorem ipsum dolor sit amet, consectetur adipiscing elit. Cras imperdiet.") Text("Lorem ipsum dolor sit amet, consectetur adipiscing elit. Cras imperdiet.") }
הגדרת רווחים בין שורות ועמודות
אחרי שמשנים את הגודל של הטראקים בתצוגת המשבצות, אפשר לשנות את המרווח בין המשבצות כדי לשפר את המרווח בין הטראקים.
אפשר לציין את הרווח בין העמודות באמצעות הפונקציה columnGap, ואת הרווח בין השורות באמצעות הפונקציה rowGap. בדוגמה הבאה, יש רווח של 16dp בין כל שורה ורווח של 8dp בין כל עמודה (איור 5).
Grid( config = { repeat(2) { column(160.dp) } repeat(3) { row(90.dp) } rowGap(16.dp) columnGap(8.dp) } ) { Card1() Card2() Card3() Card4() Card5() Card6() }
אפשר גם להשתמש בפונקציה הנוחה gap
כדי להגדיר מרווחים בגודל זהה בין עמודות ושורות,
וכדי להגדיר גדלים של עמודות ומרווחים בנפרד באמצעות פונקציה אחת.
הקוד הבא מוסיף רווחים של 8dp לרשת:
Grid( config = { repeat(2) { column(160.dp) } repeat(3) { row(90.dp) } gap(8.dp) // Equivalent to columnGap(8.dp) and rowGap(8.dp) } ) { Card1() Card2() Card3() Card4() Card5() Card6() }
הגדרת אזורים ברשת באמצעות אזורים בעלי שם
אזורים עם שמות מאפשרים לכם לצרף שמות לקבוצות של תאים ברשת, שנקראים אזורים ברשת. אתם יכולים להשתמש בשמות האלה במקום באינדקסים של קואורדינטות כשאתם ממקמים רכיבי ממשק משתמש ברשת.
לשימוש באזורים עם שמות יש שני יתרונות עיקריים מבחינת קריאות הקוד:
- כשמגדירים את פריסת הרשת, המטרה והמיקום של התוכן הצפוי ברורים.
- כשמוסיפים את התוכן, המטרה שלו ברורה.
כדי לארגן פריסות מורכבות בצורה ברורה, אתם יכולים להגדיר אזורי רשת סמנטיים כדי להפריד בין מבנה הרשת הפיזי לבין מיקום רכיבי הצאצא.
בתוך פונקציית ה-config lambda, משתמשים בפונקציה area ב-GridConfigurationScope כדי לרשום אזורים בעלי שם ברשת.
לאחר מכן אפשר להקצות רכיבי composable צאצאים לאזורים האלה באמצעות משנה המאפיינים gridItem עם מזהה האזור המתאים. הפונקציה area ממפה מזהה סמנטי (כמו ערך של מחלקת enum או מפתח מחרוזת) לקבוצה של קואורדינטות פיזיות ברשת. קווי הרשת והאינדקסים הם מבוססי-1 (כלומר, השורה הראשונה היא 1 והעמודה הראשונה היא 1).
לדוגמה, אתם מגדירים רשת עם ארבעה מזהי אזורים:
/** * An enum representing the IDs for named areas within the grid. */ enum class GridAreaNames { Area1, Area2, Area3, Area4 }
מציינים את שם האזור באמצעות הפרמטר areaId, יחד עם הקואורדינטות והטווחים של התאים באזור.
המשנה gridItem משתמש ב-areaId כמפתח כדי להקצות כל פריט צאצא לאזור הרשת המיועד שלו, כמו שמוצג בדוגמה הבאה:
Grid( config = { // Define a single column that takes all available width. repeat(2) { column(0.5f) } // Define four rows, each taking 25% of the total height. repeat(4) { row(0.25f) } // Define named grid areas by associating an areaId with specific row and column indices. // Row and column indices are 1-based. area(areaId = GridAreaNames.Area1, row = 1, column = 1, columnSpan = 2) area(areaId = GridAreaNames.Area2, row = 2, column = 1, rowSpan = 3) area(areaId = GridAreaNames.Area3, rows = 2..3, columns = 2..2) area(areaId = GridAreaNames.Area4, row = 4, column = 2) gap(4.dp) }, modifier = Modifier.size(360.dp) ) { PastelRedCard( "Area 1", // Use Modifier.gridItem(areaId) to place this composable into the // grid area defined with the matching ID in the config block. modifier = Modifier.gridItem(areaId = GridAreaNames.Area1) ) PastelGreenCard( "Area 2", modifier = Modifier.gridItem(areaId = GridAreaNames.Area2) ) PastelBlueCard( "Area 3", modifier = Modifier.gridItem(areaId = GridAreaNames.Area3) ) PastelYellowCard( "Area 4", modifier = Modifier.gridItem(areaId = GridAreaNames.Area4) ) }
באמצעות אזורים עם שמות, אפשר לארגן מחדש או לשנות את פריסת הרשת הפיזית (לדוגמה, לשנות שורות, עמודות או גדלים של רצועות) ב-config lambda בלי לשנות את הסדר או הפרמטרים של רכיבי ה-Composable של הצאצא.