Mit der Stabilisierung der Android-Architekturkomponenten begann ich, alle grundlegenden ViewModel
s auf die neue Implementierung von ViewModel
zu aktualisieren. In meinem Verständnis wird die Verwendung von LiveData
empfohlen, um die Model
-Klasse zu speichern, da sie den Lebenszyklus besser handhabt.
Ich mag die Verwendung von Data Binding
, da der Code in Java/Kotlin-Seite klarer wird und es nicht erforderlich ist, die Wertänderungen zu "beobachten", um die Benutzeroberfläche zu aktualisieren. Das Layout mit Data Binding
überwacht jedoch nur Datenänderungen, wenn die Model
(oder das ViewModel) BaseObservable
und LiveData
nicht erweitert. Ich verstehe, dass eines der Hauptziele von LiveData
die Beobachtung ist und die Benutzeroberfläche programmgesteuert aktualisiert. Für einfache Updates ist Data Binding
jedoch sehr nützlich.
Dieses Problem wurde bereits gemeldet ( GitHub und Stack Overflow ) und zuerst wurde gesagt, dass die Version 1.0 es haben würde, und nun wird gesagt, dass sich dieses Feature in der Entwicklung befindet.
Um sowohl LiveData
als auch Data Binding
zu verwenden, habe ich eine sehr einfache Implementierung der Klasse erstellt, die BaseObservable
erweitert:
import Android.Arch.lifecycle.LiveData
import Android.Arch.lifecycle.MutableLiveData
import Android.databinding.BaseObservable
class ObservableMutableLiveData<T>() : BaseObservable() {
private var data: MutableLiveData<T> = MutableLiveData()
constructor(data: T) : this() {
this.data.value = data
}
public fun set(value: T) {
if (value != data.value) {
data.value = value
notifyChange()
}
}
public fun get(): T? {
return data.value
}
public fun getObservable(): LiveData<T> {
return data
}
}
Im Grunde ist meine ObservableMutableLiveData
eine Kopie von ObservableField
, die LiveData
zum Speichern des Modells verwendet, und mit dieser Implementierung wird das Layout nach jeder Modellaktualisierung aktualisiert.
Die Fragen sind:
LiveData
? Bricht dieser Wrapper die Funktionen von LiveData
, z. B. lebenszyklusbewusst?LiveData
die neue ObservableField
. Ist das richtig?Das Android Studio 3.1 (derzeit in Canary 6) wird dieses Problem beheben, da LiveData
als observable field
verwendet werden kann:
Aktualisierungen der Datenbindung:
Sie können ein LiveData-Objekt jetzt als beobachtbares Feld in Datenbindungsausdrücken verwenden. Die ViewDataBinding-Klasse enthält jetzt eine neue setLifecycle-Methode, die Sie zum Beobachten von LiveData-Objekten verwenden müssen.
Für diejenigen, die auf diese Frage gestoßen sind und nach einem Beispiel wie ich gesucht haben, ist hier eines:
Fügen Sie im Layout .xml
das LiveData
-Element mit seinem Typ ein:
<layout>
<data>
<variable
name="myString"
type="Android.Arch.lifecycle.MutableLiveData<String>"/>
</data>
...
<TextView
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:text='@{myString}'
...
/>
...
</layout>
In Ihrem Codesatz wird der Wert und der Lebenszyklusbesitzer angezeigt:
MutableLiveData<String> myString = new MutableLiveData<>();
...
binding.setLifecycleOwner(this);
binding.setMyString(myString);
Das ist es :)
Beachten Sie, dass der Standardwert von LiveData
-Elementen null
ist, also weisen Sie Anfangswerte zu, um sicherzustellen, dass Sie den gewünschten Effekt sofort erzielen, oder verwenden Sie this , um die Nullfähigkeit durchzusetzen.
Für Android wird es sein:
androidx.lifecycle.MutableLiveData
<layout>
<data>
<variable
name="myString"
type="androidx.lifecycle.MutableLiveData;String>"/>
</data>
...
<TextView
Android:layout_width="wrap_content"
Android:layout_height="wrap_content"
Android:text='@{myString}'
...
/>
...
</layout>
Und für Kotlin:
val myStr = MutableLiveData<String>()
...
binding.apply {
setLifecycleOwner(this)
this.myString = myStr
}
Viel Glück! :)