Das Antwortsystem ist ein wichtiges Merkmal von Vue. Durch das Ändern von Eigenschaften kann die Ansicht aktualisiert werden, was die Statusverwaltung sehr einfach und intuitiv macht.
Beim Erstellen einer Vue-Instanz durchläuft Vue die Eigenschaften von Daten und konvertiert sie über Object.defineProperty von ES5 in Getter/Setter. Intern kann Vue Abhängigkeiten verfolgen und Änderungen benachrichtigen.
const vm = new Vue({ data: {foo: 1} // 'vm.foo' (在内部,同 'this.foo') 是响应的 })
Eigenschaftsänderungen beobachten
Vue-Instanzen stellen die $watch-Methode zum Beobachten von Eigenschaftsänderungen bereit.
const vm = new Vue({ data: {foo: 1} }) vm.$watch('foo', function (newValue, oldValue) { console.log(newValue, oldValue) // 输出 2 1 console.log(this.foo) // 输出 2 }) vm.foo = 2
Wenn sich die Eigenschaft ändert, wird die Antwortfunktion aufgerufen und intern wird diese automatisch an die Vue-Instanz-VM gebunden.
Es ist zu beachten, dass die Antwort asynchron ist. Wie folgt:
const vm = new Vue({ data: {foo: 1} }) vm.$watch('foo', function (newValue, oldValue) { console.log('inner:', newValue) // 后输出 "inner" 2 }) vm.foo = 2 console.log('outer:', vm.foo) // 先输出 "outer" 2
Die Bindung von Daten und Ansicht wird durch $watch Vue erreicht. Wenn Datenänderungen beobachtet werden, aktualisiert Vue das DOM asynchron. Innerhalb derselben Ereignisschleife werden mehrere Datenänderungen zwischengespeichert. In der nächsten Ereignisschleife aktualisiert Vue nur die erforderlichen Aktualisierungen. Wie folgt:
const vm = new Vue({ data: {foo: 1} }) vm.$watch('foo', function (newValue, oldValue) { console.log('inner:', newValue) // 后只输出一次 "inner" 5 }) vm.foo = 2 vm.foo = 3 vm.foo = 4 console.log('outer:', vm.foo) // 先输出 "outer" 4 vm.foo = 5
Berechnete Eigenschaft
MV* weist beim Anzeigen von Modellebenendaten häufig eine komplexe Datenverarbeitungslogik auf. In diesem Fall ist die Verwendung berechneter Eigenschaften sinnvoller.
const vm = new Vue({ data: { width: 0, height: 0, }, computed: { area () { let output = '' if (this.width > 0 && this.height > 0) { const area = this.width * this.height output = area.toFixed(2) + 'm²' } return output } } }) vm.width = 2.34 vm.height = 5.67 console.log(vm.area) // 输出 "13.27m²"
Innerhalb einer berechneten Eigenschaft ist diese automatisch an vm gebunden, daher müssen Sie beim Deklarieren berechneter Eigenschaften die Verwendung von Pfeilfunktionen vermeiden.
Im obigen Beispiel reagieren vm.width und vm.height. Wenn vm.area this.width und this.height zum ersten Mal liest, erfasst Vue sie als Abhängigkeiten von vm.area. width oder Wenn sich vm.height ändert, wird vm.area neu ausgewertet.
Berechnete Eigenschaften basieren auf dem Abhängigkeitscache. Wenn sich vm.width und vm.height nicht ändern, werden durch mehrmaliges Lesen von vm.area sofort die vorherigen Berechnungsergebnisse zurückgegeben, ohne dass eine erneute Auswertung erforderlich ist.
Da vm.width und vm.height ebenfalls reagieren, können Sie einer Variablen in vm.area abhängige Eigenschaften zuweisen und die Häufigkeit des Lesens von Eigenschaften durch das Lesen der Variablen reduzieren. Gleichzeitig löst Vue das Problem Problem der bedingten Verzweigung. Manchmal können Abhängigkeiten nicht erfasst werden.
Die neue Implementierung lautet wie folgt:
const vm = new Vue({ data: { width: 0, height: 0, }, computed: { area () { let output = '' const {width, height} = this if (width > 0 && height > 0) { const area = width * height output = area.toFixed(2) + 'm²' } return output } } }) vm.width = 2.34 vm.height = 5.67 console.log(vm.area) // 输出 "13.27m²"
Verwenden Sie das Attributbeobachtungsmodul von Vue allein über ob.js
Um das Lernen und die Verwendung zu erleichtern, extrahiert ob.js das Attributbeobachtungsmodul in Vue Und hat es gekapselt.
Installation
npm install --save ob.js
Eigenschaftsänderungen beobachten
const target = {a: 1} ob(target, 'a', function (newValue, oldValue) { console.log(newValue, oldValue) // 3 1 }) target.a = 3
Berechnete Eigenschaften hinzufügen
const target = {a: 1} ob.compute(target, 'b', function () { return this.a * 2 }) target.a = 10 console.log(target.b) // 20
Übergeben Sie den Parametersatz genau wie beim Deklarieren eines Vue Instanz
const options = { data: { PI: Math.PI, radius: 1, }, computed: { 'area': function () { return this.PI * this.square(this.radius) }, }, watchers: { 'area': function (newValue, oldValue) { console.log(newValue) // 28.274333882308138 }, }, methods: { square (num) { return num * num }, }, } const target = ob.react(options) target.radius = 3