1

I have a class in CS:

class Model
  constructor: (objectParams) ->
    @object = ##object
    ###constructor

  baseObject: => {}
  validate: ko.computed =>
    console.log ko.toJS @object

The problem is with 'validate' it is a prototype property where the binding context of the ko.computed function should be the constructor but instead gets compiled to this:

Model.prototype.validate = ko.computed(function() {
  return console.log(ko.toJS(Model.object));
});

I want it to be binded to the constructor but the fat arrow => seems to be working only this way:

property: () =>

and this way it won't work

  validate: =>
    ko.computed => console.log ko.toJS @object

because ko.computed can't be defined inside a function

how can i solve?

Matteo Pagliazzi
  • 5,140
  • 12
  • 49
  • 83

3 Answers3

1

I think robkuz identified the problem correctly. The solution should be to set the validate property inside the constructor:

class Model
  constructor: (objectParams) ->
    @object = ##object

    @validate = ko.computed =>
      console.log ko.toJS @object
Community
  • 1
  • 1
epidemian
  • 18,817
  • 3
  • 62
  • 71
  • I have put a more generalized version of that question and answer here http://stackoverflow.com/questions/13184209/when-does-the-fat-arrow-bind-to-this-instance/13184211#13184211 – robkuz Nov 01 '12 at 19:34
  • @robkuz I think that what was not evident is that the `validate` property was being set to the return value of `ko.computed` called at the class declaration level instead of inside a class method, therefore binding `@` to the class constructor. Also, i'm not sure if asking a question just to answer it yourself immediately is encouraged in SO. – epidemian Nov 01 '12 at 19:57
  • it wasn't evident you are right - simply because I tried to answer a more generalized question. SO explicitly encourages you to answer your own questions http://blog.stackoverflow.com/2011/07/its-ok-to-ask-and-answer-your-own-questions/ – robkuz Nov 02 '12 at 03:58
1

Binding your function to the instance and "preprocessing" it works like this

pipe = (fn)->
    return ->
        fn.apply(@, arguments)


class A
    foo: pipe -> @bar()
    bar: -> ...

from your pipe function (in your case ko.computed) return another function that wraps your initial function and calls it via .apply.

No need for the fat arrow as your are calling apply with @

robkuz
  • 9,488
  • 5
  • 29
  • 50
0

if you "advise" a function before associating it with a class (the prototype) there will be no binding to the instance that usually happens with using the fat arrow.

class A
    foo: advise => @someMethod()

The intermediary advise function disconnects the CS compiler so that its not clear what you want to do and so that there is no call to

this.foo = __bind(this.foo, this); 

in the constructor.

However if you do use your "advise" function within a method definition then CS will create a closure for you and you will have access to the instance

class A
    foo: ->
         advise => @someMethod()

This will generate

A.prototype.foo = function() {
    var _this = this;
    return advise(function() {
       return _this.someMethod();
    });
};

The important thing here is the definition of "var _this = this;" which than will be used within your inline function definition.

Hope this helps.

robkuz
  • 9,488
  • 5
  • 29
  • 50
  • thanks but the problem is another: ko.computed is a function that accepts as a parameter another function that I want to be binded to the instance. is this possible? – Matteo Pagliazzi Nov 01 '12 at 12:59
  • Here is another Q&A why you are running into this issue. This time negatively formulated: http://stackoverflow.com/questions/13189573/why-doesnt-the-fat-arrow-bind-to-this-when-i-pipe-my-method-definition-thru-an/13189574#13189574 – robkuz Nov 02 '12 at 05:06