Android KTX Teil von Android Jetpack.
Android KTX ist eine Reihe von Kotlin-Erweiterungen, die in Android Jetpack und anderen Android-Bibliotheken enthalten sind. KTX-Erweiterungen bieten prägnanten, idiomatischen Kotlin-Code für Jetpack, die Android-Plattform und andere APIs. Dabei nutzen diese Erweiterungen verschiedene Kotlin-Sprachfunktionen, darunter:
- Erweiterungsfunktionen
- Erweiterungseigenschaften
- Lambdas
- Benannte Parameter
- Standardwerte für Parameter
- Koroutinen
Wenn Sie beispielsweise mit
SharedPreferences arbeiten, müssen Sie
einen Editor erstellen, bevor Sie Änderungen an den Einstellungen vornehmen können. Außerdem müssen Sie diese Änderungen anwenden oder bestätigen, wenn Sie mit der Bearbeitung fertig sind, wie im folgenden Beispiel gezeigt:
sharedPreferences
.edit() // create an Editor
.putBoolean("key", value)
.apply() // write to disk asynchronously
Kotlin-Lambdas eignen sich perfekt für diesen Anwendungsfall. Sie ermöglichen einen prägnanteren Ansatz, indem Sie einen Codeblock übergeben, der ausgeführt werden soll, nachdem der Editor erstellt wurde. Der Code wird ausgeführt und die Änderungen werden dann von der SharedPreferences API atomar angewendet.
Hier ist ein Beispiel für eine der Android KTX Core-Funktionen,
SharedPreferences.edit,
die SharedPreferences eine Bearbeitungsfunktion hinzufügt. Diese Funktion verwendet ein optionales boolean-Flag als erstes Argument, das angibt, ob die Änderungen bestätigt oder angewendet werden sollen. Außerdem wird eine Aktion in Form eines Lambdas empfangen, die auf den SharedPreferences-Editor angewendet werden soll.
// SharedPreferences.edit extension function signature from Android KTX - Core
// inline fun SharedPreferences.edit(
// commit: Boolean = false,
// action: SharedPreferences.Editor.() -> Unit)
// Commit a new value asynchronously
sharedPreferences.edit { putBoolean("key", value) }
// Commit a new value synchronously
sharedPreferences.edit(commit = true) { putBoolean("key", value) }
Der Aufrufer kann wählen, ob die Änderungen bestätigt oder angewendet werden sollen. Das action-Lambda ist selbst eine anonyme Erweiterungsfunktion für SharedPreferences.Editor, die Unit zurückgibt, wie durch die Signatur angegeben. Daher können Sie die Arbeit innerhalb des
Blocks direkt mit dem
SharedPreferences.Editor ausführen.
Schließlich enthält die Signatur SharedPreferences.edit() das Keyword inline.
Dieses Keyword weist den Kotlin-Compiler an, den kompilierten Bytecode für die Funktion jedes Mal zu kopieren und einzufügen (oder inline zu verwenden), wenn die Funktion verwendet wird.
So wird der Aufwand vermieden, jedes Mal eine neue Klasse für jede action zu instanziieren, wenn diese Funktion aufgerufen wird.
Dieses Muster, Code mithilfe von Lambdas zu übergeben, sinnvolle Standardwerte anzuwenden, die überschrieben werden können, und diese Verhaltensweisen vorhandenen APIs mit inline-Erweiterungsfunktionen hinzuzufügen, ist typisch für die Verbesserungen, die von der Android KTX-Bibliothek bereitgestellt werden.
Android KTX im Projekt verwenden
Wenn Sie Android KTX verwenden möchten, fügen Sie der Datei build.gradle Ihres Projekts die folgende Abhängigkeit hinzu:
Groovy
repositories { google() }
Kotlin
repositories { google() }
AndroidX-Module
Android KTX ist in Module unterteilt, wobei jedes Modul ein oder mehrere Pakete enthält.
Sie müssen in der Datei build.gradle Ihrer App eine Abhängigkeit für jedes Modul-Artefakt angeben. Fügen Sie dem Artefakt die Versionsnummer hinzu.
Die neuesten Versionsnummern finden Sie im entsprechenden Abschnitt für jedes Artefakt in diesem Thema.
Android KTX enthält ein einzelnes Core-Modul, das Kotlin Erweiterungen für gängige Framework-APIs und mehrere domänenspezifische Erweiterungen bietet.
Mit Ausnahme des Core-Moduls ersetzen alle KTX-Modul-Artefakte die zugrunde liegende Java-Abhängigkeit in der Datei build.gradle. Sie können beispielsweise eine androidx.fragment:fragment-Abhängigkeit durch
androidx.fragment:fragment-ktx ersetzen. Diese Syntax erleichtert die Versionsverwaltung und erfordert keine zusätzlichen Deklarationen für Abhängigkeiten.
Core KTX
Das Core KTX-Modul bietet Erweiterungen für gängige Bibliotheken, die Teil des Android-Frameworks sind. Diese Bibliotheken haben keine Java-basierten Abhängigkeiten, die Sie zu build.gradle hinzufügen müssen.
Wenn Sie dieses Modul einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.core:core-ktx:1.18.0" }
Kotlin
dependencies { implementation("androidx.core:core-ktx:1.18.0") }
Hier ist eine Liste der Pakete, die im Core KTX-Modul enthalten sind:
- androidx.core.animation
- androidx.core.content
- androidx.core.content.res
- androidx.core.database
- androidx.core.database.sqlite
- androidx.core.graphics
- androidx.core.graphics.drawable
- androidx.core.location
- androidx.core.net
- androidx.core.os
- androidx.core.text
- androidx.core.transition
- androidx.core.util
- androidx.core.view
- androidx.core.widget
Collection KTX
Die Collection-Erweiterungen enthalten Dienstprogrammfunktionen für die Arbeit mit den speichereffizienten Sammlungsbibliotheken von Android, darunter ArrayMap, LongSparseArray und LruCache.
Wenn Sie dieses Modul verwenden möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.collection:collection-ktx:1.6.0" }
Kotlin
dependencies { implementation("androidx.collection:collection-ktx:1.6.0") }
Collection-Erweiterungen nutzen die Operatorüberladung von Kotlin, um Dinge wie die Verkettung von Sammlungen zu vereinfachen, wie im folgenden Beispiel gezeigt:
// Combine 2 ArraySets into 1.
val combinedArraySet = arraySetOf(1, 2, 3) + arraySetOf(4, 5, 6)
// Combine with numbers to create a new sets.
val newArraySet = combinedArraySet + 7 + 8
Fragment KTX
Das Fragment KTX-Modul bietet eine Reihe von Erweiterungen, um die Fragment-API zu vereinfachen.
Wenn Sie dieses Modul einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Cool
dependencies { implementation "androidx.fragment:fragment-ktx:1.8.9" }
Kotlin
dependencies { implementation("androidx.fragment:fragment-ktx:1.8.9") }
Mit dem Fragment KTX-Modul können Sie Fragmenttransaktionen beispielsweise mit Lambdas vereinfachen:
fragmentManager().commit {
addToBackStack("...")
setCustomAnimations(
R.anim.enter_anim,
R.anim.exit_anim)
add(fragment, "...")
}
Sie können auch in einer Zeile an ein ViewModel binden, indem Sie die viewModels und
activityViewModels Delegaten für die Eigenschaften verwenden:
// Get a reference to the ViewModel scoped to this Fragment
val viewModel by viewModels<MyViewModel>()
// Get a reference to the ViewModel scoped to its Activity
val viewModel by activityViewModels<MyViewModel>()
Lifecycle KTX
Lifecycle KTX definiert einen LifecycleScope für jedes
Lifecycle-Objekt. Alle in diesem Bereich gestarteten Koroutinen werden abgebrochen, wenn das Lifecycle zerstört wird. Sie können mit den Eigenschaften lifecycle.coroutineScope oder lifecycleOwner.lifecycleScope auf den CoroutineScope des Lifecycle zugreifen.
Wenn Sie dieses Modul einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.lifecycle:lifecycle-runtime-ktx:2.10.0" }
Kotlin
dependencies { implementation("androidx.lifecycle:lifecycle-runtime-ktx:2.10.0") }
Das folgende Beispiel zeigt, wie Sie mit lifecycleOwner.lifecycleScope vorab berechneten Text asynchron erstellen:
class MyFragment: Fragment() {
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
viewLifecycleOwner.lifecycleScope.launch {
val params = TextViewCompat.getTextMetricsParams(textView)
val precomputedText = withContext(Dispatchers.Default) {
PrecomputedTextCompat.create(longTextContent, params)
}
TextViewCompat.setPrecomputedText(textView, precomputedText)
}
}
}
LiveData KTX
Wenn Sie LiveData verwenden, müssen Sie möglicherweise Werte asynchron berechnen. Sie können beispielsweise die Einstellungen eines Nutzers abrufen und sie in der UI bereitstellen. In diesen Fällen bietet LiveData KTX eine liveData-Builder-Funktion, die eine suspend-Funktion aufruft und das Ergebnis als LiveData-Objekt bereitstellt.
Wenn Sie dieses Modul einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.lifecycle:lifecycle-livedata-ktx:2.10.0" }
Kotlin
dependencies { implementation("androidx.lifecycle:lifecycle-livedata-ktx:2.10.0") }
Im folgenden Beispiel ist loadUser() eine `suspend`-Funktion, die an anderer Stelle deklariert wurde.
Sie können die liveData-Builder-Funktion verwenden, um loadUser() asynchron aufzurufen, und dann emit(), um das Ergebnis auszugeben:
val user: LiveData<User> = liveData {
val data = database.loadUser() // loadUser is a suspend function.
emit(data)
}
Weitere Informationen zur Verwendung von Koroutinen mit LiveData finden Sie unter
Kotlin-Koroutinen mit Architekturkomponenten verwenden.
Navigation KTX
Jede Komponente der Navigationsbibliothek hat eine eigene KTX-Version, die die API prägnanter und idiomatisch für Kotlin macht.
Wenn Sie diese Module einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.navigation:navigation-runtime-ktx:2.9.8" implementation "androidx.navigation:navigation-fragment-ktx:2.9.8" implementation "androidx.navigation:navigation-ui-ktx:2.9.8" }
Kotlin
dependencies { implementation("androidx.navigation:navigation-runtime-ktx:2.9.8") implementation("androidx.navigation:navigation-fragment-ktx:2.9.8") implementation("androidx.navigation:navigation-ui-ktx:2.9.8") }
Verwenden Sie die Erweiterungsfunktionen und die Delegierung von Eigenschaften, um auf Zielargumente zuzugreifen und zu Zielen zu navigieren, wie im folgenden Beispiel gezeigt:
class MyDestination : Fragment() {
// Type-safe arguments are accessed from the bundle.
val args by navArgs<MyDestinationArgs>()
...
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
view.findViewById<Button>(R.id.next)
.setOnClickListener {
// Fragment extension added to retrieve a NavController from
// any destination.
findNavController().navigate(R.id.action_to_next_destination)
}
}
...
}
Palette KTX
Das Palette KTX-Modul bietet idiomatische Kotlin-Unterstützung für die Arbeit mit Farbpaletten.
Wenn Sie dieses Modul verwenden möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Cool
dependencies { implementation "androidx.palette:palette-ktx:1.0.0" }
Kotlin
dependencies { implementation("androidx.palette:palette-ktx:1.0.0") }
Wenn Sie beispielsweise mit einer Palette-Instanz arbeiten, können Sie das selected-Farbfeld für ein bestimmtes target mit dem Get-Operator ([ ]) abrufen:
val palette = Palette.from(bitmap).generate()
val swatch = palette[target]
Reactive Streams KTX
Mit dem Reactive Streams KTX-Modul können Sie einen beobachtbaren LiveData-Stream aus einem ReactiveStreams-Publisher erstellen.
Wenn Sie dieses Modul einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.lifecycle:lifecycle-reactivestreams-ktx:2.10.0" }
Kotlin
dependencies { implementation("androidx.lifecycle:lifecycle-reactivestreams-ktx:2.10.0") }
Nehmen wir als Beispiel eine Datenbank mit einer kleinen Liste von Nutzern. In Ihrer App laden Sie die Datenbank in den Arbeitsspeicher und zeigen dann Nutzerdaten in der UI an. Dazu können Sie
RxJava verwenden.
Die Room Jetpack-Komponente kann
die Nutzerliste als Flowable abrufen. In diesem Szenario müssen Sie auch das Rx-Publisher-Abo während der Lebensdauer Ihres Fragments oder Ihrer Aktivität verwalten.
Mit LiveDataReactiveStreams, können Sie jedoch die Vorteile von RxJava und seiner
Vielzahl von Operatoren und Funktionen zur Arbeitsplanung nutzen und gleichzeitig mit
der Einfachheit von LiveData arbeiten, wie im folgenden Beispiel gezeigt:
val fun getUsersLiveData() : LiveData<List<User>> {
val users: Flowable<List<User>> = dao.findUsers()
return LiveDataReactiveStreams.fromPublisher(users)
}
Room KTX
Room-Erweiterungen fügen Unterstützung für Koroutinen für Datenbanktransaktionen hinzu.
Wenn Sie dieses Modul verwenden möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.room:room-ktx:2.8.4" }
Kotlin
dependencies { implementation("androidx.room:room-ktx:2.8.4") }
Hier sind einige Beispiele, in denen Room jetzt Koroutinen verwendet. Im ersten Beispiel
wird eine suspend-Funktion verwendet, um eine Liste von User-Objekten zurückzugeben, während im zweiten Beispiel
Flow von Kotlin verwendet wird,
um die User-Liste asynchron zurückzugeben. Wenn Sie Flow verwenden, werden Sie auch über alle Änderungen in den Tabellen informiert, die Sie abfragen.
@Query("SELECT * FROM Users")
suspend fun getUsers(): List<User>
@Query("SELECT * FROM Users")
fun getUsers(): Flow<List<User>>
SQLite KTX
SQLite-Erweiterungen umschließen SQL-bezogenen Code in Transaktionen, wodurch viel Boilerplate-Code entfällt.
Wenn Sie dieses Modul verwenden möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.sqlite:sqlite-ktx:2.6.2" }
Kotlin
dependencies { implementation("androidx.sqlite:sqlite-ktx:2.6.2") }
Hier ist ein Beispiel für die Verwendung der transaction-Erweiterung, um eine Datenbanktransaktion auszuführen:
db.transaction {
// insert data
}
ViewModel KTX
Die ViewModel KTX-Bibliothek bietet eine viewModelScope()-Funktion, mit der Sie
einfacher Koroutinen aus Ihrem ViewModel starten können. Der
CoroutineScope
ist an Dispatchers.Main gebunden und wird automatisch abgebrochen
wenn der ViewModel gelöscht wird. Sie können viewModelScope() verwenden, anstatt für jedes ViewModel einen neuen Bereich zu erstellen.
Wenn Sie dieses Modul einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "androidx.lifecycle:lifecycle-viewmodel-ktx:2.10.0" }
Kotlin
dependencies { implementation("androidx.lifecycle:lifecycle-viewmodel-ktx:2.10.0") }
Die folgende viewModelScope()-Funktion startet beispielsweise eine Koroutine, die eine Netzwerkanfrage in einem Hintergrundthread stellt. Die Bibliothek übernimmt die gesamte Einrichtung und das entsprechende Löschen des Bereichs:
class MainViewModel : ViewModel() {
// Make a network request without blocking the UI thread
private fun makeNetworkRequest() {
// launch a coroutine in viewModelScope
viewModelScope.launch {
remoteApi.slowFetch()
...
}
}
// No need to override onCleared()
}
WorkManager KTX
WorkManager KTX bietet erstklassige Unterstützung für Koroutinen.
Wenn Sie dieses Modul einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Cool
dependencies { implementation "androidx.work:work-runtime-ktx:2.11.2" }
Kotlin
dependencies { implementation("androidx.work:work-runtime-ktx:2.11.2") }
Anstatt Worker zu erweitern, können Sie jetzt
CoroutineWorker erweitern,
das eine etwas andere API hat. Wenn Sie beispielsweise einen einfachen CoroutineWorker erstellen möchten, um einige Netzwerkoperationen auszuführen, können Sie so vorgehen:
class CoroutineDownloadWorker(context: Context, params: WorkerParameters)
: CoroutineWorker(context, params) {
override suspend fun doWork(): Result = coroutineScope {
val jobs = (0 until 100).map {
async {
downloadSynchronously("https://www.google.com")
}
}
// awaitAll will throw an exception if a download fails, which
// CoroutineWorker will treat as a failure
jobs.awaitAll()
Result.success()
}
}
Weitere Informationen zur Verwendung von CoroutineWorker finden Sie unter
Threading in CoroutineWorker.
WorkManager KTX fügt außerdem Erweiterungsfunktionen zu Operations und ListenableFutures hinzu, um die aktuelle Koroutine aussetzen.
Hier ist ein Beispiel, das die
Operation anhält, die von
enqueue() zurückgegeben wird:
// Inside of a coroutine...
// Run async operation and suspend until completed.
WorkManager.getInstance()
.beginWith(longWorkRequest)
.enqueue().await()
// Resume after work completes...
Weitere KTX-Module
Sie können auch zusätzliche KTX-Module einbeziehen, die außerhalb von AndroidX vorhanden sind.
Firebase KTX
Einige der Firebase SDKs für Android haben Kotlin-Erweiterungsbibliotheken, mit denen Sie idiomatischen Kotlin-Code schreiben können, wenn Sie Firebase in Ihrer App verwenden. Weitere Informationen finden Sie unter:
Google Maps Platform KTX
Für die Android SDKs der Google Maps Platform sind KTX-Erweiterungen verfügbar, mit denen Sie verschiedene Kotlin-Sprachfunktionen wie Erweiterungsfunktionen, benannte Parameter, Standardargumente, destrukturierende Deklarationen und Koroutinen nutzen können. Weitere Informationen finden Sie unter folgenden Links:
Play Core KTX
Play Core KTX fügt Unterstützung für Kotlin-Koroutinen für einmalige Anfragen und Flow für die Überwachung von Statusaktualisierungen hinzu, indem Erweiterungsfunktionen zu SplitInstallManager und AppUpdateManager in der Play Core-Bibliothek hinzugefügt werden.
Wenn Sie dieses Modul einbeziehen möchten, fügen Sie der Datei build.gradle Ihrer App Folgendes hinzu:
Groovy
dependencies { implementation "com.google.android.play:core-ktx:1.8.1" }
Kotlin
dependencies { implementation("com.google.android.play:core-ktx:1.8.1") }
Hier ist ein Beispiel für einen Flow zur Statusüberwachung:
// Inside of a coroutine...
// Request in-app update status updates.
manager.requestUpdateFlow().collect { updateResult ->
when (updateResult) {
is AppUpdateResult.Available -> TODO()
is AppUpdateResult.InProgress -> TODO()
is AppUpdateResult.Downloaded -> TODO()
AppUpdateResult.NotAvailable -> TODO()
}
}
Weitere Informationen
Weitere Informationen zu Android KTX finden Sie im DevBytes-Video.
Wenn Sie ein Problem melden oder eine Funktion vorschlagen möchten, verwenden Sie die Problemverfolgung für Android KTX.