Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Extending a custom Backbone.Marionette view. How to implicitly incur prototype's events/onRender?

I have a view:

var MultiSelectCompositeView = Backbone.Marionette.CompositeView.extend({

    events: {
        'click .listItem': 'setSelectedOnClick'
    },

    onRender: function () {
        console.log("MultiSelectCompositeView onRender has executed.");
    }
});

and I have another view which extends MultiSelectCompositeView:

var VideoSearchView = MultiSelectCompositeView.extend({

    events: _.extend(MultiSelectCompositeView.prototype.events, {
        'input @ui.searchInput': 'showVideoSuggestions',
        'click button#hideVideoSearch': 'destroyModel',
        'contextmenu @ui.videoSearchResults': 'showContextMenu'
    },

    onRender: function () {

        this.ui.playlistActions.append((new PlaySelectedButtonView()).render().el);
        this.ui.playlistActions.append((new SaveSelectedButtonView()).render().el);

        //  TODO: Is there a better way to do this?
        MultiSelectCompositeView.prototype.onRender.call(this, arguments);
    }
});

I'm unhappy with the fact that VideoSearchView doesn't implicitly extend the events of MultiSelectCompositeView and that VideoSearchView has to manually call MultiSelectCompositeView's onRender method.

Is there something with Backbone.Marionette which would allow me to extend my custom view in a more seamless fashion?

like image 767
Sean Anderson Avatar asked Feb 14 '23 22:02

Sean Anderson


1 Answers

You have done two things here in the wrong way.

First. Do not change the prototype of the MultiSelectCompositeView, just create and use a new object:

events : _.extend({}, MultiSelectCompositeView.prototype.events, {
  'input @ui.searchInput' : 'showVideoSuggestions'
  // ...
})

Second. Execute super method with proper arguments (using apply not call):

onRender : function () {
  // ...
  MultiSelectCompositeView.prototype.onRender.apply(this, arguments);
}

Or you can use "shortcut":

var superProto = MultiSelectCompositeView.prototype;
var VideoSearchView = MultiSelectCompositeView.extend({

  onRender : function () {
    // ...
    superProto.onRender.apply(this, arguments);
  }

});

See also - Super in Backbone.

like image 158
Vitalii Petrychuk Avatar answered Feb 17 '23 08:02

Vitalii Petrychuk