Produktneuheiten

Neuerungen im Jetpack Compose-Release vom April 2026

Lesezeit: 5 Minuten
Meghan Mehta
Developer Advocate, Android

Die Jetpack Compose-Version vom April 2026 ist jetzt stabil. Sie enthält Version 1.11 der Compose-Kernmodule (siehe die vollständige BOM-Zuordnung), Debugging-Tools für gemeinsame Elemente, Trackpad-Ereignisse und mehr. Außerdem gibt es einige experimentelle APIs, die Sie gerne ausprobieren und uns Feedback dazu geben können.

Wenn Sie das heutige Release verwenden möchten, aktualisieren Sie die Version Ihrer Compose-BOM auf:

implementation(platform("androidx.compose:compose-bom:2026.04.01"))

Änderungen in Compose 1.11.0

Koroutinen in Tests ausführen

Wir führen eine wichtige Änderung ein, wie Compose das Timing von Tests handhabt. Nach dem in Compose 1.10 angekündigten Opt-in-Zeitraum sind die V2-Test-APIs jetzt die Standard-APIs und die V1-APIs wurden eingestellt. Die Änderung des Schlüssels ist eine Änderung des Standard-Test-Dispatchers. Während die v1-APIs auf UnconfinedTestDispatcher basierten, wodurch Coroutinen sofort ausgeführt wurden, verwenden die v2-APIs StandardTestDispatcher. Wenn in Ihren Tests eine Coroutine gestartet wird, wird sie jetzt in die Warteschlange gestellt und erst ausgeführt, wenn die virtuelle Uhr vorgerückt wird.

So werden Produktionsbedingungen besser simuliert, Race Conditions effektiv beseitigt und Ihre Testsuite wird deutlich robuster und weniger fehleranfällig.

Damit Ihre Tests dem Standardverhalten von Koroutinen entsprechen und zukünftige Kompatibilitätsprobleme vermieden werden, empfehlen wir dringend, Ihre Test-Suite zu migrieren. In unserem umfassenden Migrationsleitfaden finden Sie API-Zuweisungen und häufige Korrekturen.

Verbesserungen bei der gemeinsamen Nutzung von Elementen und Tools für Animationen

Außerdem haben wir einige praktische visuelle Debugging-Tools für gemeinsame Elemente und Modifier.animatedBounds hinzugefügt. Sie können jetzt genau sehen, was im Hintergrund passiert, z. B. Zielgrenzen, Animationspfade und wie viele Übereinstimmungen gefunden werden. So lässt sich viel leichter erkennen, warum sich ein Übergang möglicherweise nicht wie erwartet verhält. Wenn Sie die neuen Tools verwenden möchten, umschließen Sie einfach Ihr SharedTransitionLayout mit der zusammensetzbaren Funktion LookaheadAnimationVisualDebugging

LookaheadAnimationVisualDebugging(
    overlayColor = Color(0x4AE91E63),
    isEnabled = true,
    multipleMatchesColor = Color.Green,
    isShowKeylabelEnabled = false,
    unmatchedElementColor = Color.Red,
) {
    SharedTransitionLayout {
        CompositionLocalProvider(
            LocalSharedTransitionScope provides this,
        ) {
            // your content
        }
    }
}

Trackpad-Ereignisse

Wir haben die Unterstützung von Trackpads in Compose überarbeitet. Dazu gehören integrierte Laptop-Trackpads, an Tablets anbringbare Trackpads oder externe/virtuelle Trackpads. Einfache Trackpad-Ereignisse werden jetzt in der Regel als PointerType.Mouse-Ereignisse betrachtet. Dadurch wird das Verhalten von Maus und Trackpad besser an die Erwartungen der Nutzer angepasst. Bisher wurden diese Trackpad-Ereignisse als gefälschte Touchscreen-Finger von PointerType.Touch interpretiert, was zu verwirrenden Nutzererfahrungen führte. Wenn Nutzer beispielsweise mit einem Trackpad geklickt und gezogen haben, wurde gescrollt, anstatt etwas auszuwählen. Durch die Änderung des Zeigertyp dieser Ereignisse in der neuesten Version von Compose wird beim Klicken und Ziehen mit einem Trackpad nicht mehr gescrollt.

Außerdem haben wir die Unterstützung für komplexere Trackpad-Gesten hinzugefügt, die seit API 34 von der Plattform erkannt werden, darunter Wischbewegungen mit zwei Fingern und Ziehgesten. Diese Gesten werden von Komponenten wie Modifier.scrollable und Modifier.transformable automatisch erkannt, um das Verhalten mit Trackpads zu verbessern.

Diese Änderungen verbessern das Verhalten von Touchpads in integrierten Komponenten. So wurde das redundante Touch-Slop entfernt, die Drag-and-drop-Startgeste ist intuitiver, in Textfeldern ist die Auswahl per Doppelklick und Dreifachklick möglich und in Textfeldern werden Kontextmenüs im Desktopstil angezeigt.

Zum Testen des Trackpad-Verhaltens gibt es neue Test-APIs mit performTrackpadInput,, mit denen Sie das Verhalten Ihrer Apps bei Verwendung mit einem Trackpad validieren können. Wenn Sie benutzerdefinierte Gestenerkennung haben, prüfen Sie das Verhalten bei verschiedenen Eingabetypen, z. B. Touchscreens, Mäusen, Trackpads und Stiften. Achten Sie außerdem darauf, dass Mausrad und Trackpad-Gesten unterstützt werden.

beforeAndAfter.webp

Standardeinstellungen für den Kompositionshost (Compose-Laufzeit)

Wir haben HostDefaultProviderLocalHostDefaultProviderHostDefaultKey und ViewTreeHostDefaultKey eingeführt, um Host-Level-Dienste direkt über compose-runtime bereitzustellen. Dadurch entfällt die Notwendigkeit, dass Bibliotheken für Suchvorgänge von compose-ui abhängig sind, was die Unterstützung von Kotlin Multiplatform verbessert. Um diese Werte mit dem Kompositionsbaum zu verknüpfen, können Bibliotheksautoren mit compositionLocalWithHostDefaultOf ein CompositionLocal erstellen, das Standardwerte vom Host auflöst.

Wrapper in der Vorschau ansehen

Benutzerdefinierte Vorschauen in Android Studio ist eine neue Funktion, mit der Sie genau festlegen können, wie der Inhalt einer Compose-Vorschau angezeigt wird.

Durch die Implementierung der PreviewWrapperProvider-Schnittstelle und die Anwendung der neuen @PreviewWrapper-Annotation können Sie ganz einfach benutzerdefinierte Logik einfügen, z. B. einen bestimmten Theme anwenden. Die Annotation kann auf eine Funktion angewendet werden, die mit @Composable und @Preview oder @MultiPreview annotiert ist. Sie bietet eine generische, benutzerfreundliche Lösung, die für alle Vorschaufunktionen funktioniert und sich durch deutlich weniger sich wiederholenden Code auszeichnet.

class ThemeWrapper: PreviewWrapper {
    @Composable
    override fun Wrap(content: @Composable (() -> Unit)) {
        JetsnackTheme {
            content()
        }
    }
}

@PreviewWrapperProvider(ThemeWrapper::class)
@Preview
@Composable
private fun ButtonPreview() {
    // JetsnackTheme in effect
    Button(onClick = {}) {
        Text(text = "Demo")
    }
}

Einstellung und Entfernung

  • Wie im Blogpost zu Compose 1.10 angekündigt, wird Modifier.onFirstVisible() eingestellt. Der Name führte oft zu Missverständnissen, insbesondere bei Lazy Layouts, bei denen die Funktion beim Scrollen mehrmals ausgelöst wurde. Wir empfehlen, zu Modifier.onVisibilityChanged() zu migrieren. Damit lassen sich Sichtbarkeitsstatus manuell und präziser erfassen, sodass sie besser auf die Anforderungen Ihres spezifischen Anwendungsfalls zugeschnitten sind.
  • Das Flag ComposeFoundationFlags.isTextFieldDpadNavigationEnabled wurde entfernt, da die Navigation über das Steuerkreuz für TextFields jetzt standardmäßig immer aktiviert ist. Das neue Verhalten sorgt dafür, dass mit den D-Pad-Ereignissen eines Gamepads oder einer TV-Fernbedienung zuerst der Cursor in die angegebene Richtung bewegt wird. Der Fokus kann erst dann auf ein anderes Element verschoben werden, wenn der Cursor das Ende des Textes erreicht hat.

Kommende APIs

In der bevorstehenden Version 1.12.0 von Compose wird compileSdk auf compileSdk 37 aktualisiert. AGP 9 und alle Apps und Bibliotheken, die von Compose abhängen, übernehmen diese Anforderung. Wir empfehlen, immer die neuesten veröffentlichten Versionen zu verwenden, da Compose neue compileSdks schnell einführt, um Zugriff auf die neuesten Android-Funktionen zu ermöglichen. Weitere Informationen dazu, welche Version von AGP für verschiedene API-Levels unterstützt wird, finden Sie in der Dokumentation

In Compose 1.11.0 werden die folgenden APIs als @Experimental eingeführt. Wir freuen uns auf Ihr Feedback, wenn Sie sie in Ihren Apps ausprobieren. @Experimental APIs werden für die frühe Evaluierung und für Feedback bereitgestellt und können in zukünftigen Releases erheblich geändert oder entfernt werden.

Stile (experimentell)

Wir führen eine neue experimentelle Foundation API für Styling ein. Die Style API ist ein neues Paradigma zum Anpassen visueller Elemente von Komponenten, was bisher mit Modifizierern erfolgte. Sie wurde entwickelt, um eine umfassendere und einfachere Anpassung zu ermöglichen. Dazu werden eine Reihe von standardmäßigen, formatierbaren Eigenschaften mit einfacher statusbasierter Formatierung und animierten Übergängen bereitgestellt. Mit dieser neuen API konnten wir bereits vielversprechende Leistungssteigerungen erzielen. Wir planen, Styles in Material-Komponenten zu übernehmen, sobald die Style API stabil ist.

Hier ein einfaches Beispiel für das Überschreiben des Hintergrunds für den gedrückten Zustand:

@Composable
fun LoginButton(modifier: Modifier = Modifier) {
    Button(
        onClick = {
            // Login logic
        },
        modifier = modifier,
        style = {
            background(
                Brush.linearGradient(
                    listOf(lightPurple, lightBlue)
                )
            )
            width(75.dp)
            height(50.dp)
            textAlign(TextAlign.Center)
            externalPadding(16.dp)

            pressed {
                background(
                    Brush.linearGradient(
                        listOf(Color.Magenta, Color.Red)
                    )
                )
            }
        }
    ){
        Text(
            text = "Login",
        )
    }
}
styles.webp

Dokumentation ansehen und Fehler hier melden

MediaQuery (experimentell)

Die neue mediaQuery API bietet eine deklarative und leistungsstarke Möglichkeit, die Benutzeroberfläche an die Umgebung anzupassen. Dadurch wird der komplexe Informationsabruf in einfache Bedingungen innerhalb eines UiMediaScope abstrahiert, sodass die Neukomposition nur bei Bedarf erfolgt.

Durch die Unterstützung einer Vielzahl von Umgebungssignalen – von Gerätefunktionen wie Tastaturtypen und Zeigergenauigkeit bis hin zu Kontextzuständen wie Fenstergröße und Ausrichtung – können Sie hochgradig responsive Benutzeroberflächen entwickeln. Die Leistung ist in derivedMediaQuery integriert, um hochfrequente Aktualisierungen zu verarbeiten. Da sich Bereiche überschreiben lassen, sind Tests und Vorschauen auf verschiedenen Hardwarekonfigurationen problemlos möglich. Bisher mussten Sie viel Boilerplate-Code schreiben, um auf bestimmte Geräteeigenschaften zuzugreifen, z. B. ob sich ein Gerät im Tischmodus befindet: 

@Composable
fun isTabletopPosture(
    context: Context = LocalContext.current
): Boolean {
    val windowLayoutInfo by
        WindowInfoTracker
            .getOrCreate(context)
            .windowLayoutInfo(context)
            .collectAsStateWithLifecycle(null)

    return windowLayoutInfo.displayFeatures.any { displayFeature ->
        displayFeature is FoldingFeature &&
            displayFeature.state == FoldingFeature.State.HALF_OPENED &&
            displayFeature.orientation == FoldingFeature.Orientation.HORIZONTAL
    }
}

@Composable
fun VideoPlayer() {
    if(isTabletopPosture()) {
        TabletopLayout()
    } else {
        FlatLayout()
    }
}

Mit UIMediaQuery können Sie jetzt die mediaQuery-Syntax hinzufügen, um Geräteattribute abzufragen, z. B. ob sich ein Gerät im Tischmodus befindet:

@OptIn(ExperimentalMediaQueryApi::class)
@Composable
fun VideoPlayer() {
    if (mediaQuery { windowPosture == UiMediaScope.Posture.Tabletop }) {
        TabletopLayout()
    } else {
        FlatLayout()
    }
}

Dokumentation ansehen und Fehler hier melden

Raster (experimentell)

Grid ist eine leistungsstarke neue API zum Erstellen komplexer, zweidimensionaler Layouts in Jetpack Compose. Row und Column eignen sich zwar gut für lineare Designs, mit Grid haben Sie jedoch die strukturelle Kontrolle, die für die Architektur auf Bildschirmebene und komplexe Komponenten erforderlich ist, ohne den Aufwand einer scrollbaren Liste. Mit Grid können Sie Ihr Layout mithilfe von Spuren, Lücken und Zellen definieren. Dabei stehen Ihnen vertraute Größenoptionen wie Dp, Prozentsätze, intrinsische Inhaltsgrößen und flexible „Fr“-Einheiten zur Verfügung. 

@OptIn(ExperimentalGridApi::class)
@Composable
fun GridExample() {
    Grid(
        config = {
            repeat(4) { column(0.25f) }
            repeat(2) { row(0.5f) }
            gap(16.dp)
        }
    ) {
        Card1(modifier = Modifier.gridItem(rowSpan = 2)
        Card2(modifier = Modifier.gridItem(colmnSpan = 3)
        Card3(modifier = Modifier.gridItem(columnSpan = 2)
        Card4()
    }
}

Sie können Elemente automatisch platzieren oder sie für mehr Präzision explizit über mehrere Zeilen und Spalten erstrecken. Das Beste daran ist, dass es sich sehr gut anpassen lässt. Sie können Ihre Raster-Tracks und ‑Spans dynamisch neu konfigurieren, um auf Gerätestatus wie den Tischmodus oder Änderungen der Ausrichtung zu reagieren. So sieht Ihre Benutzeroberfläche auf allen Formfaktoren gut aus.

Grid.gif

Dokumentation ansehen und Fehler hier melden 

FlexBox (Experimental)

FlexBox ist ein Layout-Container, der für leistungsstarke, adaptive Benutzeroberflächen entwickelt wurde. Die Größe der Elemente und die Verteilung des Platzes werden anhand der verfügbaren Containerabmessungen verwaltet. Es bewältigt komplexe Aufgaben wie das Umbrechen (wrap) und die Ausrichtung von Elementen auf mehreren Achsen (justifyContent, alignItems, alignContent). Elemente können vergrößert (grow) oder verkleinert (shrink) werden, um den Container auszufüllen. 

@OptIn(ExperimentalFlexBoxApi::class)
fun FlexBoxWrapping(){
    FlexBox(
        config = {
            wrap(FlexWrap.Wrap)
            gap(8.dp)
        }
    ) {
        RedRoundedBox()
        BlueRoundedBox()
        GreenRoundedBox(modifier = Modifier.width(350.dp).flex { grow(1.0f) })
        OrangeRoundedBox(modifier = Modifier.width(200.dp).flex { grow(0.7f) })
        PinkRoundedBox(modifier = Modifier.width(200.dp).flex { grow(0.3f) })
    }
}
AnimationGif.gif

Dokumentation ansehen und Fehler hier melden

Neue SlotTable-Implementierung (experimentell)

Wir haben eine neue Implementierung von SlotTable eingeführt, die in dieser Version standardmäßig deaktiviert ist. SlotTable ist die interne Datenstruktur, die von der Compose-Laufzeit verwendet wird, um den Status der Kompositionshierarchie zu verfolgen, Invalidierungen/Recompositionen zu erfassen, gespeicherte Werte zu speichern und alle Metadaten der Komposition zur Laufzeit zu erfassen. Diese neue Implementierung soll die Leistung verbessern, insbesondere bei zufälligen Änderungen.

Wenn Sie das neue SlotTable ausprobieren möchten, aktivieren Sie ComposeRuntimeFlags.isLinkBufferComposerEnabled

Jetzt mit dem Programmieren loslegen

Mit so vielen spannenden neuen APIs in Jetpack Compose und vielen weiteren, die noch folgen werden, ist jetzt der richtige Zeitpunkt, um zu Jetpack Compose zu migrieren. Wie immer freuen wir uns über Ihr Feedback und Ihre Funktionsvorschläge, insbesondere zu @Experimental-Funktionen, die sich noch in der Entwicklung befinden. Bitte reichen Sie sie hier ein. Viel Spaß beim Komponieren!

Verfasst von:

Weiterlesen