6

<li>タグのクリックイベントに添付する必要があるビューモデルがあります。ここにビューモデルとマークアップがあります

  var viewModel =
    {
        Folders: ['Inbox', 'Archive', 'Sent', 'Spam'],
        SelectedFolder: ko.observable('Inbox'),
        chosenFolderId: ko.observable(),
        navigate: function () {
            self.chosenFolderId(folder);               
        }
    };
ko.applyBindings(viewModel);

そして、マークアップは

   <ul class="nav nav-list bs-docs-sidenav affix" data-bind="foreach:Folders">
                @*<li data-bind="css:{active: $data == chosenFolderId() }">*@
                <li>
                    <a href="#" data-bind="click:navigate">                      
                        <!-- ko text: $data -->
                        <!-- /ko -->
                        <i class="icon-chevron-right"></i>
                    </a>
                </li>                   
            </ul>

問題はこの行にあります

<a href="#" data-bind="click:navigate"> 

<li data-bind="css:{active: $data == chosenFolderId() }">

上記の行は、それぞれNavigate関数とchosenFolderId観測可能に接続されていません。Navigateundefinedと書かれています。selectedFolderId`を解析できません. Same goes for

なぜそれが起こっているのですか?

4

1 に答える 1

14

現在のアプローチにはいくつかの問題があります。

たとえば、「現在のコンテキスト」内でforeach バインディングを使用すると、フォルダー コレクション内のアイテムになります。data-bind="foreach:Folders"ul

したがって、または使用する必要がnavigateあるメソッドにアクセスしたい場合、または「ルート」ビューモデルにアクセスしたい場合 (バインディング コンテキストの詳細を読むことができます):chosenFolderId$parent$root

<ul class="nav nav-list bs-docs-sidenav affix" data-bind="foreach:Folders">
    <li data-bind="css:{active: $data == $parent.chosenFolderId() }">
        <a href="#" data-bind="click: $parent.navigate">                      
            <!-- ko text: $data -->
            <!-- /ko -->
            <i class="icon-chevron-right"></i>
        </a>
    </li>                   
</ul>​

ビューモデルにも問題があります。navigatewhich を使用しようとするような複雑な関数があるself場合は、格納できるオブジェクト リテラルではなく、ビューモデルとして関数を使用する必要がありますthis

var viewModel = function() {
    var self = this;
    self.Folders = ['Inbox', 'Archive', 'Sent', 'Spam'];
    self.SelectedFolder = ko.observable('Inbox');
    self.chosenFolderId = ko.observable();
    self.navigate = function(folder) {
        self.chosenFolderId(folder);
    }
};
ko.applyBindings(new viewModel());​

注意:navigate関数を機能folderさせるにはパラメータが必要であり、Knockout は現在の項目を渡します。

これは動作中の JSFiddleです。

オブジェクト リテラルをビュー モデルとして使用する場合は、そのアプローチを示すJSFiddleをご覧ください。

ただし、2 つのビュー モデルを作成するアプローチの長所と短所を認識しておく必要があります。このSOの質問はそれをうまく要約しています:オブジェクトリテラルと関数として宣言されたノックアウトビューモデルの違い

于 2012-12-19T06:02:05.047 に答える