这可能不是完成任务的完全理想的优化方式。我愿意就任何更好的方法提出建议。到目前为止,负载在性能方面运行良好。
我的 knockout 应用程序通过 ajax 加载运行。在绑定(bind)调用中,我有一个嵌套循环,其中包含一个根据设置值更新点的函数。
当我尝试添加新项目时,没有抛出任何错误,但是 UI 没有更新,我似乎无法弄清楚原因。
这是我正在尝试做的事情的 fiddle 。 http://jsfiddle.net/hjchvawr/2/
addCombatant 方法确实有效,但无论出于何种原因,表都不会重新绑定(bind)。可以在输出到控制台的VM json中看到增加的值。
self.addCombatant = function(combatant){
ko.utils.arrayForEach(self.divisions(), function(d){
if(d.name() == combatant.division){
d.combatants().push({name: combatant.name,
ID: combatant.ID,
swords:{points: 0, time:'none', kills: 0}
});
}
console.log(ko.toJSON(self.divisions));
}
)}.bind(this);
编辑:
我应用了下面建议的一些更新并添加了另一个列表进行排序。它绑定(bind)和更新但是,当我添加一名战斗员时,它只绑定(bind)到一个事件并且排序关闭。如果我不能使用 sortDivision(combatants, 'swords'),我该如何进行自动排序?在这个 fiddle ( http://jsfiddle.net/4Lhwerst/2/ ) 中,我希望事件按杀戮排序,然后是时间。是否可以在不创建另一个 observeableArray 的情况下在客户端完成这种多级排序?
最佳答案
这是您表中的 foreach 绑定(bind)。
<!-- ko foreach: $root.sortDivision(combatants, 'swords') -->
sortDivision
定义:
self.sortDivision = function (div, evt) {
return div.sortBy(evt, 'time', 'asc').sortBy(evt, 'kills', 'desc');
};
您的 sortBy
函数创建了一个新的 observableArray
。这与被推送到的 observableArray
不同。
ko.observableArray.fn.sortBy = function (evt, fld, direction) {
var isdesc = direction && direction.toLowerCase() == 'desc';
return ko.observableArray(this.sort(function (a, b) {
a = ko.unwrap(evt ? a[evt][fld]() : a[fld]());
b = ko.unwrap(evt ? b[evt][fld]() : b[fld]());
return (a == b ? 0 : a < b ? -1 : 1) * (isdesc ? -1 : 1);
}));
};
对于重新表示或重新组合数据的事物,您应该使用computed
(或pureComputed
)。将任何数据项存储在一个地方。
关于javascript - 使用嵌套循环更新 ViewModel knockout ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30789523/