I'm getting the error:
Uncaught TypeError: Cannot read property 'constructor' of undefined
When declaring the following class:
class ViewHelpers extends Backbone.Events
I can use the same syntax to extend Backbone.Router, Views, Model etc. Here is the compiled javascript which I wrote in a quick log to make sure Backbone.Events was there
__t('views').ViewHelpers = (function(_super) {
#how i know it is definied here
console.log(_super.trigger)
__extends(ViewHelpers, _super);
function ViewHelpers() {
return ViewHelpers.__super__.constructor.apply(this, arguments);
}
return ViewHelpers;
})(Backbone.Events);
So the line causing the error is
ViewHelpers.__super__.constructor.apply(this, arguments);
What is different about __extends() method that it would work for Backbone.View and not Backbone.Events?
That's because Backbone.Events is not a "class", so it cannot be extended, it's a "module" that can be mixed-in into other objects (see docs here). In JavaScript terms that means that it's not a Function, that can be called as a constructor (i.e. new Backbone.Events will throw an error), it's just a plain JS object whose properties (methods) can be assigned to other objects to make them event dispatchers.
In CoffeeScript, you can mix-in the Backbone.Events into your objects when they are created:
class ViewHelpers
constructor: ->
_.extend @, Backbone.Events
Or you can just extend the class' prototype and avoid having those methods as (own) properties of all ViewHelpers instances:
class ViewHelpers
_.extend @prototype, Backbone.Events
These two approaches should work and let you instantiate and use ViewHelpers as event dispatchers:
vh = new ViewHelpers
vh.on 'foo', -> alert 'bar'
vh.trigger 'foo'
There's another way (from what @epidemian answered), which doesn't involve copying Backbone.Events into a new object to use as your prototype - instead, use Object.create to create a new object to use as your prototype, using Backbone.Events as its prototype.
class ViewHelpers
@prototype = Object.create(Backbone.Events)
Now ViewHelpers' prototype is a new, empty object whose prototype is Backbone.Events. You can define methods on ViewHelpers' prototype without affecting Backbone.Events, but all the Backbone.Events methods are still available to ViewHelpers, without having to copy them into a new object. This not only saves (a miniscule amount of) memory, but if you ended up adding on to Backbone.Events later, all ViewHelperss would see the change.
For this, you'll need either a browser that has ES5's Object.create function, or an Object.create polyfill.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With