Jetpack Compose ist ein modernes deklaratives Toolkit zum Erstellen von Android-Oberflächen in Kotlin. Der Entwickler beschreibt die UI über composable-Funktionen, und das Toolkit zeichnet automatisch nur die geänderten Teile neu. Laut Android Developers (2026) läuft Jetpack Compose ab Android 5.0 (API 21), unterstützt Material Design 3 und erreicht auf Mittelklasse-Geräten 120 FPS dank seines eigenen Recomposition-Systems — einem intelligenten Diff-Algorithmus, der nur geänderte Widgets aktualisiert.
Wichtige Punkte
Jetpack Compose ist ein deklaratives Framework von Google zum Erstellen von Android-Benutzeroberflächen, das 2019 angekündigt wurde und 2021 die stabile Version erreichte. Im Gegensatz zum alten View System (XML-Layout + Activity/Fragment) verwendet Compose annotierte Kotlin-Funktionen — @Composable. Die Oberfläche wird vollständig in Kotlin beschrieben: Es gibt keine Trennung zwischen XML und Code. Dadurch entfiel die Klasse von Fehlern im Zusammenhang mit nicht übereinstimmenden IDs in XML und Kotlin (type-safe synthetic half bei der Refaktorisierung nicht).
Compose baut auf einem eigenen Rendering-System — Canvas — auf, das nicht an die View-Hierarchie gebunden ist. Jedes Composable zeichnet sich direkt auf Canvas, ohne onMeasure/onDraw des View Systems zu durchlaufen. Dies bringt einen Leistungsschub bei komplexen Bildschirmen: In Google-Tests (2023) rendert ein Compose-Bildschirm mit 200 Elementen 40% schneller als ein ähnlicher mit RecyclerView + ViewHolder.
Compose erfordert minSdk 21 (Android 5.0) und Kotlin 1.9+. Die Compose BOM (Bill of Materials) synchronisiert die Versionen aller Compose-Bibliotheken. Das Framework ist mit vorhandenem View System-Code kompatibel: Compose wird über ComposeView in XML-Layouts eingebettet, und alte Views über AndroidView in die Compose-Hierarchie. Laut Google Play Console (2025) deckt Android 5.0+ 97% der aktiven Geräte ab, daher ist die Kompatibilität für die meisten Projekte keine Einschränkung.
@Composable ist eine Annotation, die eine normale Kotlin-Funktion in einen UI-Baustein verwandelt. Eine Composable-Funktion beschreibt, wie ein Teil der Oberfläche aussehen soll — Text, Button, Liste. Anstatt einen Wert zurückzugeben, sendet die Funktion UI-Komponenten in die Komposition (emits). Dies ähnelt einem Generator: Jede Funktion fügt beim Aufruf Elemente zum Bildschirm hinzu.
@Composable
fun ProfileCard(name: String, avatarUrl: String) {
Card(
modifier = Modifier.fillMaxWidth().padding(16.dp),
colors = CardDefaults.cardColors(
containerColor = MaterialTheme.colorScheme.surface
)
) {
Row(verticalAlignment = Alignment.CenterVertically) {
AsyncImage(
model = avatarUrl,
contentDescription = "Avatar",
modifier = Modifier.size(48.dp).clip(CircleShape)
)
Spacer(Modifier.width(12.dp))
Text(
text = name,
style = MaterialTheme.typography.titleMedium
)
}
}
}
Die Funktion ProfileCard nimmt Parameter (name, avatarUrl) entgegen und sendet Card → Row → AsyncImage + Text. Komposition ist der Baum der in einem Durchlauf gesendeten Komponenten. Wenn sich die Parameter nicht geändert haben, überspringt Compose den Funktionsaufruf (recomposition skip). Wenn sich nur name geändert hat, wird nur Text aufgerufen, die restlichen Elemente werden nicht neu gezeichnet. Diese intelligente Neuzusammensetzung ist der wichtigste Leistungsvorteil von Compose gegenüber der manuellen Optimierung des View Systems.
Composable-Funktionen nutzen aktiv Slots — trailing lambda, content: @Composable (() -> Unit). Dies ermöglicht die Erstellung von Containern: Card, Column, Row akzeptieren eine content-Lambda, und der Inhalt wird in den Slot eingefügt. Die Slot-API ersetzte XML-Attribute wie android:layout_gravity — jetzt wird die Positionierung der Kind-Elemente durch Kotlin-Code innerhalb des Content-Blocks festgelegt.
State in Compose ist jeder Wert, der sich im Laufe der Zeit ändern kann. Wenn sich der Zustand ändert, plant Compose die Neuzusammensetzung für alle Komponenten, die diesen Zustand lesen. Der Mechanismus ähnelt React-Hooks: mutableStateOf gibt MutableState<T> zurück, das Lesen von .value abonniert automatisch die aktuelle Komposition auf Änderungen.
@Composable
fun CounterExample() {
var count by remember { mutableStateOf(0) }
Column(modifier = Modifier.padding(16.dp)) {
Text("Geklickt: $count")
Button(onClick = { count++ }) {
Text("Erhöhen")
}
}
}
@Composable
fun UserScreen(viewModel: UserViewModel) {
val userName by viewModel.userName.collectAsState()
Text("Benutzer: $userName")
}
remember bewahrt den Wert zwischen Neuzusammensetzungen — sonst würde mutableStateOf bei jedem UI-Update neu erstellt. collectAsState() konvertiert StateFlow aus der ViewModel in einen Compose-kompatiblen Zustand. Empfehlung — Verwenden Sie ViewModel mit StateFlow für zustandsbezogene Bildschirminformationen und mutableStateOf für lokale Zustände (z. B. aufgeklappte Karte). Diese Trennung folgt dem Prinzip intelligenter/stummer Komponenten.
State Hoisting ist ein Muster zum Anheben des Zustands aus einer Kind-Komponente in die Eltern-Komponente. Der Elternteil übergibt Wert und Callback über Parameter, das Kind ruft den Callback bei Änderung auf. Der Elternteil hält mutableStateOf, das Kind nur Parameter. Dies macht die Komponente wiederverwendbar und testbar: Dasselbe TextField kann mit jeder Datenquelle verwendet werden.
Modifier ist ein Objekt, das Transformationen von Composable beschreibt: Größe, Abstände, Hintergrund, Klickbehandlung, Animation, Scrollen. Modifikatoren werden über eine Aufrufkette angewendet: Modifier.fillMaxWidth().padding(16.dp).background(Color.Blue).clickable { }. Jeder Aufruf gibt einen neuen Modifier mit der hinzugefügten Eigenschaft zurück — keine Mutation des ursprünglichen Objekts.
Die Reihenfolge der Modifikatoren ist wichtig. Modifier.padding(16.dp).background(Color.Blue) färbt den Bereich mit Abstand. Modifier.background(Color.Blue).padding(16.dp) färbt das innere Rechteck, der Abstand bleibt transparent. Die Mechanik ähnelt dem CSS-Box-Modell: padding zuerst → background funktioniert wie margin + background; background zuerst → padding funktioniert wie background + Innenabstand. Der Entwickler muss sich nur merken: padding zuerst = Außenabstand, padding danach = Innenabstand.
Wenn die integrierten Modifikatoren nicht ausreichen, wird ein benutzerdefinierter über Modifier.composed { ... } oder Modifier.then() erstellt. Innerhalb eines benutzerdefinierten Modifikators können Layout-Messungen (Modifier.layout { measurable, constraints -> ... }), Zeichnen (Modifier.drawWithContent { ... }), Gesten (Modifier.pointerInput { ... }) verwendet werden. Beispiel: ein Modifikator für eine pulsierende Animation beim Klicken — misst die Größe, startet bei Klick eine Skalierungsanimation über animateFloatAsState.
Für Animationen bietet Compose animate*AsState (animateFloatAsState, animateColorAsState, animateDpAsState) — Werte animieren zwischen altem und neuem Zustand bei Änderung. Für Ein-/Ausblendanimationen — AnimatedVisibility und AnimatedContent mit integrierten Übergängen (fade, slide, expand). Alle Animationen arbeiten auf der Grafikebene, ohne unnötige Komposition auszulösen.
Composable-Funktionen sollten keine Nebeneffekte direkt ausführen (Netzwerkanfragen, Timer, Abonnements) — sie werden bei jeder Neuzusammensetzung aufgerufen, was zu doppelten Anfragen führen würde. Für Nebeneffekte bietet Compose eine Familie von Effect-Funktionen: LaunchedEffect startet eine Coroutine beim Eintritt in die Komposition und bricht sie beim Austritt ab, DisposableEffect — für Ressourcen, die eine explizite Bereinigung erfordern (Sensoren, BroadcastReceiver).
@Composable
fun SensorReader() {
val context = LocalContext.current
var sensorValue by remember { mutableStateOf(0f) }
DisposableEffect(Unit) {
val sensor = registerSensorListener(context) { value ->
sensorValue = value
}
onDispose {
unregisterSensorListener(sensor)
}
}
Text("Wert: $sensorValue")
}
@Composable
fun UserGreeting(userId: String) {
LaunchedEffect(userId) {
val profile = api.fetchProfile(userId)
// Statusaktualisierung
}
}
LaunchedEffect(userId) wird neu gestartet, wenn sich userId ändert — die vorherige Coroutine wird abgebrochen, eine neue mit der neuen userId gestartet. Dies macht die manuelle Verwaltung von Anfrageabbrüchen überflüssig. DisposableEffect(Unit) — ein Effekt mit festem Schlüssel Unit, feuert beim Eintritt in die Komposition und ruft onDispose beim Austritt auf. SensorReader registriert einen Listener und meldet sich beim Verlassen des Bildschirms ab — ohne Risiko von Speicherlecks.
Wenn eine Coroutine nicht beim Eintritt in die Komposition, sondern bei einem Ereignis (Button-Klick) gestartet werden soll, verwenden Sie rememberCoroutineScope(). Es gibt einen an den Composable-Lebenszyklus gebundenen CoroutineScope zurück, ohne dass DisposableEffect erforderlich ist. Beispiel: Starten einer Netzwerkanfrage bei Button-Klick — scope.launch { viewModel.loadData() }.
Die Wahl zwischen Compose und View System ist die wichtigste architektonische Frage für Android-Entwickler im Jahr 2026. Beide Technologien werden von Google unterstützt, aber Compose ist die Hauptrichtung, in die Google Ressourcen investiert. View System erhält nur kritische Korrekturen und entwickelt sich nicht weiter. Der Unterschied zeigt sich in Syntax, Zustandsverwaltung, Leistung und Entwicklungszeit.
| Aspekt | Jetpack Compose | View System |
|---|---|---|
| UI-Beschreibung | Kotlin @Composable-Funktionen | XML-Layout + Activity/Fragment |
| Zustand | mutableStateOf, StateFlow, automatisches Neuzzeichnen | findViewById, manuell: setText, notifyDataSetChanged |
| Leistung | Intelligente Neuzusammensetzung, Canvas-Rendering | View-Hierarchie, measure/layout/draw |
| Animationen | animate*AsState, AnimatedVisibility, integriert | ValueAnimator, ObjectAnimator, Transition |
| Kompatibilität | minSdk 21, ComposeView/AndroidView-Brücken | Alle Versionen, jede |
| APK-Größe | +3–5 MB für Compose | Kein Overhead |
Für neue Projekte empfiehlt Google Jetpack Compose als Standard für die UI-Entwicklung. View System bleibt für die Wartung von Code, der vor 2021 geschrieben wurde, und für Fälle, in denen eine minimale APK-Größe kritisch ist (z. B. für Schwellenmärkte mit Einsteigergeräten). Compose reduziert das UI-Codevolumen um 30–50% im Vergleich zu View System dank seiner deklarativen Syntax und integrierten Animationen.
Häufig gestellte Fragen
Ja, über ComposeView im XML-Layout. Fügen Sie die Compose-Abhängigkeit hinzu und umschließen Sie den Bildschirm oder einen Teil davon in ComposeView { MyComposable() }. Die Migration erfolgt Bildschirm für Bildschirm.
Der Grund ist, dass der Zustand zu hoch angehoben wird oder änderbare Objekte verwendet werden. Lösung: derivedStateOf für abgeleitete Daten und remember für stabile Referenzen.
Verwenden Sie LazyColumn (ähnlich wie RecyclerView). Elemente werden beim Scrollen erstellt und wiederverwendet. Für komplexe Listen mit verschiedenen Zelltypen — LazyColumn { items(items, key = { it.id }) { ... } }.
Nein, Sie können direkt mit Compose beginnen. Kenntnisse des View Systems helfen bei der Wartung von Legacy-Code, aber Compose ist ein eigenständiges Ökosystem mit eigener Dokumentation und eigenen Mustern.
Ja, Material 3 ist seit 2023 das Standard-Theme von Compose. Es wird über implementation("androidx.compose.material3:material3") hinzugefügt. Material 2 gilt als veraltet.
Zusammenfassung
Wir entwickeln eine mobile Applikation schlüsselfertig
IT Sectr entwickelt seit 2017 iOS- und Android-Apps für Startups und Unternehmen. Wir beraten Sie und schlagen die beste Lösung vor.
Lesen Sie auch