当你使用Vue时,你可能已经听说过Vue的双向绑定功能。双向绑定是Vue框架中最重要的功能之一,它让你的应用程序变得更加动态和交互。我们接下来完成一个Vue双向绑定简单版本。
html<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width,initial-scale=1.0">
<title>cs</title>
<script>
</script>
</head>
<body>
<div id="app">
<input type="text" >
值:<span></span>
</div>
<script>
class Dep {
constructor(){
this.subs=[]
}
addSub(sub){
this.subs.push(sub)
}
notify(val){
this.subs.forEach((sub)=>{
console.log(sub)
sub.update(val)
})
}
}
class Observer{
constructor(value){
this.value=value
this.walk(value)
}
walk(value){
Object.keys(value).forEach((key)=>{
this.defineReactive(value,key,value[key])
})
}
defineReactive(obj,key,val){
let dep=new Dep()
this.observer(val)
Object.defineProperty(obj,key,{
get:()=>{
if(Dep.target){
dep.addSub(Dep.target)
}
return val
},
set:(newValue)=>{
if(newValue===val)return
val=newValue
dep.notify(val)
this.observer(val)
}
})
}
observer(value){
if(!value || typeof value!=='object')return
return new Observer(value)
}
}
class Watcher {
constructor(vm,key,cb){
this.vm=vm
this.key=key
this.cb=cb
this.val=this.get()
}
update(val){
this.cb.call(this,val)
}
get(){
Dep.target=this
let val=this.vm[this.key]
Dep.target=null
return val
}
}
let obj={
name:1,
list:{
age:20
}
};
new Observer(obj)
let input=document.querySelector('input')
let span=document.querySelector('span')
input.addEventListener('input',(e)=>{
obj.name=e.target.value
})
new Watcher(obj,'name',(val)=>{
span.innerText=val
})
</script>
</body>
</html>
本文作者:BARM
本文链接:
版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!