国产探花免费观看_亚洲丰满少妇自慰呻吟_97日韩有码在线_资源在线日韩欧美_一区二区精品毛片,辰东完美世界有声小说,欢乐颂第一季,yy玄幻小说排行榜完本

首頁 > 編程 > JavaScript > 正文

mvvm雙向綁定機制的原理和實現代碼(推薦)

2019-11-20 09:45:51
字體:
來源:轉載
供稿:網友

mvvm框架的雙向綁定,即當對象改變時,自動改變相關的dom元素的值,反之,當dom元素改變時,能自動更新對象的值,當然dom元素一般是指可輸出的input元素。

1. 首先實現單向綁定,在指定對象的屬性值發生改變時觸發callback函數。

2. 單向綁定可采用ES5新增的defineProperty實現(或defineProperties),用了ES5注定就不支持IE9以下了,為了防止遞歸死循環問題,原有屬性需要剪切到一個私有屬性中保存。

3. 循環調用defineProperty定義閉包時產生作用域的問題,為解決作用域變量對象的值會取到最后一次運行值問題,多定義一層立即調用的閉包函數將值傳入。

4. 我們定義getFN和setFN函數用于在屬性get和set的時候觸發,它的功能是對私有屬性__private的讀寫并觸發回調函數通知UI層更新界面。

5.單向綁定實現完成后,實現反向的綁定,即UI層onchange之后觸發更新數據,這個相對比較容易,在dom中通過自定義屬性bindKey關聯model的值變化,監聽使用oninput事件,相比onchange的好處是可以實時變化不用等失焦,而且對右鍵粘貼、菜單粘貼,拖動文字進文本框等方式都可以觸發,完全無死角,缺點是只支持IE9以上,但是在IE9以下有等價的onpropertychange可以用還是能兼容的。

6.總結,雙向綁定的原理并不復雜,整體代碼不超過50行,非常精簡,不過還是有一些技術含量,下面是完整的代碼,如果不想使用龐大的框架,可以用一下。ie9以下是不支持的,如要支持ie9以下可以使用avalon,它用vbs做了get,set存取器的封裝,這點還是比較強大的。

html:

<div id="container">  <p>  name:<input type="text" bindkey="userName">  </p>  <p>  age:<input type="text" bindkey="age">  </p><div>

js:

<script type="text/javascript">  window.Model={    userName:"windy",    age:34,    skill:["javascript","html","css","jquery","node"],      }  function bindingModel(model,changeCallback){    var propertiesMap={};    model.__private={};    function getFn(name){      var result=this.__private[name]      console.log("get value:"+name+"="+ result);      return result;    };    function setFn(name,val){      if(this.__private[name]!=val){        console.log("set value:"+name+"="+val);               this.__private[name]=val;        if(changeCallback){          changeCallback(name,val);        }      }    };    for(elem in model){      if(model.hasOwnProperty(elem) && elem!="__private" && typeof(model[elem])!="function"){        (function(propName,propValue){          model.__private[propName]=propValue;// init value          propertiesMap[propName]={            get:function(){ return getFn.call(this,propName)},            set:function(v){ return setFn.call(this,propName,v)},            //value:model[elem],            //writable: true,            enumerable: true,            configurable: true          }        })(elem,model[elem]);      }    }    Object.defineProperties(model,propertiesMap)      }  function bindingBoth(model,dom){    dom.find("[bindkey]").each(function(item){      var key=$(this).attr("bindkey");      $(this).val(model[key]);      $(this).bind("input",function(){        model[key]=$(this).val();      })    });    bindingModel(model,function(name,val){      var el=dom.find("[bindkey="+name+"]");      if(el.val()!=val){        el.val(val);      }          });  }  bindingBoth(window.Model,$("#container"))  </script>

以上這篇mvvm雙向綁定機制的原理和實現代碼(推薦)就是小編分享給大家的全部內容了,希望能給大家一個參考,也希望大家多多支持武林網。

發表評論 共有條評論
用戶名: 密碼:
驗證碼: 匿名發表
主站蜘蛛池模板: 肥城市| 富民县| 江阴市| 中阳县| 聂荣县| 科尔| 逊克县| 泽库县| 富平县| 华蓥市| 锡林郭勒盟| 杭锦旗| 靖西县| 共和县| 新和县| 怀柔区| 博野县| 平顺县| 北宁市| 新巴尔虎左旗| 共和县| 信宜市| 奈曼旗| 剑河县| 剑河县| 丽水市| 中西区| 湛江市| 麦盖提县| 梓潼县| 宁陵县| 浪卡子县| 天台县| 垫江县| 关岭| 思茅市| 遂平县| 宜丰县| 乡宁县| 左权县| 郓城县|