简体   繁体   English

knockout.js排序的可观察数组

[英]knockout.js sorted observable array

I would like to have an observable array which will sort itself when an object is pushed into it (it would be even better if it would sort itself if any of the values it was using in the comparator function was changed). 我希望有一个可观察的数组,当一个对象被推入它时它将自己排序(如果它在比较器函数中使用的任何值被更改,它会更好地排序)。

Something where you could define the comparator function you want the array to sort on and then every time push was called it would add the pushed objects into the correct place in the array so the array remained sorted, like: 您可以在其中定义希望数组排序的比较器函数,然后每次调用push时,都会将推送的对象添加到数组中的正确位置,以便数组保持排序状态,如:

var sortedArray = ko.sortedObservableArray(
    function (a,b) { return b - a;},
    [1,7,4]
); // sortedArray will be [1,4,7]
sortedArray.push([5,2]); // sortedArray will now be [1,2,4,5,7]

Are there any libraries that will do this for me and if not what is the best way to go about implementing this? 是否有任何库可以为我做这个,如果没有,最好的方法是实现这个?

I ended up creating a sorted observable array by extending knockout observable array: 我最终通过扩展knockout observable数组创建了一个排序的可观察数组:

ko.sortedObservableArray = function (sortComparator, initialValues) {
    if (arguments.length < 2) {
        initialValues = [];
    }
    var result = ko.observableArray(initialValues);
    ko.utils.extend(result, ko.sortedObservableArray.fn);
    delete result.unshift;
    result.sort(sortComparator);
    return result;
};

ko.sortedObservableArray.fn = {
    push: function (values) {
        if (!$.isArray(values)) {
            values = [values];
        }
        var underlyingArray = this.peek();
        this.valueWillMutate();
        underlyingArray.push.apply(underlyingArray, values);
        underlyingArray.sort(this.sortComparator);
        this.valueHasMutated();
    },
    sort: function (sortComparator) {
        var underlyingArray = this.peek();
        this.valueWillMutate();
        this.sortComparator = sortComparator;
        underlyingArray.sort(this.sortComparator);
        this.valueHasMutated();
    },
    reinitialise: function (values) {
        if (!$.isArray(values)) {
            values = [values];
        }
        var underlyingArray = this.peek();
        this.valueWillMutate();
        underlyingArray.splice(0, underlyingArray.length);
        underlyingArray.push.apply(underlyingArray, values);
        underlyingArray.sort(this.sortComparator);
        this.valueHasMutated();
    },
    reverse: function () {
        var underlyingArrayClone = this.peek().slice();
        underlyingArrayClone.reverse();
        return underlyingArrayClone;
    }
};

Which can be used in the following way: 可以通过以下方式使用:

var sortedArray = ko.sortedObservableArray(
    function (a,b) { return a - b;},
    [1,7,4]
); // sortedArray will be [1,4,7]
sortedArray.push([5,2]); // sortedArray will now be [1,2,4,5,7]
sortedArray.sort(function (a,b){
    return b - a;
}); // sortedArray will now be [7,5,4,2,1]
sortedArray.push(6); // sortedArray will now be [7,6,5,4,2,1]

The only problem I have is that when reinitialising the sorted observable array with a new array in the same way you would reinitialise an observable array the sorted observable array isn't being sorted. 我唯一的问题是,当使用新数组重新初始化已排序的可观察数组时,您将重新初始化一个可观察数组,排序的可观察数组不会被排序。 To get around this I have added a reinitialise function on the sorted observable array: 为了解决这个问题,我在已排序的可观察数组上添加了一个重新初始化函数:

var sortedArray = ko.sortedObservableArray(
    function (a,b) { return a - b;},
    [1,7,4]
); // sortedArray will be [1,4,7]

sortedArray([3,2,8]); // this doesn't work correctly, sortedArray will be [3,2,8]
// instead of [2,3,8]

// To get around this you can use reinitialise()
sortedArray.reinitialise([3,2,8]); // sortedArray will be [2,3,8]

Try this: 试试这个:

var sortedArray = ko.observableArray();
sortedArray.subscribe(function () {
    if (!sortedArray._isSorting) {
        sortedArray._isSorting = true;
        sortedArray.sort(function (a, b) { return b - a; });
        sortedArray._isSorting = false;
    }
});

You can wrap this up in a function to create new sorted observable arrays whenever you want. 您可以将其包装在函数中,以便随时创建新的已排序可观察数组。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM