1

以下の背後にある論理を理解していません。誰かが私を理解するのを手伝ってくれることを願っています. Web アプリをクリーンアップしていて、次のコード行が見つかりました。アプリは Knockout.js を使用した MVC アプリです。次の構造を持ついくつかのカスタム バインディング セットアップがあります。

var originalBindingInit = ko.bindingHandlers.binding.init;
var originalBindingUpdate = ko.bindingHandlers.binding.update;

ko.bindingHandlers.binding = {
    init: function (element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
        originalBindingInit(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext);

        // Init code here... 
    },

    update: function (element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
        originalBindingUpdate(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext);

        // Update code here...
    }
};

init と update がバインディングの外側の変数に設定され、バインディングの各セクションの最初の行で実行される理由がわかりません。これを行うことでループを作成しているように思えます。

誰でもこれに光を当てることができますか?ノックアウトのドキュメントでカバーされている場合、私はそれを見逃しており、そのことをお詫び申し上げます.

4

1 に答える 1

1

このことを考慮:

var A = 1;
var originalA = A;
A = 2;

このように、A が使用されたすべての場所に新しい価値があり、古いものを引き続き使用できます。JavaScript では関数はオブジェクトなので、同じことができます。古いものを保持し、いくつかの新しい機能で上書きします。

var functionA = function () {};
var originalFunctionA = functionA;
functionA = function () {};

同じ参照がなくなったため、ループは作成されません。古い参照は新しい関数によって上書きされます。完璧な例はあなたの質問にあります。knockoutmethod を持つライブラリがありbindingます。それを拡張するには、ライブラリの元のソースを変更できますが、ライブラリが更新されるたびにそれを行う必要があります。このような変更が必要なほど、維持が難しくなります。

そのため、元のバインディング関数の場所に新しいバインディング関数を記述します。いいですが、完全に変更したくなくて少しだけ拡張したい場合は、最初に行ったすべてを記述する必要があります。すでに書かれているのに、なぜもう一度書くのですか?元の関数を新しい参照にコピーします。

var originalBindingInit = ko.bindingHandlers.binding.init;
var originalBindingUpdate = ko.bindingHandlers.binding.update;

そして、仕事をするために必要なときに呼び出します。

var bindingInit = function () {
    // do sth befeore
    originalBindingInit( someVariable );
    // do sth after
}

いくつかの変数の準備のために拡張機能を最初に配置し、元の関数を呼び出して常に行うことを行うことができます。

var someRoundedVariable = Math.round( someVariable );
originalBindingInit( someRoundedVariable );

Knockout JS では、カスタム バインディング ハンドラーを記述することでこれを行う別の方法があります。そして、元のものを呼び出すより。

ko.bindingHandlers.verifyValue = {
    init: function(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
        // do sth to verify value and than call other binding:
        ko.bindingHandlers.value.init(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext);
    },
    update: function(element, valueAccessor, allBindingsAccessor, viewModel, bindingContext) {
        // The rest of this binding is handled by the default value binding. Pass it on!
        ko.bindingHandlers.value.update(element, newValueAccessor, allBindingsAccessor, viewModel, bindingContext);
    }
};

どちらにも短所と長所があります。View を変更できず、ViewModel だけにアクセスできる場合もあれば、拡張機能なしで元のバインディングが必要ない場合 (またはそのままにしておくのは危険) がある場合もあります。新しいバインディングを作成することをお勧めします。

于 2013-09-04T11:05:40.883 に答える