I render a collection of backbone models in a list view, where each model has its own listItemView such as.
var els = [];
_.each(this.collection.models, function(model){
var view = new TB_BB.RequestItemView({model : model});
els.push(view.render().el);
});
$('#request-list').append(els);
Each of the ItemsView can be expanded on a click event (where a call to the server is made) such as.
showDetails : function() {
var m = new TB_BB.RequestDetails({id : this.model.get('id')});
var outerthis = this;
m.fetch({success : function() {
var det = new TB_BB.RequestDetailsView({model : m, el : outerthis.el, current : outerthis, template : '#request-expanded-template'});
det.render();
}});
}
So the logic is that this expanded view opens in the el of the current item. You may have noticed that I am passing a reference to the current view (outerthis) this was to avoid me having zombies of this view when closing expanding view.
So in the expanded view we have a ‘hide’ method which should hide the expanded view and show the original element such as (where current is the reference to the non-expanded view).
hideDetails : function() {
$(this.el).empty();
this.options.current.render();
}
I’m pretty sure this is not the best way of doing this – but not sure what would be the best way? In this case there are no zombies when calling the hidedetails (as its referencing the original view). However I am guessing that each time the ‘showDetails’ view is called and closed a new zombie exists? Could anyone enlighten what would be a better way of having expanded views of a list?
I’ve had a similar case in the past where I had to render a tree type structure, with list items opening to show sub-lists and closing again. The way I implemented the solution was to have the something like this as the html structure:
So each list item was rendered with an empty element for the sub view. Then in the click handler I would check if this list-item already has created a view for the sub-list, if yes just show the sub-list element; if not, create sub list view, which renders ajax-loader.gif and call collection.fetch to fetch data.
So my recommendation is to use separate dom elements, create subviews lazily and just hide the dom element when you close something, keeping a reference to the view.