KnockOutJs - Web版的WPF

     从人类不断进化的历程中,我们可以总结出一个规律,那就是分工越来越细。每个人的精力有限,关注的点越集中就能够把一件事情做到极致。程序最开始的时候是面向过程的,后来发现职责不明确,于是一步一步演化成了面向对象。ASP是数据与界面混杂的,ASP.NET 就划分了前后端,但是还不够好,因为处理逻辑不集中,耦合性太改,不便于测试。WPF之所以能取代原来的winform,有人说WPF能够做很多漂亮的界面,这只是很小的一个原因,真正的原因在于WPF做到了很好的界面与逻辑的分离,并且很优雅地做了数据与视图的绑定。

      MVC模式中,视图是可以直接和模型进行交互的,这就给用户体验带了了很大的提升,ASP.NET MVC 中部分视图的使用,能够很好地实现布局刷新的效果,从分页,查询等等各个方面带来优质的用户体验。当我们因为MVC给我们带来的好处欣喜若狂时,我们脑海里产生了一个疑问,我们的WEB应用能不能像WPF一样呢,实现DOM对象与数据的直接绑定呢,这样的话我们就不必再写很多javascript代码去响应DOM的值发生改变的事件,虽然jquery已经非常强大,很多的事情几句话就能搞定。

      这时候KnockOut就横空出世了,它完美地解决了DOM与数据模型绑定的问题。不过这里不得不提一句,Knockout并不是唯一一个实现了MVVM模式的JS库,而且也不是第一个,ExtJs才是第一个实现了MVVM的,ExtJs是重量级(有人说是超重量级)的前端企业级库,但不及Jquery锋利(有一本书叫锋利的Jquery),建议大家阅读。

      今天写了个几个例子,演示了这个变化过程。

 1.传统的数据绑定形式。

<script type="text/javascript">
        $(document).ready(function () {
            function Account(bank, accNo, type, status) {
                var self = this;
                self.bank = bank;
                self.accNo = accNo;
                self.type = type;
                self.status = status;
            };
            var myAcc = new Account("Bank1", "12345678", "Saving", "Active");
            // To add this
            $("#accontBankName").text(myAcc.bank);
            $("#accountNum").text(myAcc.accNo);
            $("#accountType").text(myAcc.type);
            $("#accountStatus").text(myAcc.status);
        });
</script> 

<h2>My Account </h2>
<span>Bank Name:</span><span id="accontBankName"></span>
<br />
<span>Account Number:</span><span id="accountNum"></span>
<br />
<span>Account Type:</span><span id="accountType"></span>
<br />
<span>Status:</span><span id="accountStatus"></span>
效果如下:

这里作为演示,数据是固定的,实际情况下我们会使用jquery发起GET请求从后台去取数据。

2.使用knockOut绑定数据

<script type="text/javascript">

    $(document).ready(function () {
        function Account(bank, accNo, type, status) {
            var self = this;
            self.bank = bank;
            self.accNo = accNo;
            self.type = type;
            self.status = status;
        };
        function AccountViewModel() {
            var self = this;
            self.account = new Account("sbi", "12345678", "Saving", "Active");
        };
        ko.applyBindings(new AccountViewModel());

        //ko.applyBindings(new Account("sbi", "12345678", "Saving", "Active"));

    });
</script>

<h2>My Account </h2>
<span>Bank Name:</span><span id="accontBankName" data-bind="text: account.bank"></span>
<br />
<span>Account Number:</span><span id="accountNum" data-bind="text: account.accNo"></span>
<br />
<span>Account Type:</span><span id="accountType" data-bind="text: account.type"></span>
<br />
<span>Status:</span><span id="accountStatus" data-bind="text: account.status"></span>

效果如下:

这时候我们的UI绑定的是数据对象的某个属性,但是看起来优势不是很明显。看下面的例子!

3.数据改变的绑定

<script type="text/javascript">

    $(document).ready(function () {
        function Account(bank, accNo, type, status) {
            var self = this;
            self.bank = bank;
            self.accNo = accNo;
            self.type = type;
            self.status = ko.observable(status);
        };
        function AccountViewModel() {
            var self = this;
            self.account = new Account("sbi",
                "12345678", "Saving", "Active");
        };
        ko.applyBindings(new AccountViewModel());
    });
</script>   

<h2>My Account </h2>
<span>Bank Name:</span>
<span data-bind="text: account.bank"
      span id="accontBankName"></span>
<br />
<span>Account Number:</span>
<span data-bind="text: account.accNo"
      span id="accountNum"></span>
<br />
<span>Account Type:</span>
<span data-bind="text: account.type"
      span id="accountType"></span>
<br />
<span>Status:</span>
<span data-bind="text: account.status"
        span id="accountStatus"></span>
<p>
    Change Account status
    <input data-bind="value:account.status" />
</p>

效果如下:

这时候我们修改文本框里面的Active值,我们发现状态随之改变!

我们改变文本框的时候,knockout 帮我们去修改了对象的值;那么KNOCKOUT只能做这些吗?显然不是这样的!

4.动态计算

<script type="text/javascript">
    $(document).ready(function() {
        // Here's my data model
        // Here's my data model
        var ViewModel = function (first, last) {
            this.firstName = ko.observable(first);
            this.lastName = ko.observable(last);

            this.fullName = ko.pureComputed(function () {
                // Knockout tracks dependencies automatically. It knows that fullName depends on firstName and lastName, because these get called when evaluating fullName.
                return this.firstName() + " " + this.lastName();
            }, this);
        };

        ko.applyBindings(new ViewModel("Planet", "Earth")); // This makes Knockout get to work
    });
</script>

<p>First name: <input data-bind="value: firstName" /></p>
<p>Last name: <input data-bind="value: lastName" /></p>
<h2>Hello, <span data-bind="text: fullName"> </span>!</h2>

上面输入的值能够立即通过计算显示到下面。

注意:

开发环境VS2013 + KNOCKOUT3 + CHROME

源代码下载:http://download.csdn.net/detail/afandaafandaafanda/8544045

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值