简单实现vue2中的响应式

vue2数据双向绑定的工作原理是通过 object.defineProperty() 来劫持各个属性的setter和getter,在数据变动时 发布消息给订阅者,触发相应的监听回调。现在我们就通过代码来简单实现吧

示例将通过输入框输入 与box里面内容相互绑定

<div id="app">
            <input class="username" type="text" />
            <input class="password" type="text" />
            <div style="display: flex;" >
                <span> 账号:</span><div class="box1"></div>
            </div>
            <div  style="display: flex;" >
               <span> 密码:</span><div class="box2"></div>
            </div>
    </div>
// An highlighted block
        let dataObj = {}
        // 订阅者模拟器
        const Dep = {
            // 存储订阅者
            clientList:{},
            // 监听订阅者
            listen:function(key,fn){
                // 判断是否含有订阅者,没有则存储订阅者,并添加订阅方法
                ((this.clientList[key]) || (this.clientList[key] = [])).push(fn)
            },
            // 当值发生改变时推送
            trigger: function(){
       
                 // Array.prototype.shift.call(arguments) 取 arguments 中的第一个参数 arguments不是数组,是类数组
                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++];){
                        // 将this 重新绑定到使用者
                          fn.apply(this,arguments)
                    
                    }
                    
            }
        }
                // 数据劫持
        let dataHijack = function({data,key,selector}){
            let value = '',
            el = document.querySelector(selector)
   
            Object.defineProperty(data,key,{
            get: function(){
                 return value
            },
            set:function(val){
                // 更改值
                value = val
                console.log('设置了新值');
                Dep.trigger(key,val)

            }
        })
            // 添加订阅者模式
            Dep.listen(key,function(text){
                     el.innerHTML = text     
            })
        }
                //调用方法
        dataHijack({
               data:dataObj,
               key:'username',
               selector:'.box1'
        })
        dataHijack({
               data:dataObj,
               key:'password',
               selector:'.box2'
        })
      
        // dataObj.password = '臭屁猪'


// 绑定数据

       const username = document.querySelector(".username")
       const password = document.querySelector(".password")

        username.addEventListener("keyup",function(e){
                // console.log(e.target.value);
                dataObj.username = e.target.value
        })
        password.addEventListener("keyup",function(e){
                // console.log(e.target.value);
                dataObj.password = e.target.value
        })

在这里插入图片描述
这样就完成了

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值