רשימות מאפשרות למשתמשים לבחור פריט מתוך קבוצת אפשרויות במכשירי WearOS.
בהרבה מכשירי Wear OS יש מסכים עגולים, ולכן קשה יותר לראות פריטים ברשימה שמופיעים בחלק העליון והתחתון של המסך. לכן, ב-Compose for Wear OS יש גרסה של המחלקה LazyColumn שנקראת TransformingLazyColumn, שתומכת בהנפשות של שינוי גודל ושינוי צורה.
כשהפריטים מגיעים לקצוות, הם קטנים יותר ודהויים.
כדי להחיל את אפקטי ההזזה והשינוי המומלצים:
- משתמשים ב-
Modifier.transformedHeightכדי לאפשר ל-Compose לחשב את שינוי הגובה בזמן שהפריט עובר במסך. - משתמשים ב-
transformation = SurfaceTransformation(transformationSpec)כדי להחיל את האפקטים הוויזואליים, כולל הקטנת התוכן של הפריט. - משתמשים ב
TransformationSpecמותאם אישית לרכיבים שלא מקבלים אתtransformationכפרמטר, כמוText.
באנימציה הבאה אפשר לראות איך רכיב ברשימה משנה את הגודל והצורה שלו כשהוא מתקרב לחלק העליון והתחתון של המסך:
בקטע הקוד הבא אפשר לראות איך ליצור רשימה באמצעות פריסתTransformingLazyColumn כדי ליצור תוכן שנראה מצוין במגוון גדלים של מסכי Wear OS.
בקטע הקוד מוצג גם השימוש בשינוי minimumVerticalContentPadding, שצריך להגדיר אותו בפריטים ברשימה כדי להחיל את הריווח הנכון בחלק העליון והתחתון של הרשימה.
כדי להציג את אינדיקטור הגלילה, משתפים את columnState בין ScreenScaffold לבין TransformingLazyColumn:
val columnState = rememberTransformingLazyColumnState() val transformationSpec = rememberTransformationSpec() ScreenScaffold( scrollState = columnState ) { contentPadding -> TransformingLazyColumn( state = columnState, contentPadding = contentPadding ) { item { ListHeader( modifier = Modifier .fillMaxWidth() .transformedHeight(this, transformationSpec) .minimumVerticalContentPadding(ListHeaderDefaults.minimumTopListContentPadding), transformation = SurfaceTransformation(transformationSpec) ) { Text(text = "Header") } } // ... other items item { Button( modifier = Modifier .fillMaxWidth() .transformedHeight(this, transformationSpec) .minimumVerticalContentPadding(ButtonDefaults.minimumVerticalListContentPadding), transformation = SurfaceTransformation(transformationSpec), onClick = { /* ... */ }, icon = { Icon( imageVector = Icons.Default.Build, contentDescription = "build", ) }, ) { Text( text = "Build", maxLines = 1, overflow = TextOverflow.Ellipsis, ) } } } }
הוספת אפקט של הצמדה והטלה
ההצמדה מבטיחה שכאשר משתמש מסיים גלילה או תנועת החלקה, הרשימה תתייצב עם פריט שממוקם בדיוק בנקודה ספציפית, בדרך כלל במרכז המסך. במסכים עגולים, שבהם הפריטים משנים את הגודל והצורה שלהם כשהם מתרחקים מהמרכז, הצמדה שימושית במיוחד כדי לוודא שהפריט הרלוונטי ביותר יישאר גלוי וקריא באופן מלא באזור הצפייה האופטימלי.כדי להוסיף התנהגות של הצמדה והטלה, מגדירים את הפרמטר flingBehavior לערך
TransformingLazyColumnDefaults.snapFlingBehavior(columnState).
מגדירים את rotaryScrollableBehavior כך שיתאים, באמצעות RotaryScrollableDefaults.snapBehavior(columnState), לחוויית שימוש עקבית כשמשתמשים בכתר או במסגרת הפיזיים.
val columnState = rememberTransformingLazyColumnState() ScreenScaffold(scrollState = columnState) { contentPadding -> TransformingLazyColumn( state = columnState, flingBehavior = TransformingLazyColumnDefaults.snapFlingBehavior(columnState), rotaryScrollableBehavior = RotaryScrollableDefaults.snapBehavior(columnState) ) { // ... // ... } }
היפוך הפריסה
כברירת מחדל, רשימה שאפשר לגלול בה מעוגנת לקצה העליון שלה. אם משתמש גלל לתחתית של רשימה רגילה ופריט חדש נוסף לסוף הרשימה, התצוגה של המשתמש נשארת על הפריט הנוכחי. לדוגמה, אם המשתמש צופה בפריט 10 בתחתית המסך, ופריט 11 מתווסף, התצוגה נשארת ממוקדת בפריט 10, ופריט 11 מופיע מחוץ למסך מתחת לתצוגה הנוכחית.
במקרים כמו אפליקציות להעברת הודעות או יומנים בזמן אמת, בדרך כלל לא רוצים את ההתנהגות הזו. כשפריטים חדשים מגיעים, המשתמשים בדרך כלל רוצים לראות את התוכן האחרון באופן מיידי אם הם כבר הגיעו לתחתית הרשימה. אם הרבה פריטים מגיעים בבת אחת, הרשימה צריכה לדלג ולהציג את הפריט האחרון בתחתית (כלומר, יכול להיות שחלק מהפריטים שבאמצע לא יוצגו בכלל אלא אם המשתמש יגלול למעלה).
כדי לתמוך בתרחישי השימוש האלה, TransformingLazyColumn מאפשרת לשנות את פריסת הרכיבים על ידי הגדרת reverseLayout = true. השינוי הזה משנה את העיגון של הרשימה מקצה עליון לקצה תחתון.
כדי שיהיה לכם נוח, ההגדרה reverseLayout = true גם הופכת את הסדר החזותי של הפריטים ואת הכיוון של תנועות הגלילה:
- הפריטים מורכבים מלמטה למעלה, כלומר אינדקס 0 מופיע בתחתית המסך.
- אם גוללים למעלה, רואים פריטים עם אינדקסים גבוהים יותר.
כדי להוסיף התנהגות של הצמדה והזזה יחד עם פריסה הפוכה, אפשר לשלב את flingBehavior ו-rotaryScrollableBehavior כמו בקטע הקוד הבא:
val columnState = rememberTransformingLazyColumnState() val transformationSpec = rememberTransformationSpec() ScreenScaffold(scrollState = columnState) { contentPadding -> TransformingLazyColumn( state = columnState, contentPadding = contentPadding, reverseLayout = true, modifier = Modifier.fillMaxWidth() ) { items(10) { index -> Button( label = { Text( text = "Item ${index + 1}" ) }, onClick = {}, modifier = Modifier .fillMaxWidth() .transformedHeight(this, transformationSpec) .minimumVerticalContentPadding(ButtonDefaults.minimumVerticalListContentPadding), transformation = SurfaceTransformation(transformationSpec) ) } item { // With reverseLayout = true, the last item declared appears at the top. ListHeader( modifier = Modifier .fillMaxWidth() .transformedHeight(this, transformationSpec) .minimumVerticalContentPadding(ListHeaderDefaults.minimumTopListContentPadding), transformation = SurfaceTransformation(transformationSpec) ) { Text("Header") } } } }
בתמונות הבאות אפשר לראות את ההבדל בין רשימה רגילה לרשימה הפוכה:
כפתורי קצה ברשימות
ב-Material 3, אפשר להוסיף EdgeButton, שהוא לחצן שצמוד לקצה התחתון של הרשימות. עם זאת, חשוב להקפיד לא להוסיף את זה כפריט ב-TransformingLazyColumn, אלא להשתמש במשבצת edgeButton ב-ScreenScaffold.
שימוש במשבצת edgeButton מבטיח שהלחצן ימוקם בצורה נכונה בתחתית המסך ויתנהג בצורה מתאימה כשגוללים ברשימה.
בקטע הקוד הבא אפשר לראות איך מטמיעים את EdgeButton:
val columnState = rememberTransformingLazyColumnState() ScreenScaffold( scrollState = columnState, edgeButton = { EdgeButton( onClick = { /* TODO */ }, modifier = Modifier.scrollable( columnState, orientation = Orientation.Vertical, reverseDirection = true, // Apply overscroll to the EdgeButton for proper scrolling behavior. overscrollEffect = rememberOverscrollEffect(), ) ) { Text("More") } } ) { contentPadding -> TransformingLazyColumn( contentPadding = contentPadding, state = columnState, ) { // ... // ... } }
החלקה לחשיפה ברשימות
רכיב SwipeToReveal מאפשר לכם לגשת לפעולות של פריט ברשימה, כמו Card או Chip, באמצעות החלקה. בדרך כלל, בהחלקה לצדדים מופיעים לחצן או שני לחצנים של פעולות (כמו 'מחיקה' או 'עוד').
כשמשתמשים ב-SwipeToReveal בתוך TransformingLazyColumn, חשוב לפעול לפי ההנחיות הבאות:
- איפוס בגלילה: כשמשתמש גולל ברשימה, כל הפריטים שנפתחו בהחלקה יאופסו למצב המכוסה שלהם.
- גבהים עקביים: כדי לשמור על מראה עקבי, צריך להגדיר את הגובה של לחצני הפעולה כך שיתאים לגובה של הפריט הפנימי שמופיע אחרי ההחלקה (בין אם מדובר ב
Buttonאו בCard). - שינוי מאגר התגים: מחילים את המשנה
transformedHeightואתtransformationSpecעל הרכיבSwipeToRevealעצמו. - אל תבצעו טרנספורמציה כפולה: אל תשתמשו במגדירי
transformedHeightאוtransformationבפריט הפנימי שניתן להחלקה (הכרטיס או הלחצן בתוך מאגרSwipeToReveal).
מומלץ בשבילכם
- הערה: טקסט הקישור מוצג כש-JavaScript מושבת
- Compose for Wear OS Codelab
- רשימות ורשתות
- שימוש ב-Views ב-Compose