MVVM架構~使用boxy和knockoutjs實現編輯功能(neng)
這(zhe)個功能我認為非常有用,尤(you)其在(zai)后臺管理系統(tong)中(zhong),它對用戶來說,使用體驗(yan)這(zhe)塊非常不(bu)錯,下面是它的(de)截圖
說在前
在(zai)實現這個功能(neng)(neng)中,我(wo)們對(dui)knockout的基礎知(zhi)識(shi)一定(ding)要(yao)牢(lao)牢(lao)掌握,要(yao)知(zhi)道,在(zai)knockout里一切都(dou)是對(dui)象,并(bing)(bing)且要(yao)知(zhi)識(shi)knockout可以根據DIV進行(xing)綁定(ding),對(dui)于驗(yan)(yan)(yan)證這塊,可以根據你的object進行(xing)驗(yan)(yan)(yan)證,而(er)并(bing)(bing)非只能(neng)(neng)驗(yan)(yan)(yan)證全局對(dui)象,而(er)對(dui)于boxy來說,
要(yao)(yao)知(zhi)道它加載(zai)HTML代(dai)(dai)碼的方(fang)式(如果HTML代(dai)(dai)碼上有knockout綁(bang)定,則需要(yao)(yao)先(xian)將html代(dai)(dai)碼加載(zai)上,然(ran)后(hou)再(zai)綁(bang)定model,這就用到了boxy的回調屬(shu)性afterShow)
做在后
Html代碼
<table class="listTbl"> <thead> <tr> <td width="100"></td> <td>ID</td> <td>姓名</td> <td>電子郵件</td> </tr> </thead> <tbody data-bind="foreach:UserList"> <tr> <td> <a href="javascript:;" data-bind="click:$parent.del">刪除</a> <a href="javascript:;" data-bind="click:$parent.edit">編輯</a> </td> <td data-bind="text:UserInfoID"></td> <td data-bind="text:UserName"></td> <td data-bind="text:Email"></td> </tr> </tbody> </table> <script type="text/html" id="editUserDiv"> <form style="width: 500px;" id="editUser" data-bind="with:selectUser"> <div class="editor-label"> 賬號: </div> <div class="editor-field"> <input type="hidden" name="UserInfoID" data-bind='value: UserInfoID' /> <input name="UserName" data-bind='value: UserName' /> </div> <div class="editor-label"> Email: </div> <div class="editor-field"> <input name="Email" data-bind='value: Email' /> </div> <div class="editor-label"> 手機(ji): </div> <div class="editor-field"> <input name="Phone" data-bind='value: Phone' /> </div> <div class="editor-label"> 密碼: </div> <div class="editor-field"> <input name="Password" data-bind='value: Password' /> </div> <div class="editor-label"> 真實姓(xing)名: </div> <div class="editor-field"> <input name="RealName" data-bind='value: RealName' /> </div> <div style="clear: both;"></div> <p> <input type="button" value="Save" data-bind="click:$parent.save" /> </p> </form> </script>
JS代碼
<script type="text/ecmascript">
function toVal(obj) {
if (typeof obj == "function")
return obj();
else
return obj;
}
var Model = function () {
//properies
var self = this;
ko.validation.configure({//ko.validation相關配置
insertMessages: true//不自動插入錯(cuo)誤消(xiao)息
});
self.UserList = ko.observableArray(@Html.Raw(Json.Encode(Model)));
self.selectUser = ko.observable();
//methods
self.del = function (o) {
Boxy.confirm("are you sure?", function () {
$.post("/ef/DelAjaxPost?userinfoID=" + o.UserInfoID, function (data) {
alert(data == true ? "成功" : "失敗");
self.UserList.remove(o);
});
});
}
self.edit = function (o) {
$(".boxy-wrapper").empty()//關閉之(zhi)前的彈(dan)框
new Boxy($("#editUserDiv").html(), {
afterShow: function () {//彈出框這(zhe)前,綁定數據(ju)到彈框元(yuan)素上
//屬性驗證
o.Phone = ko.observable(toVal(o.Phone)).extend({ required: true });/*先將要驗(yan)證(zheng)(zheng)的字段變成ko對象,并添(tian)加(jia)擴展驗(yan)證(zheng)(zheng)特性*/
o.Email = ko.observable(toVal(o.Email)).extend({ required: true });
o.RealName = ko.observable(toVal(o.RealName)).extend({ required: true });
o.Password = ko.observable(toVal(o.Password)).extend({ required: true });
o.UserName = ko.observable(toVal(o.UserName)).extend({ required: true });
//綁定對象到ko
self.selectUser(o);
//綁定對象到頁面
ko.applyBindings(self, document.getElementById("editUser"));
}, modal: true, title: "提示", closeText: "x"
});
}
self.save = function (o) {
self.errors = ko.validation.group(o);
if (o.isValid()) {
$.post("/EF/EditAjaxPost", $("form").serialize()/*這個方法(fa)必須使input有(you)name屬性(xing),只有(you)id屬性(xing)不行(xing)*/, function (data) {
location.href = "/ef/userlist";
});
} else {
self.errors.showAllMessages();
}
}
}
var M = new Model();
ko.applyBindings(M);
</script>
我(wo)們看在(zai)上(shang)面的代碼,很簡(jian)單(dan),其實我(wo)也是找(zhao)不(bu)少資料,因為開始做的時間出現了很多意想不(bu)到的問題(ti),不(bu)過,慶(qing)幸的是,我(wo)還是把它(ta)解決(jue)了,呵(he)呵(he).
歡迎大家和我一(yi)起(qi)去(qu)學習KnockoutJS,一(yi)起(qi)去(qu)討(tao)論關于MVVM架構(gou)的(de)一(yi)些想法(fa)!