vuejs 双向绑定粗浅理解

1 实现observer 能够对对象的所有变动进行监听,当发生变动时通知订阅者

var data = {name: 'kindeng'};
observe(data);
data.name = 'dmq'; // 哈哈哈,监听到值变化了 kindeng --> dmq

function observe(data) {
    if (!data || typeof data !== 'object') {
        return;
    }
    // 取出所有属性遍历
    Object.keys(data).forEach(function(key) {
        defineReactive(data, key, data[key]);
    });
};

function defineReactive(data, key, val) {
    observe(val); // 监听子属性
    Object.defineProperty(data, key, {
        enumerable: true, // 可枚举
        configurable: false, // 不能再define
        get: function() {
            return val;
        },
        set: function(newVal) {
            console.log('哈哈哈,监听到值变化了 ', val, ' --> ', newVal);
            val = newVal;
        }
    });
}

就是

Object.keys遍历data对象然后传给Object.defineProperty中的get/set钩子

然后实现一个消息订阅器

function Dep() {
    this.subs = [];
}
Dep.prototype = {
    addSub: function(sub) {
        this.subs.push(sub);
    },
    notify: function() {
        this.subs.forEach(function(sub) {
            sub.update();
        });
    }
};  

2 compiler主要做的事情是解析模板指令,将模板中的变量替换成数据,然后初始化渲染页面视图,并将每个指令对应的节点绑定更新函数,添加监听数据的订阅者,一旦数据有变动,收到通知,更新视图

具体思路有几点

  1. 根据el把相对应的元素转换成fragment
  2. 然后遍历所有节点和子节点,调用相对应指令函数进行渲染,并调用相对应指令进行函数绑定

3 实现watcher 作为连接compile和observer的桥梁 能够订阅并收到属性变动的通知 执行指令绑定的相对应的回调函数
Watcher订阅者作为Observer和Compile之间通信的桥梁,主要做的事情是:


  1. 在自身实例化时往属性订阅器(dep)里面添加自己
  2. 自身必须有一个update()方法
  3. 待属性变动dep.notice()通知时,能调用自身的update()方法,并触发Compile中绑定的回调,则功成身退.

4 mvvm入口函数,整合以上三者
通过observer来监听自己model数据变化,通过compile来编译模版指令,利用watcher来搭起observer和compile之间通信的桥梁。
达到 数据变化>=视图更新 视图更新>=数据变化的效果

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值