KO ObservableArray 更新在与 .sort 绑定时中断

KO ObservableArray update breaks when binding with .sort

本文关键字:绑定 定时 中断 sort ObservableArray 更新 KO      更新时间:2023-09-26

我在标记中对我的ObservableArray进行排序,但由于某种原因,当我将一个新对象推送到页面ObservableArray时,这不会更新。

//store.get('pages') returns an ObservableArray
<!-- ko foreach:store.get('pages').sort(function (l , r ) { return l.pageNumber() < r.pageNumber() ? -1 : 1}) -->
    <markup/>
<!--/ko-->

但是,当我删除排序调用时,它可以很好地捕获数组更改。这样

//works fine,  updates when item pushed to observableArray
<!-- ko foreach:store.get('pages') -->
    <markup/>
<!--/ko-->

对简单的解决方法有任何想法吗?

编辑

尝试使用 valueHasMutated(),也不会强制更新。

解决方法: 我最终将排序调用移动到 observableArray 上的订阅中,它现在似乎工作正常,但不知道为什么。

store.get返回一个observableArraystore.get(...).sort(...)返回一个数组。 您实际上是在进行如下所示的单向绑定:

<div data-bind="foreach: ['foo', 'bar']"></div>

此外,尽管您绑定了函数调用的返回值,但对我来说,它有一种代码气味,即您正在将业务逻辑与视图逻辑耦合。 你有这样的东西:

// View
<div data-bind="foreach: $root.get()"></div>
// Javascript
function ViewModel () {
    var self = this;
    self.get = function () {
        return ko.observableArray();
    };
}

它有效,但从你的角度来看,不清楚你在做什么。 我认为更好的解决方案是:

// View
<div data-bind="foreach: stores"></div>
// Javascript
function ViewModel () {
    var self = this;
    self.stores = ko.observableArray();
    self.get = function () {
        var arr = ["foo", "bar"];
        stores(arr.sort(...));// When you do this, KO updates the foreach binding this is bound to
        return stores;// not that you need to, you can access it from the viewModel.
    };
}

很高兴您找到了解决方法,但请花一分钟时间规划您的 HTML 绑定结构。 这是我创建新视图时开始的第一个地方,它决定了我如何构建视图模型。