v-model其实只是一个语法糖
主要的实现依靠:
- v-bind绑定响应式数据
- 触发input事件并传递数据
<input v-model="value"></input>
等同于
<input :value="value" @input="value = $event.target.value"></input>
原理:
其中observe是最主要的部分,用Object.defineProperty来实现数据的劫持,使用get,set方法来通知订阅者,触发update方法,从而实现更新视图
function defineReactive(obj, key, val) {
var dep = new Dep()
Object.defineProperty(obj, key, {
get: function() {
//添加订阅者watcher到主题对象Dep
if (Dep.target) {
// JS的浏览器单线程特性,保证这个全局变量在同一时间内,只会有同一个监听器使用
dep.addSub(Dep.target)
}
return val
},
set: function(newVal) {
if (newVal === val) return
val = newVal
console.log(val)
// 作为发布者发出通知
dep.notify()
}
})
}
//通知后dep会循环调用各自的update方法更新视图
function observe(obj, vm) {
Object.keys(obj).forEach(function(key) {
defineReactive(vm, key, obj[key])
})
}