vue源码—02vue2响应式原理defineProperty

vue源码—02vue2响应式原理defineProperty

vue源码—02vue2响应式原理defineProperty

 看以下html文件

<html>

<head>
    <title>definedproperty</title>
</head>

<body>
    <div id="app">
        <p id="name"></p>
    </div>
    <script>
        var obj = {}
        Object.defineProperty(obj, 'name', {
            get:function() {
                // querySelector() 方法仅仅返回匹配指定选择器的第一个元素。如果你需要返回所有的元素,请使用 querySelectorAll() 方法替代。
                return document.querySelector('#name').innerHTML;
            },
            set:function(val) {
                document.querySelector('#name').innerHTML = val
            }
        })
        obj.name = 'jerry'
    </script>
</body>

</html>

vue源码—02vue2响应式原理defineProperty

 vue原理就是:

数据绑定的原理,是利用了Object.defineProperty的属性,把data里面的数据,每个都在Object.defineProperty定义了一下getter和setter,这样的话就有机会去监听这些属性的变化。当这些属性发生变化的时候,就会通知需要更新的地方去更新。

接下来看一个实例

index.html

<html>

<head>
    <title>definedproperty</title>
</head>

<body>
    <script src="./kvue.js"></script>
    <script>
        const app = new KVue({
            data: {
                test: "I am test",
                foo: {
                    bar: "bar"
                }
            }
        });
        app.$data.test = "hello, jjsun";
        app.$data.foo.bar = "oh my bar";
    </script>
</body>

</html>

kvue.js

// new KVUE({data:{...}})

class KVue {
    constructor(options) {
        this.$options = options;

        // 数据响应化
        this.$data = options.data;
        this.observe(this.$data)
    }
    observe(value) {
        if (!value || typeof value !== 'object') {
            return
        }

        // 遍历该对象
        Object.keys(value).forEach(key => {
            // 定义响应化
            this.defineReactive(value, key, value[key])
        })
    }

    // 数据的响应化
    defineReactive(obj, key, val) {
        this.observe(val);//解决数据嵌套
        Object.defineProperty(obj, key, {
            get() {
                return val;
            },
            set(newVal) {
                if (newVal === val) {
                    return;
                }
                val = newVal;
                console.log(`${key}属性更新了:${val}`);
            }
        })
    }
}

vue源码—02vue2响应式原理defineProperty