In my opinion the problem is with having the view's render method return the view.
Your view probably looks something like this:
var Someview = Backbone.View.extend({
initialize: function () {
this.template = _.template($("#someview-template"));
this.model.on('change', this.render());
},
render: function() {
var html = this.template(this.model);
this.$el.html(html);
return this;
}
});
Then somewhere you have a method that creates the view and attaches it to the DOM.
var $main = $('#main'); //main area in the DOM eg: <div id="main"></div>
$main.append(new Somveview({model: item}).render().$el);
The problem is that render() must be called to gain access to the view's element...
Think about this, when a change is made on the model the view is going to render again.
This means if you want to add any transition effects such as fading or sliding your likely going to add them in the view's render method.
Add some effects into the views render method.
var Someview = Backbone.View.extend({
initialize: function () {
this.template = _.template($("#someview-template"));
this.model.on('change', this.render());
},
render: function() {
var html = this.template(this.model);
this.$el.html(html).hide().slideDown(600);
return this;
}
});
This works, any change to the model will cause the view to render and we will see the slide down effect. But only because the view has already been appended to the DOM!!! THE PROBLEM, we notice that the slideDown effect does not happen on page load. So, as a patch, we duplicate the effect in the place where we are creating the view and appending it to the DOM.
The reason why the effect does not occur on page load is because the effect has already happened before we are appending the view's element to the DOM.
But why duplicate the effect, it makes sense to me to change the view a little.
var Someview = Backbone.View.extend({
initialize: function () {
this.template = _.template($("#someview-template"));
this.model.on('change', this.render());
},
render: function() {
var html = this.template(this.model);
this.$el.html(html);
//no longer returning the views object from the render method.
}
});
Create the view and append it to the DOM
var $main = $('#main'); //main area in the DOM eg: <div id="main"></div>
var someview = new Somveview({model: item}); //create the view
$main.append(someview.$el); // add the view's element to the DOM
someview.render(); // Rendering after we have appended to the DOM !!