Knockout.js(二):监控数组属性(Observables Arrays)
如果想发现并响应一个对象的变化,就应该使用监控属性(observables),如果想发现并响应一个集合的变化,就需要使用监控属性数组(observableArray)。在很多情况下,它都非常有用,比如你要在UI上需要显示/编辑的一个列表数据集合,然后对集合进行添加和删除。
声明ObservableArray
var myObservableArray = ko.observableArray(); myObservableArray.push("some value");
将一个对象放在observableArray里不会使这个对象本身的属性变化可监控,observable只会监控它拥有的对象,并在这些对象添加或删除的时候发出通知。
如果想在初始化数组的时候给其赋初值,可以在构造器里加入这些初始对象。
var anotherObservableArray = ko.observableArray([ {name: "Bungle", type: "Bear" }, {name: "George", type: "Hippo" }, {name: "Zippy", type: "Unknown" } ]);
一个observableArray其实就是一个observable的监控对象,只不过他的值是一个数组,可以用JavaScript的数组函数进行数组的访问:
alert('The length of the array is ' + myObservableArray().length); //The length of the array is 1 alert('The first element is ' + myObservableArray()[0]); //The first element is some value alert('The length of the array is ' + anotherObservableArray().length); //The length of the array is 3 alert('The first element is ' + anotherObservableArray()[0]); //The first element is [object Object]
ObservableArray的常用方法
可以观察到上面访问数组的时候,使用的是JavaScript的函数,但KO提供了更好的功能等价函数,有以下优点:
♦ 兼容所有浏览器。
♦ 在数组操作函数方面(如push和splice等),KO可以自动触发依赖跟踪,并通知所有的订阅者它的变化,然后让UI界面相应地自动更新。
♦ 语法更方便(如myObservableArray.push(...)比myObservableArray().push(...)来的方便吧??)
1.indexOf()
myObservableArray.indexOf('Blah'):返回以0为第一个索引的第一个Blah的匹配项的索引
2.slice()
myObservableArray.slice(...):返回给定的从开始索引到结束索引之间所有的对象集合
3.push()
myObservableArray.push(‘some new value’):在数组末尾添加一个新项
4.pop()
myObservableArray.pop():删除数组最后一项并返回返回该项
5.unshift()
myObservableArray.unshift(‘some new value’):在数组头部添加一个项
6.shift()
myObservableArray.shift():删除数组头部第一项并返回该项
7.reverse()
myObservableArray.reverse():翻转整个数组的顺序
8.sort()
myObservableArray.sort():给数组排序
9.splice()
myObservableArray.splice(1,3):删除指定开始索引"1"和指定数目"3"的数组对象元素(第2,3,4个元素)。
10.remove和removeAll
myObservableArray.remove(someItem); // 删除所有等于someItem的元素并将被删除元素作为一个数组返回
myObservableArray.remove(function(item) { return item.age < 18 }); // 删除所有age属性小于18的元素并将被删除元素作为一个数组返回
myObservableArray.removeAll(['Chad', 132, undefined]); // 删除所有等于'Chad', 123, or undefined的元素并将被删除元素作为一个数组返回
11.destroy和destroyAll
myObservableArray.destroy(someItem) 找出所有等于someItem的元素并给他们添加一个属性_destroy,并赋值为true
myObservableArray.destroy(function(someItem) { return someItem.age < 18 }) 找出所有age属性小于18的元素并给他们添加一个属性_destroy,并赋值为true
myObservableArray.destroyAll(['Chad', 132, undefined]) 找出所有等于'Chad', 123, 或undefined 的元素并给他们添加一个属性_destroy,并赋值为true
在KO render一个foreach模板的时候,会自动隐藏带有_destroy属性并且值为true的元素。
所以如果你的"delete”按钮调用destroy(someItem) 方法的话,UI界面上的相对应的元素将自动隐藏,然后等你提交这个JSON对象到Rails上的时候,这个元素项将从数据库删除(同时其它的元素项将正常的插入或者更新)。