Vue2响应式原理
// 订阅器模型
let Dep = {
clientList: {}, // 容器
// 添加订阅
listen: function (key, fn) {
// 短路表达式 fn:附送消息
(this.clientList[key] || (this.clientList[key] = [])).push(fn);
},
// 发布
trigger: function () {
let key = Array.prototype.shift.call(arguments),
fns = this.clientList[key];
if (!fns || fns.length === 0) {
return false;
}
for (let i = 0, fn; fn = fns[i++];) {
fn.apply(this, arguments)
}
}
}
// 数据劫持
let dataHi = function ({ data, tag, datakey, selector }) {
let value = '',
el = document.querySelector(selector);
Object.defineProperty(data, datakey, {
// 取值
get: function () {
console.log("取值")
return value;
},
set: function (val) {
console.log("设置值")
value = val;
// 发布
Dep.trigger(tag, val)
}
})
// 订阅
Dep.listen(tag, function(text){
el.innerHTML = text
})
}
Vue3响应式原理
// 1. Object.defineProperty => Proxy()
// Vue2.x data中的属性做了遍历 + 递归, 给每一个属性设置getter, setter
// data中预定义属性做出响应式
// 2. Proxy()
// 2.1 监听是针对一整个对象(完全代理所有属性)
// 2.2 在目标对象之前假设一层拦截 => 外界访问该对象,必须通过这层拦截
// 响应式重要特征 => 需要捕获到修改,做出对应的反应
let obj = {
name: '小明',
age: 18
}
const p = new Proxy(obj, {
// target => 源数据
// 查
get(target, propName){
console.log(`读取了P的${propName}属性`)
return target[propName]
// return Reflect.get(target, propName)
},
// 改 + 增
set(target, propName, value){
console.log(`修改了P的${propName}属性,值为${value}`)
target[propName] = value
},
// 删
deleteProperty(target, propName){
console.log(`删除了P的${propName}属性`)
return delete target[propName] // 真,假
}
})
网友评论