Principles and differences between Vue2 bidirectional binding and Vue3 bidirectional binding

Two way binding includes: data update from view to view (realized by listening), and data update from view to view.

Vue responsive principle:

MVVM architecture pattern

The Model layer represents the data Model and defines the business logic of data modification and operation

View represents the UI component, which is responsible for transforming the data model into UI and displaying it

ViewModel is an object that synchronizes View and Model

Under the MVVM architecture, there is no direct connection between View and Model. ViewModel connects the View layer and Model layer through two-way data binding. The interaction between Model and ViewModel is two-way. Therefore, the changes of View data will be synchronized to the Model, and the changes of Model data will be immediately reflected to the View.

Vue2 implementation process

Official documents

1. Pass a normal JavaScript object into the Vue instance as the data option

Simple bidirectional binding
<!DOCTYPE html>
 <html>
    <head>
      <meta charset="utf-8">
      <title>title</title>
    </head>
    <body>
      <input type="text" id="demo" />
      <div id="xxx">{{name}}</div>

      <script type="text/javascript">
        const obj = {};
        Object.defineProperty(obj, 'name', {
          set: function(value) {							   //From data to view
            document.getElementById('xxx').innerHTML = value;
            document.getElementById('demo').value = value;
          }
        });
        document.querySelector('#demo').oninput = function(e) {/ / from view to data
          obj.name = e.target.value;
        }
        obj.name = '';
      </script>
    </body>
</html>

2. Vue will traverse all properties of this object and use Object.defineProperty Turn all these properties into getters / setters.


When the data changes, it will trigger its set function and put the method to be updated in it to update the data to the view
These getters / setters are invisible to the user, but internally they enable Vue to track dependencies and notify changes when properties are accessed and modified.

3. Each component instance corresponds to a watcher instance, which will record the "contacted" data property as a dependency during component rendering. After that, when the setter of the dependency triggers, it will notify the watcher, so that its associated components can be re rendered

This means that each component takes the data it needs as a dependency. As long as there is a dependency to update (listen), it will trigger its own set function to notify the watcher subscribing to this data. The Watcher will monitor its changes and tell the component to update.

vue2 defects and solutions:

Due to JavaScript limitations, Vue cannot detect changes in arrays and objects.
a. Vue cannot detect the addition or removal of properties - via Vue Set (VM. Someobject, 'b', 2), or VM$ set
b. Cannot detect array changes, for example, a[1]=0—— Ibid., method Vue set(vm.items, indexOfItem, newValue)
c. Cannot add an item in data - write data initially and the value is empty

For further understanding, please refer to the blog

  1. The update from data to view requires monitoring and hijacking of data. Here, we set up a listener Observer to monitor all data;
  2. Set a subscriber Watcher, receive the change notification of the attribute and execute the corresponding function to update the view;
  3. Set up a parser Compiler, parse the instructions of all nodes in the view DOM, initialize the data in the template, and then initialize the corresponding subscriber.

Vue3 implementation process:

1. Returns a normal JavaScript object from the data function of a component

2. Vue wraps the object in a with get and set handlers Proxy Yes.

Proxy and Reflect were introduced in ES6, which enabled Vue 3 to avoid some responsiveness problems in earlier versions of Vue.
Proxy, proxy, is an object that wraps another object (similar to a shallow copy) and allows you to block any interaction with that object.
Usage:

let exam = {
    name: "Tom",
    age: 24
}
let handler = {
    get: function(target, key){
        console.log("getting "+key);
        return Reflect.get(target,key);
    },
    set: function(target, key, value){
        console.log("setting "+key+" to "+value)
        Reflect.set(target, key, value);
    }
}
let proxy = new Proxy(exam, handler)
proxy.name = "Jerry"
proxy.name
// setting name to Jerry
// getting name
// "Jerry"

get is read control and set is write control

3. After wrapping the proxy, you need to track when a property is read

const dinner = {
  meal: 'tacos'
}

const handler = {
  get(target, property, receiver) {//
    track(target, property)
    return Reflect.get(...arguments)
  }
}

const proxy = new Proxy(dinner, handler)
console.log(proxy.meal)

// tacos

The track () function will check which effect is currently running (translated as a side effect function in the document) and record it together with the target and property, which makes vue know that the property is the dependency of the current effect - subscription.

4. Rerun this side effect when the property value changes. To do this, you need to use a set function on the agent

const dinner = {
  meal: 'tacos'
}

const handler = {
  get(target, property, receiver) {
    track(target, property)
    return Reflect.get(...arguments)
  },
  set(target, property, value, receiver) {
    trigger(target, property)
    return Reflect.set(...arguments)
  }
}

const proxy = new Proxy(dinner, handler)
console.log(proxy.meal)

// tacos

Trigger the effect that depends on the property of the target through the trigger () function -- release

The implementation of track and trigger functions is to be completed

Added by jetskirich on Mon, 03 Jan 2022 09:57:25 +0200