Skip to content
Nick Nance edited this page Jan 23, 2015 · 6 revisions

Overview

Composer enhances the existing Backbone.View class with a simple API without altering its' existing behavior. To this point there are two significant aspects of the plugin important to understand.

Rendering

Composer provides an implementation of the render function that isn't provided by default in Backbone. Composer mostly provides this implementation as a way to remove boilerplate code. The additional features of the plugin can be used even if you elect to override the provided rendering implementation. However, it is likely you will find the benefits of its render implementation to be useful. The benefits include:

Templating

If you assign a template function to the view, Composer will use the template function to establish the DOM for the view. For example:

Backbone.View.extend({
  template: JST['templates/index.ejs'],
  ...
});

Composer doesn't handle the loading of the template or make any assumptions on how the template is loaded. It does require that the template is defined as a function. It is recommend that you use a template system that is pre-compiled.

Removing the div wrapper

By default Backbone wraps all views with a div tag. This can cause confusion and create unexpected DOM elements. Backbone's solution to this problem requires elements of the template being defined in the view code. In many situations this solution isn't desirable.

This can be avoided by setting the attachToTemplate option to true on a view to automatically attach the outer tag of the view to the top level tag of the template. Keeping all the DOM definition in the template. For example:

Backbone.View.extend({
  template: JST['templates/index.ejs'],
  attachToTemplate: true,
  ...
});

If you want to set this value globally you can do something like this:

Backbone.View.prototype.attachToTemplate = true;

Serializing View Data

In Backbone there are many ways to hidrate a view with data. Composer promotes the use of a serializeData function as good approach to clearly defining the required data structure required by the template.

By implementing a serializeData function in a view, Composer will use the results of this function as the input to the template function. A simple example would be:

Backbone.View.extend({
  serializeData: function() {
    return this.model.toJSON();
  }
});

Rendering hooks

When using the Composer render function the view will fire a rendered event once the view has completed rendering to the DOM and it's sub views are restored.

Also ViewManage will call an onRender function if it is implemented. This allows for a common use case of jquery pluggins that need to be initialized after the template has been rendered. For example:

Backbone.View.extend({
  ...
  onRender: function() {
    this.$('#state').select2();
  }
});

Subviews

Composer provides functions for adding and removing subviews to a parent view to facility life cycle management and restoring the view during rerendering.

One of the more complicated aspects of Backbone is managing the life cycles of views in a way that doesn't cause memory leaks. Composer address this problem with a few basic capabilities:

Adding Subviews

addSubView

The primary way to add subviews to a parent is to call the Composer function this.addSubView with an option object. The view property is the only required property in the option object. All views added via addSubView will automatically be removed from the DOM and removed from memory when the parent view closes. A common use case includes:

showItems: function() {
  this.collection.forEach(function(model){
    var view = new ItemView({model: model});
    this.addSubView({view: view});
  }, this);
}

By calling addSubView with view option it will automatically call render on the view and start tracking it. A shown event will be fired on the subview once it has been added to the parent view DOM.

A selector can be included in the option object to identify where in the parent the new view should be added: a selector, jQuery object, or element.

These location how to place the new view within the selector. Options include: 'prepend', 'before', 'after' or 'append'(default). For example:

var view = new ItemView({model: this.model});
this.addSubView({view: view, selector: '.container', location: 'prepend'});

An onShow function can be implemented on the view to handle any required post processing needed after the view has been added to the parents DOM.

setView

Use setView to replace the entire contents of the view with a new view. This includes removing all views currently contained within the view. The common use case is a container view that has to swap in an entirely new view when the main route changes. A simple example would be:

var container = new Backbone.View({el: '.container'});
var view = new UserView({model: this.model});
container.setView(view);

Calling setView will trigger a 'shown' event.

Removing Subviews

removeSubViews

Use removeSubViews to remove all the subviews of a parent by removing the view from the DOM and releasing the memory.

removeSubViewForModel

Call removeSubViewForModel with a model parameter to remove a subview that has the associated model. This is the most common use case for removing a single view.

view.close

Close can be called on any view and it will be removed from it's parent and removed from the DOM

Life Cycle

There are two key areas to the life cycle of Backbone views. Closing and rendering.

When calling close on a view it will automatically remove all of it's subviews and will also fire a close event. This event is monitored by it's parent so that it will be removed up the view chain.

When a view has subviews and needs to be entirely rerendered, Backbone requires this to be handled manually. Composer provides this management automatically by adding the subview DOM back to the parent DOM before inserting into the document.

Life Cycle Hooks

When using Composer subview functions the view will fire a shown event once the view has added to the parent's DOM. Also ViewManage will call an onShown function if it is implemented.

When a view is closed it will call an onClose function if implemented just before it is removed from the parent. It will also fire a closed event once the view has been completely removed.

When