Deeptechtons
Deeptechtons

Reputation: 11125

BackboneJs - Should model or Collection have knowledge of view

In one of the example i picked from SO answers here and many BackBoneJs examples i see that the initialize function knows which view the model is going to be rendered with. I don't know i am kind of biased now, is this a good practice or it depends on type of application being developed.

Example

http://jsfiddle.net/thomas/Yqk5A/

Edited Fiddle

http://jsfiddle.net/Yqk5A/187/

Code Reference

FriendList = Backbone.Collection.extend({
    initialize: function(){
        this.bind("add", function( model ){
            alert("hey");
            view.render( model );
        })
    }
});

Is the above a good practice or below

var friendslist = new FriendList;
var view = new FriendView({el: 'body'});
friendslist.bind("add", function( model ){
            alert("hey" + model.get("name"));
            view.render( model );
        })

in the edited fiddle collection is rendered by a view, and we also can use many more views to render the collection.

Upvotes: 2

Views: 179

Answers (2)

timDunham
timDunham

Reputation: 3318

I don't think the collection should know about the view that is used to render it. I know in my projects, the same collection is render in multiple ways so that approach would deteriorate rapidly.

In general I pass the collection to the view that renders the collection and the view will listen to add/remove/update events of the collection to render the elements. The collection view will have knowledge of the child view.

Check out the following link (3rd blog in a series) and in particular the UpdatingCollectionView. This is the approach that I've found useful.

http://liquidmedia.ca/blog/2011/02/backbone-js-part-3/

Upvotes: 1

Sander
Sander

Reputation: 13431

I am all for using events, I myself don't want to move the bind's outside the model, I'd keep them there like the original example

var app = {};
app.evt = _.extend({}, Backbone.Events);  // adding a global event aggregator 

FriendList = Backbone.Collection.extend({
    initialize: function(){
        this.bind("add", function( model ){
            alert("hey");
            app.evt.trigger('addfriend', model);
        })
    }
});

//further in your code you can bind to that event
app.evt.bind("addfriend", function(model){
    var view = new FriendView({el: 'body'});
    view.render(model);
});

however, i find the example a bit weird, creating a new view, with body as element, and rendering it with giving a model to the render function. i'd find it more logic if the view is created with a model as attribute, and then rendering the content into the body. but thats another subject all together.

in short, i move creating the view outside, listening to an event being triggered, but the bind on the collection stays in the collection code. i find it more managable to keep all the collection code at the same place.

Upvotes: 2

Related Questions