1

モデル内のデータを更新するとき、並べ替え順序を維持することは可能ですか (最後に jsfiddle)? 次のマークアップがあります。

<table>
  <thead>
    <tr>
      <th data-bind="sort: { arr: Records, prop: 'Name' }">Name</th>
      <th data-bind="sort: { arr: Records, prop: 'Number' }">Number</th>
      <th data-bind="sort: { arr: Records, prop: 'Desc' }">Description</th>
    </tr>
  </thead>
  <tbody data-bind="foreach: Records">
    <tr>
      <td data-bind="text: Name"></td>
      <td data-bind="text: Number"></td>
      <td data-bind="text: Desc"></td>
    </tr>
  </tbody>
</table>
<button data-bind="click: changeMe">Remove</button>
<button data-bind="click: resetMe">Reset</button>

現在、ソート自体はbindingHandlers、この元の投稿を使用して実装されています。

var recs = [];

ko.bindingHandlers.sort = {
    init: function(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
        var asc = false;
        element.style.cursor = 'pointer';

        element.onclick = function(){
            var value = valueAccessor();
            var prop = value.prop;
            var data = value.arr;

            asc = !asc;
            if(asc){
                data.sort(function(left, right){
                    return left[prop] == right[prop] ? 0 : left[prop] < right[prop] ? -1 : 1;
                });
            } else {
                data.sort(function(left, right){
                    return left[prop] == right[prop] ? 0 : left[prop] > right[prop] ? -1 : 1;
                });
            }
        }
    }
};

function ViewModel(){
  var self = this;
  self.Records = ko.observableArray();

    self.changeMe = function() {
        self.Records.pop()
    }

    self.resetMe = function() {
        var recs = []
        recs.push({Name: 'Bob', Number: 1, Desc: 'I am awesome'});
        recs.push({Name: 'Joe', Number: 2, Desc: 'Another description'});
        recs.push({Name: 'Mitch', Number: 3, Desc: 'Something'});
        recs.push({Name: 'Steven', Number: 4, Desc: 'Yo'});
        self.Records(recs);   
    }
}

var viewModel = new ViewModel();
recs.push({Name: 'Bob', Number: 1, Desc: 'I am awesome'});
recs.push({Name: 'Joe', Number: 2, Desc: 'Another description'});
recs.push({Name: 'Mitch', Number: 3, Desc: 'Something'});
recs.push({Name: 'Steven', Number: 4, Desc: 'Yo'});
recs.push({Name: 'Robin', Number: 6, Desc: 'Hello'});
recs.push({Name: 'Batman', Number: 7, Desc: 'Description'});
recs.push({Name: 'John', Number: 5, Desc: 'Ok'});
viewModel.Records(recs);
ko.applyBindings(viewModel);

たとえば、このJSFiddleと次の一連の相互作用について考えてみましょう。

  • 列をクリックして、行がその列でソートされるようにします。「数値」を2回クリックすると、降順にソートされます。
  • ここで、[リセット] をクリックして ajax 呼び出しをシミュレートします (つまり、モデルを更新しているとします)。これで、ソート順が元に戻りました。

ソート順を保持するにはどうすればよいですか。つまり、「番号」で降順でソートする必要があることを覚えていますか? もちろん、これを何らかの方法で列の横に表示しますか? datatablesのやり方に似ています (各列名の横にある上下の矢印に注目してください)。

助言がありますか?

4

1 に答える 1

0

試してみましたが、もっと良い方法があるはずです。

ポイントは、「dataUpdated」フラグを作成したことです。そのため、データが更新されるたびに、それらを再度並べ替えます。また、私は観察可能なオブジェクトに「小道具」と「順序」を保持しているので、それらが変更されたときに何かを行うこともできます(たとえば、矢印アイコンを持ち、順序に従って変更します)

見てみな

--> http://jsfiddle.net/blackjim/xgEdg/15/

var recs = [];
ko.bindingHandlers.changed = {
    update: function(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {

        if(viewModel.dataUpdated()){
            console.log('data updated, sorting...');
            sortThis(viewModel.Records,viewModel.sortData().order,viewModel.sortData().col);
        }
        viewModel.dataUpdated(false);
    }
}

ko.bindingHandlers.sort = {
    init: function (element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
        var order = 'none';    //    initial order status for this column

        if(!viewModel.Records.dataSort){
            viewModel.Records.dataSort = { col: 'none', order: 'none' };
        }

        element.style.cursor = 'pointer';
        element.sortAsc = element.sortAsc || false;

        element.onclick = function () {
            var value = valueAccessor(),
                prop = value.prop,
                data = value.arr;

            // sortData updated
            viewModel.sortData({
                col: prop,
                order: order = (order === 'asc' ? 'desc' : 'asc')
            });

            sortThis(data, order, prop);
        }
    }
};

//    function for sorting the observable array
function sortThis(data, order, prop){

    if (order === 'asc') {
        data.sort(function (left, right) {
            return left[prop] == right[prop] ? 0 : left[prop] < right[prop] ? -1 : 1;
        });
    } else {
        data.sort(function (left, right) {
            return left[prop] == right[prop] ? 0 : left[prop] > right[prop] ? -1 : 1;
        });
    }
}

function ViewModel() {
    var self = this;

    self.Records = ko.observableArray();
    self.sortData = ko.observable({
        col: "none",
        order: "none"
    });
    self.dataUpdated = ko.observable(false);    //    flag for data updating

    self.changeMe = function () {
        self.Records.pop();
    }

    self.resetMe = function () {

        self.Records.removeAll();
        self.Records.push({
            Name: 'Bob',
            Number: 1,
            Desc: 'I am awesome'
        });
        self.Records.push({
            Name: 'Joe',
            Number: 2,
            Desc: 'Another description'
        });
        self.Records.push({
            Name: 'Mitch',
            Number: 3,
            Desc: 'Something'
        });
        self.Records.push({
            Name: 'Steven',
            Number: 4,
            Desc: 'Yo'
        });
        //    trigger the dataUpdated 'event'
        self.dataUpdated(true);

    }
}

var viewModel = new ViewModel();

recs.push({
    Name: 'Bob',
    Number: 1,
    Desc: 'I am awesome'
});
recs.push({
    Name: 'Joe',
    Number: 2,
    Desc: 'Another description'
});
recs.push({
    Name: 'Mitch',
    Number: 3,
    Desc: 'Something'
});
recs.push({
    Name: 'Steven',
    Number: 4,
    Desc: 'Yo'
});
recs.push({
    Name: 'Robin',
    Number: 6,
    Desc: 'Hello'
});
recs.push({
    Name: 'Batman',
    Number: 7,
    Desc: 'Description'
});
recs.push({
    Name: 'John',
    Number: 5,
    Desc: 'Ok'
});
viewModel.Records(recs);
ko.applyBindings(viewModel);
于 2013-06-22T10:05:09.957 に答える