Подтвердить что ты не робот

Нокаут - использование foreach и сортировка вместе

У меня возникли проблемы с объединением привязки foreach с сортировкой. У меня есть список так:

<article data-bind="foreach: widgets">  

Виджеты - это простой obvservable массив:

var widgets= ko.observableArray();

Это работает красиво, давая мне список моих "виджетов". Если я добавлю новый "виджет" в этот список, он будет динамически отображаться в списке посредством привязки данных.

Однако, как только я добавлю сортировку в массив:

<article data-bind="foreach: widgets.sort(function (left, right) { return left.order() == right.order() ? 0 : (left.order() < right.order() ? -1 : 1); })">

Затем новые добавленные виджеты больше не отображаются в моем списке - если я не перезагружу страницу. (Сортировка прекрасно работает на этом этапе - если я обновляю поле "порядок", которое я сортирую, элементы в моем списке динамически пересортируются).

Как я могу заставить сортировку хорошо играть с динамическим обновлением новых элементов в моем наблюдаемом массиве?

Я использую Breezejs для получения моих данных, однако я не думаю, что это влияет на этот сценарий.

4b9b3361

Ответ 1

observableArray.sort возвращает отсортированный базовый ( "обычный" ) массив, а не observableArray, поэтому изменения не отображаются в пользовательском интерфейсе.

Чтобы обновить сортировку и пользовательский интерфейс, вам нужно создать ko.computed, который выполняет сортировку и использует вычисление в вашей привязке. Поскольку ko.computed будет прослушивать изменения widgets и пересчитывать сортировку.

var widgets= ko.observableArray();

var sortedWidgets = ko.computed(function() {
   return widgets().sort(function (left, right) { 
        return left.order() == right.order() ? 
             0 : 
             (left.order() < right.order() ? -1 : 1); 
   });
});

Затем вы можете связать его с:

<article data-bind="foreach: sortedWidgets" />