הצגת התוכן מקצה לקצה באפליקציה וטיפול ברכיבי חלונות בניסוח אוטומטי

פלטפורמת Android אחראית על ציור ממשק המשתמש של המערכת, כמו שורת המצב וסרגל הניווט. ממשק המשתמש של המערכת מוצג ללא קשר לאפליקציה שבה המשתמש משתמש.

WindowInsets מספק מידע על ממשק המשתמש של המערכת כדי לוודא שהאפליקציה תצייר באזור הנכון וממשק המשתמש לא יוסתר על ידי ממשק המשתמש של המערכת.

ציור מקצה לקצה מאחורי סרחי המערכת
איור 1. ציור מקצה לקצה מאחורי סרחי המערכת.

ב-Android מגרסה 14 (רמת API 34) וגרסאות קודמות, ממשק המשתמש של האפליקציה לא מצויר מתחת לסרגלי המידע של המערכת ולא מציג חתכים כברירת מחדל.

ב-Android 15 ואילך (רמת API 35 ואילך), האפליקציה תציג את התוכן מתחת לסרגלי המערכת ותציג פריימים חתוכים ברגע שהיא מטרגטת ל-SDK 35. כך חוויית השימוש תהיה חלקה יותר, והאפליקציה תוכל לנצל את כל שטח החלון שזמין לה.

הצגת תוכן מאחורי ממשק המשתמש של המערכת נקראת מלא מסך. בדף הזה תלמדו על הסוגים השונים של רכיבי inset, איך להציג את האפליקציה מקצה לקצה ואיך להשתמש בממשקי ה-API של הרכיבים האלה כדי להוסיף אנימציה לממשק המשתמש ולוודא שרכיבי ממשק המשתמש של המערכת לא מסתירים את התוכן של האפליקציה.

יסודות של מוטמעים

כשאפליקציה מוצגת מקצה לקצה, חשוב לוודא שהתוכן והאינטראקציות החשובים לא מוסתרים על ידי ממשק המשתמש של המערכת. לדוגמה, אם הלחצן ממוקם מאחורי סרגל הניווט, יכול להיות שהמשתמש לא יוכל ללחוץ עליו.

הגודל של ממשק המשתמש של המערכת והמידע על המיקום שלו מצוינים באמצעות הכנסות.

לכל חלק בממשק המשתמש של המערכת יש סוג מתאים של תצוגת משנה שמתארת את הגודל ואת המיקום שלו. לדוגמה, הרכיבים הפנימיים של שורת הסטטוס מספקים את המיקום והגודל של שורת הסטטוס, ואילו הרכיבים הפנימיים של סרגל הניווט מספקים את המיקום והגודל של סרגל הניווט. כל סוג של תצוגה מוטמעת מורכב מארבעה מימדים בפיסקלים: למעלה, ימין, שמאל ותחתון. המימדים האלה קובעים את המרחק שבו ממשק המשתמש של המערכת ירחיב מהצדדים התואמים של חלון האפליקציה. לכן, כדי למנוע חפיפה עם סוג כזה של ממשק משתמש מערכת, צריך להציב את ממשק המשתמש של האפליקציה בתוך המסך באותה כמות.

סוגי המודעות המובנות האלה ל-Android זמינים דרך WindowInsets:

WindowInsets.statusBars

התמונות המצורפות שמתארות את שורות הסטטוס. אלה סרחי המערכת העליונים של ממשק המשתמש, שמכילים סמלי התראות ואינדיקטורים אחרים.

WindowInsets.statusBarsIgnoringVisibility

שורת הסטטוס מופיעה בחלק הפנימי של המסך כשהיא גלויה. אם שורות הסטטוס מוסתרות כרגע (בגלל מעבר למצב צפייה immersive במסך מלא), אז הקטעים הפנימיים של שורת הסטטוס הראשית יהיו ריקים, אבל הקטעים הפנימיים האלה לא יהיו ריקים.

WindowInsets.navigationBars

התמונות המצורפות שמתארות את סרחי הניווט. אלה סרחי ממשק המשתמש של המערכת בצד ימין, שמאל או תחתון של המכשיר, שמתארים את סמל שורת המשימות או את סמלי הניווט. הם יכולים להשתנות במהלך זמן הריצה בהתאם לשיטת הניווט המועדפת על המשתמש ולאינטראקציה שלו עם סרגל האפליקציות.

WindowInsets.navigationBarsIgnoringVisibility

סרגל הניווט נדחק פנימה כשהסמלים גלויים. אם סרגי הניווט מוסתרים כרגע (בגלל מעבר למצב צפייה immersive במסך מלא), הקטעים הפנימיים של סרגל הניווט הראשי יהיו ריקים, אבל הקטעים הפנימיים האלה לא יהיו ריקים.

WindowInsets.captionBar

התמונה הממוזערת שמתארת את עיטור החלון של ממשק המשתמש של המערכת, אם מדובר בחלון בצורה חופשית, כמו סרגל הכותרת העליון.

WindowInsets.captionBarIgnoringVisibility

סרגל הכתוביות נדחק כשהן גלויות. אם סרחי הכותרת מוסתרים כרגע, הקטעים הפנימיים של סרגל הכותרת הראשי יהיו ריקים, אבל הקטעים הפנימיים האלה לא יהיו ריקים.

WindowInsets.systemBars

האיחוד של הרכיבים הנוספים בסרגל המערכת, כולל שורת הסטטוס, סרחי הניווט וסרגל הכותרות.

WindowInsets.systemBarsIgnoringVisibility

סרגל המערכת נדחק כשהסמלים גלויים. אם סרחי המערכת מוסתרים כרגע (בגלל מעבר למצב צפייה immersive במסך מלא), הקטעים הפנימיים של סרגל המערכת הראשי יהיו ריקים, אבל הקטעים הפנימיים האלה לא יהיו ריקים.

WindowInsets.ime

התמונות שמתארות את נפח המרחב שבתחתית המסך שבו מופיעה מקלדת התוכנה.

WindowInsets.imeAnimationSource

התמונות הממוזערות שמתארות את נפח המרחב שהמקלדת הווירטואלית השתמש בו לפני האנימציה הנוכחית של המקלדת.

WindowInsets.imeAnimationTarget

התמונות הממוזערות שמתארות את נפח המרחב שבו תתפוס מקלדת התוכנה אחרי אנימציית המקלדת הנוכחית.

WindowInsets.tappableElement

סוג של תצוגה מפורטת יותר של ממשק המשתמש של הניווט, שמציג את גודל המרחב שבו המערכת תנהל את 'הקשות', ולא האפליקציה. בסרגלי ניווט שקופים עם ניווט באמצעות תנועות, אפשר להקיש על רכיבים מסוימים באפליקציה דרך ממשק המשתמש של ניווט המערכת.

WindowInsets.tappableElementIgnoringVisibility

האלמנטים שניתן להקיש עליהם מוצגים בתוך המסך כשהם גלויים. אם הרכיבים שניתן להקיש עליהם מוסתרים כרגע (בגלל מעבר למצב מסך מלא immersive), אז הרכיבים הראשיים שניתן להקיש עליהם בתוך המסך יהיו ריקים, אבל הרכיבים האלה בתוך המסך לא יהיו ריקים.

WindowInsets.systemGestures

הקטעים הפנימיים שמייצגים את מספר הקטעים הפנימיים שבהם המערכת תפריע להבעות לצורך ניווט. אפליקציות יכולות לציין ידנית טיפול במספר מוגבל של התנועות האלה באמצעות Modifier.systemGestureExclusion.

WindowInsets.mandatorySystemGestures

קבוצת משנה של תנועות המערכת שתמיד יטופלו על ידי המערכת, ולא ניתן לבטל את ההסכמה לשימוש בהן באמצעות Modifier.systemGestureExclusion.

WindowInsets.displayCutout

התמונות הממוזערות שמייצגות את כמות הרווחים הנדרשים כדי למנוע חפיפה עם מגרעת במסך (חור או חריץ).

WindowInsets.waterfall

התמונות הקטנות שמייצגות את האזורים המעוגלים בתצוגת מפל. במסך Waterfall יש אזורים מעוגלים בקצוות המסך, שבהם המסך מתחיל להתעגל לאורך הצדדים של המכשיר.

הסוגים האלה מסוכמים בשלושה סוגים של 'הוספה בחלון משנה' 'בטוחים', שמבטיחים שהתוכן לא מוסתר:

סוגי התצוגה הממוזערת 'הבטוחים' האלה מגינים על התוכן בדרכים שונות, בהתאם לתצוגות הממוזערות של הפלטפורמה הבסיסית:

  • משתמשים ב-WindowInsets.safeDrawing כדי להגן על תוכן שאסור לצייר מתחת לממשק המשתמש של המערכת. זהו השימוש הנפוץ ביותר ב-insets: כדי למנוע ציור של תוכן שמוסתר על ידי ממשק המשתמש של המערכת (חלקית או לגמרי).
  • משתמשים ב-WindowInsets.safeGestures כדי להגן על תוכן באמצעות תנועות. כך אפשר למנוע מצב שבו תנועות מערכת מתנגשות בתנועות של אפליקציות (כמו תנועות לגלילה למטה, לקרוסלה או במשחקים).
  • מומלץ להשתמש ב-WindowInsets.safeContent בשילוב של WindowInsets.safeDrawing ו-WindowInsets.safeGestures כדי לוודא שאין חפיפה חזותית או חפיפה של תנועות בתוכן.

הגדרת שוליים

כדי לתת לאפליקציה שליטה מלאה על המיקום שבו היא תציג את התוכן, צריך לבצע את שלבי ההגדרה הבאים. בלי לבצע את השלבים האלה, יכול להיות שהאפליקציה תצייר צבעים שחורים או צבעים מוצקים מאחורי ממשק המשתמש של המערכת, או שהאנימציה לא תתבצע באופן סינכרוני עם המקלדת הווירטואלית.

  1. מטרגטים ל-SDK 35 ואילך כדי לאכוף תצוגה מקצה לקצה ב-Android 15 ואילך. האפליקציה תוצג מאחורי ממשק המשתמש של המערכת. אתם יכולים לשנות את ממשק המשתמש של האפליקציה באמצעות רכיבי insets.
  2. לחלופין, אפשר להפעיל את enableEdgeToEdge() ב-Activity.onCreate(), כדי שהאפליקציה תהיה במסך מלא בגרסאות קודמות של Android.
  3. מגדירים את הערך android:windowSoftInputMode="adjustResize" בעמודה AndroidManifest.xml של הפעילות. ההגדרה הזו מאפשרת לאפליקציה לקבל את הגודל של IME התוכנה כרכיבים מוטמעים, שאפשר להשתמש בהם כדי למלא את התוכן ולפרוס אותו בצורה מתאימה כשה-IME מופיע ונעלם באפליקציה.

    <!-- in your AndroidManifest.xml file: -->
    <activity
      android:name=".ui.MainActivity"
      android:label="@string/app_name"
      android:windowSoftInputMode="adjustResize"
      android:theme="@style/Theme.MyApplication"
      android:exported="true">
    

Compose APIs

אחרי שהפעילות שלכם תתחיל לטפל בכל הרכיבים המוצגים בחלק הפנימי, תוכלו להשתמש ב-Compose API כדי לוודא שהתוכן לא מוסתר ושהרכיבים שניתן לקיים איתם אינטראקציה לא חופפים לממשק המשתמש של המערכת. ממשקי ה-API האלה מסנכרנים גם את הפריסה של האפליקציה עם השינויים בחלונית המשנה.

לדוגמה, זוהי השיטה הבסיסית ביותר להוספת התמונות הקטנות לתוכן של כל האפליקציה:

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)

    enableEdgeToEdge()

    setContent {
        Box(Modifier.safeDrawingPadding()) {
            // the rest of the app
        }
    }
}

קטע הקוד הזה מחיל את הרכיבים הפנימיים של החלון safeDrawing כמילוי מסביב לכל התוכן של האפליקציה. כך מוודאים שהרכיבים שניתן לבצע איתם אינטראקציה לא חופפים לממשק המשתמש של המערכת, אבל זה גם אומר שאף חלק מהאפליקציה לא יופיע מאחורי ממשק המשתמש של המערכת כדי ליצור אפקט מקצה לקצה. כדי לנצל את כל החלון, צריך לשנות את המיקום שבו מופיעים הרכיבים הנוספים בכל מסך או בכל רכיב.

כל סוגי התצוגה המוצגת בתוך התצוגה הראשית האלה מקבלים אנימציה באופן אוטומטי באמצעות אנימציות של IME שהועברו לאחור ל-API 21. כתוצאה מכך, כל הפריסות שמשתמשות בהטמעות האלה יתעדכנו באופן אוטומטי כשערכו של ההטמעה ישתנה.

יש שתי דרכים עיקריות להשתמש בסוגי ההכנסה האלה כדי לשנות את הפריסות של Composable: מודפי ריפוד ומודפי שינוי גודל ההכנסה.

משתני Padding

Modifier.windowInsetsPadding(windowInsets: WindowInsets) מחילה את ה-insets של החלון הנתון כמילוי, בדיוק כמו Modifier.padding. לדוגמה, Modifier.windowInsetsPadding(WindowInsets.safeDrawing) מחילה את הפריימים הפנימיים של הציור הבטוח כמילוי לכל 4 הצדדים.

יש גם כמה שיטות כלי מובנות לסוגי התצוגה הנפוצים ביותר. Modifier.safeDrawingPadding() הוא אחד מה-methods האלה, והוא שווה ערך ל-Modifier.windowInsetsPadding(WindowInsets.safeDrawing). יש משתני אופן פעולה דומים לסוגים האחרים של הוספה.

משתני גודל של תמונות מוטמעות

המשתנים הבאים מחילים כמות של חלונות מוטמעים על ידי הגדרת הגודל של הרכיב לגודל של החלונות המוטמעים:

Modifier.windowInsetsStartWidth(windowInsets: WindowInsets)

החלת הצד ההתחלתי של windowInsets כרוחב (כמו Modifier.width)

Modifier.windowInsetsEndWidth(windowInsets: WindowInsets)

החלת הצד הסופי של windowInsets כרוחב (כמו Modifier.width)

Modifier.windowInsetsTopHeight(windowInsets: WindowInsets)

החלת הצד העליון של windowInsets כגובה (כמו Modifier.height)

Modifier.windowInsetsBottomHeight(windowInsets: WindowInsets)

החלת הצד התחתון של windowInsets כגובה (כמו Modifier.height)

המשתנים האלה שימושיים במיוחד לקביעת הגודל של Spacer שיתפוס את המרחב של התמונות הממוזערות:

LazyColumn(
    Modifier.imePadding()
) {
    // Other content
    item {
        Spacer(
            Modifier.windowInsetsBottomHeight(
                WindowInsets.systemBars
            )
        )
    }
}

צריכת מודעות מוטמעות

משתני הפאדינג של הרכיבים הפנימיים (windowInsetsPadding ופונקציות עזר כמו safeDrawingPadding) צורכים באופן אוטומטי את החלק של הרכיבים הפנימיים שמוחל כפאדינג. כשנכנסים עמוק יותר לתוך עץ הקומפוזיציה, המשתנים של הרווח הפנימי המוטמע ושל גודל ההטמעה הפנימית יודעים שחלק מההטמעות הפנימיות כבר נוצלו על ידי המשתנים של הרווח הפנימי המוטמע החיצוני, ומונעים שימוש באותו חלק מההטמעות הפנימיות יותר מפעם אחת, כי זה יגרום ליותר מדי מקום פנוי.

בנוסף, מודификаторי גודל של תצוגות מפורטות מונעים שימוש באותו חלק של תצוגות מפורטות יותר מפעם אחת, אם כבר נוצלו תצוגות מפורטות. עם זאת, מכיוון שהן משנות את הגודל שלהן ישירות, הן לא צורכות רכיבי inset בעצמן.

כתוצאה מכך, משתני padding בתוך עץ משנים באופן אוטומטי את כמות ה-padding שחלה על כל רכיב.

בדוגמה של LazyColumn מקודם, הגודל של LazyColumn משתנה באמצעות המשתנה המשנה imePadding. בתוך LazyColumn, הפריט האחרון מוגדר לגובה של החלק התחתון של סרחי המערכת:

LazyColumn(
    Modifier.imePadding()
) {
    // Other content
    item {
        Spacer(
            Modifier.windowInsetsBottomHeight(
                WindowInsets.systemBars
            )
        )
    }
}

כשה-IME סגור, המאפיין imePadding() לא מחיל שוליים, כי ל-IME אין גובה. מאחר שמגביל imePadding() לא מחיל שוליים, לא נעשה שימוש בקטעי הטקסט הפנימיים והגובה של Spacer יהיה זהה לגובה החלק התחתון של שורות המערכת.

כשה-IME נפתח, האנימציה של הרכיבים הפנימיים של ה-IME מתאימה את עצמה לגודל של ה-IME, והמַגְדִּיל imePadding() מתחיל להחיל תוספת מרווח בתחתית המסך כדי לשנות את הגודל של LazyColumn בזמן פתיחת ה-IME. כשהמשתנה המשנה imePadding() מתחיל להחיל את החפיפה התחתונה, הוא מתחיל גם לצרוך את כמות החפיפות הזו. לכן, הגובה של Spacer מתחיל לרדת, כי חלק מהרווח בין פסי המערכת כבר הוחל על ידי המשתנה imePadding(). אחרי שהמַעֲדִּר imePadding() מחיל כמות של ריפוד בחלק התחתון שגדולה מהעמודות של המערכת, הגובה של Spacer הוא אפס.

כשה-IME נסגר, השינויים מתרחשים בכיוון ההפוך: ה-Spacer מתחיל להתרחב מגובה אפס ברגע ש-imePadding() חל על פחות מהצד התחתון של סרחי המערכת, עד שבסופו של דבר ה-Spacer תואם לגובה של הצד התחתון של סרחי המערכת ברגע שהאנימציה של ה-IME מסתיימת.

איור 2. עמודה עצלה מקצה לקצה עם TextField.

ההתנהגות הזו מתבצעת באמצעות תקשורת בין כל המשתנים המשתנים של windowInsetsPadding, ואפשר להשפיע עליה בכמה דרכים נוספות.

גם Modifier.consumeWindowInsets(insets: WindowInsets) צורך רכיבי inset באותו אופן כמו Modifier.windowInsetsPadding, אבל הוא לא מחיל את רכיבי ה-inset שנצרכו כמילוי. אפשר להשתמש באפשרות הזו בשילוב עם המשתנים לשינוי גודל ההכנסה, כדי לציין לשכנים של הרכיב שכבר נצרכו כמה הכנסות:

Column(Modifier.verticalScroll(rememberScrollState())) {
    Spacer(Modifier.windowInsetsTopHeight(WindowInsets.systemBars))

    Column(
        Modifier.consumeWindowInsets(
            WindowInsets.systemBars.only(WindowInsetsSides.Vertical)
        )
    ) {
        // content
        Spacer(Modifier.windowInsetsBottomHeight(WindowInsets.ime))
    }

    Spacer(Modifier.windowInsetsBottomHeight(WindowInsets.systemBars))
}

התנהגות הפונקציה Modifier.consumeWindowInsets(paddingValues: PaddingValues) דומה מאוד לזו של הגרסה עם הארגומנט WindowInsets, אבל היא מקבלת לשימוש PaddingValues שרירותי. הדבר שימושי כדי להודיע לצאצאים מתי הרווח או המילוי מסופקים על ידי מנגנון אחר מלבד המשתנים של המילוי הפנימי, כמו Modifier.padding רגיל או רווחים בגובה קבוע:

Column(Modifier.padding(16.dp).consumeWindowInsets(PaddingValues(16.dp))) {
    // content
    Spacer(Modifier.windowInsetsBottomHeight(WindowInsets.ime))
}

במקרים שבהם צריך את הנתונים הגולמיים של חלון ההכנסה ללא צריכה, משתמשים ישירות בערכי WindowInsets, או משתמשים ב-WindowInsets.asPaddingValues() כדי להחזיר PaddingValues של הנתונים הגולמיים שלא מושפעים מהצריכה. עם זאת, בגלל האזהרות שבהמשך, מומלץ להשתמש במשתני הערך של הוספת הריפוד של חלונות המשנה ובמשתני הערך של גודל חלונות המשנה בכל הזדמנות אפשרית.

שוליים ושלבי Jetpack פיתוח נייטיב

Compose משתמש בממשקי ה-API הבסיסיים של AndroidX כדי לעדכן את הרכיבים הפנימיים ולספק להם אנימציה, תוך שימוש בממשקי ה-API הבסיסיים של הפלטפורמה לניהול הרכיבים הפנימיים. בגלל התנהגות הפלטפורמה הזו, ל-insets יש קשר מיוחד לשלבים של Jetpack Compose.

הערך של הפריטים שמוטמעים בתוך התמונה מתעדכן אחרי שלב היצירה, אבל לפני שלב הפריסה. כלומר, בקריאה של הערך של הפריימים המוטמעים בהרכבה בדרך כלל נעשה שימוש בערך של הפריימים המוטמעים שמאוחר יותר מסגרת אחת. המשתנים המובנים שמתוארים בדף הזה נועדו לעכב את השימוש בערכים של הפריטים המוצגים בחזית עד לשלב הפריסה. כך מובטח שהערכים של הפריטים המוצגים בחזית ישמשו באותו פריים שבו הם מתעדכנים.

אנימציות של IME במקלדת באמצעות WindowInsets

אפשר להחיל את Modifier.imeNestedScroll() על מאגר גלילה כדי לפתוח ולסגור את ה-IME באופן אוטומטי כשגוללים לתחתית המאגר.

class WindowInsetsExampleActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        WindowCompat.setDecorFitsSystemWindows(window, false)

        setContent {
            MaterialTheme {
                MyScreen()
            }
        }
    }
}

@OptIn(ExperimentalLayoutApi::class)
@Composable
fun MyScreen() {
    Box {
        LazyColumn(
            modifier = Modifier
                .fillMaxSize() // fill the entire window
                .imePadding() // padding for the bottom for the IME
                .imeNestedScroll(), // scroll IME at the bottom
            content = { }
        )
        FloatingActionButton(
            modifier = Modifier
                .align(Alignment.BottomEnd)
                .padding(16.dp) // normal 16dp of padding for FABs
                .navigationBarsPadding() // padding for navigation bar
                .imePadding(), // padding for when IME appears
            onClick = { }
        ) {
            Icon(imageVector = Icons.Filled.Add, contentDescription = "Add")
        }
    }
}

אנימציה שמציגה רכיב של ממשק משתמש שגוללים למעלה ולמטה כדי לפנות מקום למקלדת
איור 3. אנימציות של IME.

תמיכה ברכיבי Material 3 בתוך רכיבים אחרים

כדי להקל על השימוש, רכיבים רבים מרכיבי ה-composable המובנים של Material 3 (androidx.compose.material3) מטפלים בעצמם בהוספת רכיבים, על סמך המיקום שלהם באפליקציה בהתאם למפרטי Material.

רכיבים מורכבים בתוך קטע

בהמשך מופיעה רשימה של רכיבי Material שמטפלים באופן אוטומטי בהכנסות.

סרגי האפליקציות

קונטיינרים של תוכן

פיגום

כברירת מחדל, Scaffold מספק תצוגות מפורטות כפרמטר paddingValues לשימוש ולצריכה. Scaffold לא מחילה את התמונות הממוזערות על התוכן. האחריות הזו היא שלכם. לדוגמה, כדי לצרוך את הרכיבים האלה עם LazyColumn בתוך Scaffold:

Scaffold { innerPadding ->
    // innerPadding contains inset information for you to use and apply
    LazyColumn(
        // consume insets as scaffold doesn't do it by default
        modifier = Modifier.consumeWindowInsets(innerPadding),
        contentPadding = innerPadding
    ) {
        items(count = 100) {
            Box(
                Modifier
                    .fillMaxWidth()
                    .height(50.dp)
                    .background(colors[it % colors.size])
            )
        }
    }
}

שינוי של ברירת המחדל של הפריטים שמוצגים בחלק הפנימי של המסך

אפשר לשנות את הפרמטר windowInsets שמוענק ל-composable כדי להגדיר את ההתנהגות שלו. הפרמטר הזה יכול להיות סוג אחר של חלון להטמעה שיחולו עליו במקום זאת, או מושבת על ידי העברת מופע ריק: WindowInsets(0, 0, 0, 0).

לדוגמה, כדי להשבית את הטיפול בהטמעה ב-LargeTopAppBar, מגדירים את הפרמטר windowInsets למכונה ריקה:

LargeTopAppBar(
    windowInsets = WindowInsets(0, 0, 0, 0),
    title = {
        Text("Hi")
    }
)

יכולת פעולה הדדית עם התצוגות המפורטות של מערכת View

יכול להיות שתצטרכו לשנות את ברירת המחדל של הפריטים המוצגים בחלק הפנימי של המסך אם במסך שלכם מופיעים גם תצוגות וגם קוד Compose באותה היררכיה. במקרה כזה, צריך לציין בבירור איזה רכיב צריך לצרוך את ה-insets ואילו רכיבים צריכים להתעלם מהם.

לדוגמה, אם הפריסה החיצונית ביותר היא פריסה של Android View, צריך להשתמש ב-insets במערכת View ולהתעלם מהם ב-Compose. לחלופין, אם הפריסה החיצונית ביותר היא רכיב Compose, צריך להשתמש ברכיבי ה-inset ב-Compose ולספק את הרווח הנדרש לרכיבי ה-Compose של AndroidView בהתאם.

כברירת מחדל, כל ComposeView צורך את כל ה-insets ברמת הצריכה WindowInsetsCompat. כדי לשנות את התנהגות ברירת המחדל הזו, מגדירים את הערך של ComposeView.consumeWindowInsets לערך false.

הגנה על סרגל המידע

אחרי שהאפליקציה שלכם מטרגטת ל-SDK 35 ואילך, הצגה מקצה לקצה נאכפת. שורת הסטטוס של המערכת וסרגלי הניווט באמצעות תנועות הם שקופים, אבל סרגל הניווט עם שלושת הלחצנים הוא שקוף למחצה.

כדי להסיר את הגנה הרקע השקופה שמוגדרת כברירת מחדל של ניווט עם שלושה לחצנים, מגדירים את Window.setNavigationBarContrastEnforced לערך false.

משאבים