2

ノックアウト マッピング プラグインのドキュメントには、「「キー」を使用してオブジェクトを一意に識別する」というタイトルのセクションがあります。これは、部分的に変更されたオブジェクトのすべてのプロパティの表示を完全に置き換えるのではなく、オブジェクトの一部を更新し、表示のその部分のみを更新する方法を説明しています。私の質問をより明確にするために、ここで少し変更した単純な例では、すべてが見事に機能します。私の変更は次のとおりでした:

  1. 2 秒後にオブジェクトを正しい名前に置き換えます。

  2. 表示の変更されていない部分を強調表示すると、更新が行われたときに実際に置き換えられていないことがわかります。

1. シンプルなオブジェクト( jsFiddle )

<h1 data-bind="text: name"></h1>
<ul data-bind="foreach: children">
    <li><span class="id" data-bind="text: id"></span> <span data-bind="text: name"></span></li>
</ul>

<script>
var data = {
    name: 'Scot',
    children: [
        {id : 1, name : 'Alicw'}
    ]
};
var mapping = {
    children: {
        key: function(data) {
            console.log(data);
            return ko.utils.unwrapObservable(data.id);
        }
    }
};
var viewModel = ko.mapping.fromJS(data, mapping);
ko.applyBindings(viewModel);

var range = document.createRange();
range.selectNode(document.getElementsByClassName("id")[0]);
window.getSelection().addRange(range);

setTimeout(function () {
    var data = {
        name: 'Scott',
        children: [
            {id : 1, name : 'Alice'}
        ]
    };
    ko.mapping.fromJS(data, viewModel);
}, 2000);
</script>

しかし、より複雑なネストされたデータ構造に対して同じ動作を実現する方法は明確ではありません。次の例では、上記のコードを使用して、データをリストにラップしています。これを上記と同じように動作させたいのですが、そうではありません。1 つのプロパティが変更されたため、表示全体がやり直されます。これは、上記の例とは異なり、データが更新された後に強調表示が失われるためです。

2. より複雑なネストされたオブジェクト( jsFiddle )

<!-- ko foreach: parents -->
    <h1 data-bind="text: name"></h1>
    <ul data-bind="foreach: children">
        <li><span class="id" data-bind="text: id"></span> <span data-bind="text: name"></span></li>
    </ul>
<!-- /ko -->

<script>
var data = {
    parents: [
        {
            name: 'Scot',
            children: [
                {id : 1, name : 'Alicw'}
            ]
        }
    ]
};
var mapping = {
    children: {
        key: function(data) {
            console.log(data);
            return ko.utils.unwrapObservable(data.id);
        }
    }
};
var viewModel = ko.mapping.fromJS(data, mapping);
ko.applyBindings(viewModel);

var range = document.createRange();
range.selectNode(document.getElementsByClassName("id")[0]);
window.getSelection().addRange(range);

setTimeout(function () {
    var data = {
        parents: [
            {
                name: 'Scott',
                children: [
                    {id : 1, name : 'Alice'}
                ]
            }
        ]
    };
    ko.mapping.fromJS(data, viewModel);
}, 2000);
</script>

つまり、基本的に私が求めているのは、よりネストされたデータ構造を考慮して、2 番目の例を最初の例のように機能させるにはどうすればよいかということです。ID は子ごとに一意であると想定できます (したがって、Scott 以外に別の親を追加した場合、その子は id=2 で始まるなど)。

4

1 に答える 1

2

そこでの興味深い観察と素晴らしい記事。親と子にキーを定義すると機能するようです。このフィドルを試してください:

http://jsfiddle.net/8QJe7/6/

親コンストラクターが子マッピングを行う、親と子のインスタンス化可能なビュー モデル関数を定義します。

于 2012-08-19T22:34:57.740 に答える