Die Android-Plattform ist für das Zeichnen der System-UI wie der Statusleiste und der Navigationsleiste verantwortlich. Diese System-UI wird unabhängig davon angezeigt, welche App der Nutzer verwendet.
WindowInsets
stellt Informationen zum System bereit.
Benutzeroberfläche, um sicherzustellen, dass Ihre App im richtigen Bereich gezeichnet wird und nicht verdeckt wird
über die System-UI.
Unter Android 14 (API-Level 34) und niedriger wird die UI Ihrer App nicht darunter dargestellt. Systemleisten und Display-Aussparungen standardmäßig.
Unter Android 15 (API-Level 35) und höher wird Ihre App unter dem System angezeigt Balken und Display-Aussparungen, sobald Ihre App auf SDK 35 ausgerichtet ist. Das führt zu einer besseren Nutzererfahrung und ermöglicht es Ihrer App, den gesamten verfügbaren Fensterbereich zu nutzen.
Wenn Inhalte hinter der System-UI angezeigt werden, wird dies als Bildschirmrand-zu-Bildschirmrand-Ansicht bezeichnet. Auf dieser Seite erfahren Sie mehr über die verschiedenen Arten von Einblendungen, wie Sie den gesamten Bildschirm nutzen und wie Sie die Einblendungs-APIs verwenden, um Ihre Benutzeroberfläche zu animieren und dafür zu sorgen, dass die Inhalte Ihrer App nicht von System-UI-Elementen verdeckt werden.
Eingefügte Grundlagen
Wenn eine App raffiniert wird, müssen Sie dafür sorgen, dass wichtige Inhalte und Interaktionen werden von der System-UI nicht verdeckt. Wenn eine Schaltfläche beispielsweise hinter der Navigationsleiste platziert ist, kann der Nutzer möglicherweise nicht darauf klicken.
Die Größe der System-Benutzeroberfläche und Informationen zum Speicherort werden angegeben. über insets.
Jeder Teil der System-UI hat einen entsprechenden Einsatztyp, der beschreibt, und wo es platziert wird. Einblendungen für die Statusleiste geben beispielsweise die Größe und Position der Statusleiste an, während Einblendungen für die Navigationsleiste die Größe und Position der Navigationsleiste angeben. Jede Art von Einfügung besteht aus vier Pixelabmessungen: oben, links, rechts und unten. Diese Abmessungen geben an, wie weit sich die System-UI von den entsprechenden Seiten des App-Fensters erstreckt. Um Überschneidungen mit dieser Art von System-UI zu vermeiden, muss die App-Benutzeroberfläche um diesen Betrag eingerückt sein.
Diese integrierten Android-Einfügungstypen sind über WindowInsets
verfügbar:
Die Einfügungen zur Beschreibung der Statusleisten. Das sind die oberen System-UI-Leisten mit Benachrichtigungssymbolen und anderen Indikatoren. |
|
Die Statusleiste wird eingerückt, wenn sie sichtbar ist. Wenn die Statusleisten derzeit ausgeblendet sind (weil der immersive Vollbildmodus aktiviert ist), sind die Einzüge der Hauptstatusleiste leer. |
|
Die Einfügungen zur Beschreibung der Navigationsleisten. Dies sind die System-UI-Leisten auf der linken, rechten oder unteren Seite des Geräts, die die Taskleiste oder Navigationssymbole beschreiben. Diese können sich zur Laufzeit ändern, je nachdem, welche Navigationsmethode der Nutzer bevorzugt und wie er mit der Taskleiste interagiert. |
|
Die Navigationsleiste wird eingerückt, wenn sie sichtbar ist. Wenn die Navigationsleisten derzeit ausgeblendet sind (aufgrund des immersiven Vollbildmodus), sind die Einfügungen der Hauptnavigationsleiste leer, aber diese Einfügungen sind nicht leer. |
|
Der Einschub, der die Fensterdekoration der System-UI beschreibt, wenn sich das Fenster in einem freiformigen Fenster befindet, z. B. die obere Titelleiste. |
|
Die Untertitelleiste wird eingeblendet, wenn sie sichtbar ist. Wenn die Untertitelleisten derzeit ausgeblendet sind, sind die Einfügungen der Hauptuntertitelleiste leer, aber diese Einfügungen sind nicht leer. |
|
Die Gesamtheit der Systemleisten-Einfügungen, einschließlich der Statusleisten, Navigationsleisten und der Untertitelleiste. |
|
Die Systemleisteneinfügungen für den Zeitpunkt, zu dem sie sichtbar sind. Wenn die Systemleisten derzeit ausgeblendet sind (aufgrund des immersiven Vollbildmodus), sind die Haupteinfügungen der Systemleiste leer. Diese Einfügungen sind jedoch nicht leer. |
|
Die Einsätze, die angeben, wie viel Platz die Softwaretastatur unten einnimmt. |
|
Die Einblendungen, die den Platz beschreiben, den die Softwaretastatur vor der aktuellen Tastaturanimation belegt hat. |
|
Die Einzüge, die den Platz beschreiben, den die Softwaretastatur nach der aktuellen Tastaturanimation einnimmt. |
|
Eine Art von Einblendungen, die detailliertere Informationen zur Navigations-UI enthalten und den Bereich angeben, in dem „Tippen“ vom System und nicht von der App verarbeitet wird. Bei transparenten Navigationsleisten mit Gestennavigation können einige App-Elemente über die Systemnavigations-UI angetippt werden. |
|
Die antippbaren Elementeinsätze, die sichtbar sind. Wenn die antippbaren Elemente derzeit ausgeblendet sind (aufgrund des immersiven Vollbildmodus), sind die Haupteinfügungen der antippbaren Elemente leer. Diese Einfügungen sind jedoch nicht leer. |
|
Die Einfügungen, die die Anzahl der Einfügungen darstellen, bei denen das System Gesten zur Navigation abfängt. Apps können die Verarbeitung einer begrenzten Anzahl dieser Touch-Gesten über |
|
Ein Teil der Systemgesten, die immer vom System verarbeitet werden und die nicht über |
|
Die Einsätze, die den Abstand darstellen, der erforderlich ist, um eine Überlappung mit einer Display-Aussparung (Kerbe oder Nadelloch) zu vermeiden. |
|
Die Einsätze, die die gekrümmten Bereiche einer Wasserfalldarstellung darstellen. Ein Waterfall-Display hat an den Rändern des Displays gekrümmte Bereiche, in denen das Display an den Seiten des Geräts umgeschlagen wird. |
Diese Typen werden in drei „sichere“ Einblendungstypen zusammengefasst, die dafür sorgen, dass Inhalte nicht verdeckt werden:
Diese „sicheren“ Einbettungstypen schützen Inhalte je nach zugrunde liegender Plattform auf unterschiedliche Weise:
- Verwenden Sie
WindowInsets.safeDrawing
, um Inhalte zu schützen, die nicht unter der Benutzeroberfläche des Systems gezeichnet werden sollen. Dies ist die häufigste Verwendung von Einblendungen: Sie verhindern, dass Inhalte gezeichnet werden, die teilweise oder vollständig von der Benutzeroberfläche des Systems verdeckt werden. - Verwenden Sie
WindowInsets.safeGestures
, um Inhalte mit Touch-Gesten zu schützen. Dieses vermeidet, dass System-Touch-Gesten mit App-Gesten in Konflikt stehen (z. B. für die unteren Tabellenblätter, Karussells oder in Spielen). - Verwenden Sie
WindowInsets.safeContent
als Kombination ausWindowInsets.safeDrawing
undWindowInsets.safeGestures
, damit sich Inhalte nicht überschneiden und es keine Überschneidungen bei Gesten gibt.
Einrichtung von Einsätzen
Um Ihrer App die volle Kontrolle darüber zu geben, wo sie Inhalte abruft, führen Sie die folgenden Einstellungen aus Schritte. Ohne diese Schritte zeichnet Ihre App möglicherweise schwarze oder leuchtende Farben hinter dem System-UI oder nicht synchron mit der Softwaretastatur animiert werden.
- Wählen Sie SDK 35 oder höher aus, um unter Android 15 und höher Edge-to-Edge zu erzwingen. Ihre App hinter der System-UI angezeigt. Sie können die Benutzeroberfläche Ihrer App anpassen, indem Sie Einsätze.
- Optional können Sie
enableEdgeToEdge()
inActivity.onCreate()
aufrufen, damit Ihre App in älteren Android-Versionen randlos angezeigt wird. Du kannst
android:windowSoftInputMode="adjustResize"
in deinen Aktivitäten festlegen:AndroidManifest.xml
-Eintrag. Mit dieser Einstellung kann Ihre App die Größe der Software-IME als Einzüge erhalten. So können Sie Inhalte entsprechend auffüllen und layouten, wenn die IME in Ihrer App erscheint und verschwindet.<!-- 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
Sobald Ihre Aktivität die Verarbeitung aller Einblendungen übernommen hat, können Sie mit Compose APIs dafür sorgen, dass Inhalte nicht verdeckt und interaktive Elemente nicht mit der System-UI überlappen. Diese APIs synchronisieren auch das Layout Ihrer App mit den Änderungen am Insert.
So wenden Sie die Einblendungen beispielsweise auf den Inhalt Ihrer gesamten App an:
override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) enableEdgeToEdge() setContent { Box(Modifier.safeDrawingPadding()) { // the rest of the app } } }
Dieses Snippet wendet die safeDrawing
-Fenstereinsätze als Abstand um den
den gesamten Inhalt der App. So wird sichergestellt, dass
interaktive Elemente
sich mit der System-UI überschneidet, bedeutet dies auch, dass keine der Apps hinter
der Benutzeroberfläche des Systems,
um einen Edge-to-Edge-Effekt zu erzielen. Damit Sie das gesamte Fenster optimal nutzen können, müssen Sie die Platzierung der Einblendungen auf Bildschirm- oder Komponentenebene optimieren.
Alle diese Einblendungstypen werden automatisch mit IME-Animationen animiert, die auf API 21 zurückportiert wurden. Alle Layouts, in denen diese Einfügungen verwendet werden, automatisch animiert, wenn sich die eingefügten Werte ändern.
Es gibt zwei Hauptmethoden, mit denen Sie diese Arten von Einzügen verwenden können, um Ihre zusammensetzbaren Layouts anzupassen: Padding-Modifikatoren und Modifikatoren für die Einzuggröße.
Modifikatoren für das Padding
Modifier.windowInsetsPadding(windowInsets: WindowInsets)
wendet die
vorgegebenen Fenstereinfügungen als Abstand und verhält sich dann genauso wie Modifier.padding
.
Bei Modifier.windowInsetsPadding(WindowInsets.safeDrawing)
werden die sicheren Zeichenbereiche beispielsweise als Abstand auf allen vier Seiten angewendet.
Außerdem gibt es mehrere integrierte Dienstprogrammmethoden für die gängigsten Arten von Einträgen.
Modifier.safeDrawingPadding()
ist eine solche Methode, entspricht
Modifier.windowInsetsPadding(WindowInsets.safeDrawing)
. Für die anderen Arten von Einblendungen gibt es analoge Modifikatoren.
Eingefügte Größenmodifikatoren
Die folgenden Modifikatoren wenden eine Menge an Fenstereinfügungen an, indem sie die Größe der für die Komponente die Größe der Einsätze fest:
Die Startseite von „windowInsets“ wird als Breite angewendet (z. B. |
|
Wendet die Endeseite von windowInsets auf die Breite an (z. B. |
|
Die Oberseite von „windowInsets“ wird als Höhe angewendet (z. B. |
|
|
Die untere Seite von „windowInsets“ wird als Höhe angewendet (z. B. |
Diese Modifikatoren sind besonders nützlich, um die Größe eines Spacer
festzulegen, das den Platz von Einzügen einnimmt:
LazyColumn( Modifier.imePadding() ) { // Other content item { Spacer( Modifier.windowInsetsBottomHeight( WindowInsets.systemBars ) ) } }
Einblendung
Die Modifikatoren für den eingefügten Abstand (windowInsetsPadding
und Hilfsfunktionen wie
safeDrawingPadding
) automatisch den Teil der Einfügungen verbrauchen, die
als Abstand angewendet. Wenn Sie tiefer in den Kompositionbaum eindringen, wissen verschachtelte Modifikatoren für den Abstand von Einzügen und die Größe von Einzügen, dass ein Teil der Einzüge bereits von Modifikatoren für den Abstand von äußeren Einzügen belegt wurde. Sie vermeiden es, denselben Teil der Einzüge mehrmals zu verwenden, was zu zu viel zusätzlichem Platz führen würde.
Mit Modifikatoren für eingefügte Größen wird verhindert, dass ein Teil der Einfügungen mehrmals verwendet wird. falls bereits Insets aufgebraucht sind. Da sie jedoch ihre verwenden, verbrauchen sie selbst keine Einsätze.
Durch verschachtelte Padding-Modifikatoren wird daher automatisch die Größe des Paddings für jedes Composeable geändert.
Im gleichen LazyColumn
-Beispiel wie zuvor wird die LazyColumn
durch den imePadding
-Modifikator in der Größe angepasst. Innerhalb von LazyColumn
hat das letzte Element die Höhe des unteren Endes der Systemleisten:
LazyColumn( Modifier.imePadding() ) { // Other content item { Spacer( Modifier.windowInsetsBottomHeight( WindowInsets.systemBars ) ) } }
Wenn die IME geschlossen ist, wird mit dem imePadding()
-Modifikator kein Abstand angewendet, da die IME keine Höhe hat. Da mit dem imePadding()
-Modifikator kein Abstand angewendet wird, werden keine Einzüge verwendet und die Höhe der Spacer
entspricht der Größe der Unterseite der Systemleisten.
Wenn der IME geöffnet wird, werden die IME-Einfügungen so animiert, dass sie der Größe des IME entsprechen.
Der imePadding()
-Modifikator wendet jetzt einen Abstand unten an, um die Größe von
LazyColumn
, wenn der IME geöffnet wird. Wenn der imePadding()
-Modifikator beginnt, den unteren Abstand anzuwenden, wird auch diese Menge an Einzügen verbraucht. Daher beginnt die Höhe des Spacer
zu sinken, da ein Teil des Abstands für die Systemleisten bereits durch den imePadding()
-Modifikator angewendet wurde. Sobald die
Der imePadding()
-Modifikator wendet einen größeren Abstand unten an
als die Systembalken, ist die Höhe von Spacer
null.
Wenn der IME geschlossen wird, erfolgen die Änderungen umgekehrt: Der Spacer
beginnt,
wird von einer Höhe von 0 aus maximiert, sobald imePadding()
weniger angewendet wird als die
der Systembalken, bis Spacer
schließlich der Höhe des
sobald der IME vollständig animiert ist.
Dieses Verhalten wird durch die Kommunikation zwischen allen windowInsetsPadding
-Modifizierern erreicht und kann auf verschiedene andere Arten beeinflusst werden.
Modifier.consumeWindowInsets(insets: WindowInsets)
verbraucht auch Einsätze
wie für Modifier.windowInsetsPadding
, sie gilt jedoch nicht für
die aufgenommenen Einsätze als Padding. Dies ist in Kombination mit dem Einsatz
Größenmodifikatoren, um Geschwistern anzuzeigen, dass eine bestimmte Anzahl von Einsätzen
bereits verbraucht:
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)
verhält sich sehr gut
ähnlich wie bei der Version mit einem WindowInsets
-Argument,
beliebige PaddingValues
abrufen. Dies ist nützlich, um
untergeordneten Elementen, wenn der Abstand oder die Abstände durch einen anderen Mechanismus als die
Modifikatoren für eingefügten Abstand, z. B. ein gewöhnliches Modifier.padding
oder eine feste Höhe
Abstandshalter:
Column(Modifier.padding(16.dp).consumeWindowInsets(PaddingValues(16.dp))) { // content Spacer(Modifier.windowInsetsBottomHeight(WindowInsets.ime)) }
Wenn die Rohfenstereinfügungen ohne Verbrauch benötigt werden, verwenden Sie die Methode
WindowInsets
-Werte direkt oder verwenden Sie WindowInsets.asPaddingValues()
für
PaddingValues
der Insets zurückgeben, die vom Verbrauch nicht betroffen sind.
Aufgrund der nachfolgenden Vorbehalte sollte jedoch die Verwendung des Paddings für Fenstereinschnitte vorgezogen werden.
Modifikatoren und Fenstereinblendungen Größenmodifikatoren wann immer möglich.
Phasen der Insets und Jetpack Compose-Phasen
Compose verwendet die zugrunde liegenden AndroidX Core APIs, um Einfügungen zu aktualisieren und zu animieren. die die zugrunde liegenden Plattform-APIs nutzen, die Einsätze verwalten. Aufgrund dieser Plattform Insets haben eine besondere Beziehung zu den Phasen von Jetpack. Schreiben:
Der Wert der Insets wird nach der Erstellungsphase, aber vor den Änderungen aktualisiert. Layoutphase. Das bedeutet, dass das Lesen des Werts von Insets in der Zusammensetzung verwendet im Allgemeinen einen Wert der Insets, der einen Frame zu spät kommt. Die auf dieser Seite beschriebenen integrierten Modifikatoren verzögern die Verwendung der Werte der Einzüge bis zur Layoutphase. So wird sichergestellt, dass die Einzugswerte im selben Frame verwendet werden, in dem sie aktualisiert werden.
Tastatur-IME-Animationen mit WindowInsets
Sie können Modifier.imeNestedScroll()
auf einen scrollbaren Container anwenden, um die IME automatisch zu öffnen und zu schließen, wenn Sie zum Ende des Containers scrollen.
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") } } }
Eingefügte Unterstützung für Material 3-Komponenten
Für eine einfachere Bedienung gibt es viele der
(androidx.compose.material3
)
Einsatzfelder selbst verarbeiten, je nachdem, wie die zusammensetzbaren Funktionen in Ihrer App platziert sind.
gemäß den Materialspezifikationen.
Einfügen von Composeable-Elementen
Im Folgenden finden Sie eine Liste der Materialkomponenten, die Einzüge automatisch verarbeiten.
App-Leisten
TopAppBar
/SmallTopAppBar
/CenterAlignedTopAppBar
/MediumTopAppBar
/LargeTopAppBar
: Die obere und horizontale Seite der Systemleisten werden als Abstand angewendet, da sie oben im Fenster verwendet wird.BottomAppBar
: Die unteren und horizontalen Seiten der Systemleisten werden als Abstand angewendet.
Inhaltscontainer
ModalDrawerSheet
/DismissibleDrawerSheet
/PermanentDrawerSheet
(Inhalt in einer modalen Navigationsleiste): Die Einfügungen vertikal und start werden auf Inhalte angewendet.ModalBottomSheet
: Mit dieser Option werden die Unterschnitte angewendet.NavigationBar
: Dient zum Anwenden der unteren und horizontalen Einsätze.NavigationRail
: Die Einfügungen Vertical und start werden angewendet.
Gerüst
Standardmäßig stellt Scaffold
Einzüge als Parameter paddingValues
bereit, die Sie verwenden können.
Scaffold
wendet die Einblendungen nicht auf Inhalte an. Dafür sind Sie selbst verantwortlich.
So verwenden Sie diese Einzüge beispielsweise mit einem LazyColumn
in einem 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]) ) } } }
Standard-Einzüge überschreiben
Sie können den an das Composeable übergebenen Parameter windowInsets
ändern, um das Verhalten des Composeables zu konfigurieren. Dieser Parameter kann ein anderer Fenstereinzug sein, der stattdessen angewendet werden soll, oder deaktiviert werden, indem eine leere Instanz übergeben wird: WindowInsets(0, 0, 0, 0)
.
Wenn Sie beispielsweise die Einzug-Verarbeitung für LargeTopAppBar
deaktivieren möchten, setzen Sie den Parameter windowInsets
auf eine leere Instanz:
LargeTopAppBar( windowInsets = WindowInsets(0, 0, 0, 0), title = { Text("Hi") } )
Interoperabilität mit den Einblendungen des Google Maps-Systems
Möglicherweise müssen Sie die Standardeinfügungen überschreiben, wenn Ihr Bildschirm sowohl Ansichten als auch Erstellen Sie Code in derselben Hierarchie. In diesem Fall müssen Sie explizit welches die Einsätze aufnimmt und welches sie ignorieren soll.
Wenn Ihr äußerstes Layout beispielsweise ein Android-View-Layout ist, sollten Sie die Einzüge im View-System verwenden und für Compose ignorieren.
Wenn Ihr äußerstes Layout ein Composeable ist, sollten Sie die Einzüge in Compose verwenden und die AndroidView
-Composeables entsprechend ausrichten.
Standardmäßig werden von jedem ComposeView
alle Inset-Assets auf der Verbrauchsebene WindowInsetsCompat
verbraucht. Wenn Sie dieses Standardverhalten ändern möchten, setzen Sie ComposeView.consumeWindowInsets
auf false
.
Ressourcen
- Jetzt für Android – eine voll funktionsfähige Android-App, die vollständig mit Kotlin und Jetpack Compose erstellt wurde.
- Edge-to-Edge-Erzwingung in Android 15 – ein Codelab zur Edge-to-Edge-Erzwingung von Android 15
- 3 Dinge, die Ihre Android-App verbessern: Vollbild, Vorhersagefunktion für die Rückwärtsnavigation und Glance – ein YouTube-Video zur Vollbildansicht in Android 15
- Rand bis zum Rand und Einfügungen | Tipps zum Schreiben: Ein YouTube-Video, in dem gezeigt wird, wie Insets von Rand zu Rand gezeichnet werden
Empfehlungen für dich
- Hinweis: Der Linktext wird angezeigt, wenn JavaScript deaktiviert ist.
- Materialkomponenten und -layouts
CoordinatorLayout
zu Compose migrieren- Weitere Hinweise