淘汰赛订阅范围

Knockout subscribe scope

是否可以更改 Knockout 中的订阅范围?

我有这样的东西:

element =
    {
        type: ko.observable()
        name: ko.observable()
        content: ko.observable()
    }

element.type.subscribe(this._typeChanged.bind(element))

基本上我想访问我订阅的 属性 对象。像我的代码中那样的绑定不起作用,因为它绑定到整个 VeiwModel 而不是对象。

问题在于您创建视图模型的方式。视图模型应该是自包含的,包括对其进行操作的功能。它应该是这样的:

var ViewModel = function() {
    var self = this;
    self.type = ko.observable();
    self.name = ko.observable();
    self.content = ko.observable();
    self.type.subscribe(function(newVal) {
        // here you have access to all the viewmodel properties through self
    });
    return self;
};

这是一个使用 var self=this; pattern.To 的构造函数,使用您需要实例化它的视图模型,即 var vm = new ViewModel()。 (可以省略new)。

当然你也可以定义一个函数,绑定到self,或者在构造函数中接收回调,绑定到self。在这种情况下,函数实现将通过 this 访问视图模型,而不是 self,后者在函数体内是未定义的。

var doSomethignWithVm = function(newVal) {
    // acces viewmodel via this
    // you can also use newVal
};

您修改构造函数以将此作为回调接收:

var ViewModel = function(doSomethingCallback) {
    self.type.subscribe(callback.bind(self));
};

这种模式没有多大意义,因为您的回调应该知道您的视图模型。在这种情况下,将订阅功能直接包含在模型中更有意义。

编辑 注意:正如我在对 Joel Ramos Michaliszen 的回答的评论中提到的,这两个代码是等效的:

self.type.subscribe(callback.bind(self));
self.type.subscribe(callback.bind, self);

您可以通过在文件 knockout/src/subscribales/subscribable.js 中查看 knockout's gitbhubsubscribable 的源代码来检查这一点。如果您寻找订阅实现,您会看到:

subscribe: function (callback, callbackTarget, event) {
    // ...
    boundCallback = callbackTarget ? callback.bind(callbackTarget) : callback;

即如果您提供第二个参数,它用于将第一个参数中传递的函数绑定到它。

也许当你订阅一个 observable 时,你可以传递 2 个参数,第一个是 callback,第二个是scope/context,试试这样:

element.type.subscribe(this._typeChanged, element)

subscribe函数接受三个参数:callback是每当通知发生时调用的函数,target(可选)定义回调函数中this的值,event(可选;默认为"change") 是接收通知的事件的名称。

参考。 http://knockoutjs.com/documentation/observables.html

虽然我知道我可能采用了错误的方法,但我也处于无法对应用程序进行任何重大更改的阶段。

我发现我可以使用 lodash 来帮助我解决这个问题。 我最终使用部分函数将元素附加为订阅回调中的参数:

element.type.subscribe(_.partial(this.typeChanged, element))

或在 coffeescript 中

element.type.subscribe $_.partial @typeChanged, element

现在 chartTypeChanged 在输入上有 2 个参数,而不是一个。