Skip to content
Branch: master
Go to file

Latest commit


Failed to load latest commit information.
Latest commit message
Commit time

Backbone.js Subviews

Version 0.7.0

Extends Backbone.View with support for nested subviews that can be reused and cleaned up when need be. (helps mitigate ghosted views)


  • Cleanup views when no longer needed
  • Provided access to parent views
  • Add additional methods to help with reusing Views
  • Keeps views uninitialized until needed
  • Propagates model to subviews
  • Listen to models/collections by defining them in a hash
  • And more...

Using Subviews

var MySubview = Backbone.View.extend({
	render: function(){
		console.log(this.parentView.className) // 'my-view'
		console.log(this.viewName) // 'my-subview'
	cleanup: function(){
		console.log('perform cleanup')
		// such as this.stopListening(this.model)

var MyView = Backbone.View.extend({
	className: 'my-view',
	initialize: function(){'my-subview', MySubview).renderTo(this)
	render: function(){
		// render the child view'my-subview').render();
		return this;

When you remove a view, all subviews will be informed and told to cleanup

MyView.remove() // MySubview:'perform cleanup'

You can reuse views too instead of recreating over and over.

var MyListSubivew = Backbone.View.extend({});

var MyListView = Backbone.View.extend({
	render: function(){
		// assuming this view has a collection...
		this.collection.each(this.addOne, this)
		return this;
	addOne: function(model){
		let viewName = 'item-'
		// MyListSubivew will only be initialized once for the given viewName, MyListSubivew)
		// if you data/options are needed upon initialization of the view, you can do This
		//, MyListSubivew, {model: model, another:'option'})

Defining Views

Since creating and appending subviews to a view is a common routine, backbone.subviews provides a way to setup and render them automatically for you.

var View1 = Backbone.View.extend({className: 'v1'});
var View2 = Backbone.View.extend({className: 'v2'});
var BadgeView = Backbone.View.extend({className: 'badge'});
var ViewColl = Backbone.View.extend({className: 'v-coll', tagName: 'ul'});

var RootView = Backbone.View.extend({

	className: 'rootview',
	template: '<h1 class="title">Title</h1>',

	views: {
		'view1': View1,
		'view2': View2,
		'badge': {
			view: BadgeView,
			appendTo: '.title'
		'view-collection': {
			view: ViewColl,
			setModel: function(v, model){
				v.collection = model.get('a-child-collection')


When the RootView is rendered, all the views defined in views will be initialized, appended to RootView and then their render() method called.

This will give us the following DOM structure

<div class="rootview">
	<h1 class="title">Title<div class="badge"></div></h1>
	<div class="v1"></div>
	<div class="v2"></div>
	<ul class="v-coll"></ul>

If you override render you'll need to remember to call renderViews() on your own.

Attaching Listeners to Model/Collections

It is common practice for a view to listen to a model or collection for changes and react accordingly. This can be done by specifying a hash of events like so:

listeners: {
	model: {
		'change': 'render',
		'destroy': 'remove',
		'reset': function(){
			// inline function also supported
	collection: {},
	'name-of-child-collection': {}

// the above is the equivalent of doing this manually
this.listenTo(this.model, 'change', this.render)
this.listenTo(this.model, 'destroy', this.remove)
this.listenTo(this.model, 'rest', function(){})

You'll notice above that Child Collection is supported. The third listener would evaluate to:


Methods & References

There are some useful methods added to Backbone.Views

.sv() or .subview() - save and access subviews

.renderTo() - render and append to a backbone view (or jquery element)

.empty() - clears the view of contents

.inDOM() - whether or not the view is presented in the DOM or just stored in memory

.reRender() - will only render if in the DOM

.renderViews() - init and append (if needed) and then render all defined views (this.views)

.forEachView(callback) - perform an action on all defined views

.renderTemplate() - will take this.template and merge with this.model and append to el. (See backbone.template-data)

.parentView - a reference to the parent view of this child

.parent(viewName, returnPromise=false) - will traverse up parent views until matched view name. Use root to get the top level view. Dot notation is supported for traversing up to a parent and then down to a subview.

.viewName - the name the child is stored under in the parent



  • Defined views:{} will get setModel called upon initialization (if they have it)
  • Model/Collection listeners can be defined and applied automatically


  • collection: this.collection also passed to view upon creation (previously only this.model was given)


  • fix .sv alias not passing opts arg


  • return this in setModel for chainability
  • add renderTo method
  • view arg in .sv() can be uninitialized - the view will only initialize once.
  • defined view in views has setModel option available


  • new .parent(viewName, returnPromise=false) method for traversing up the parent views to the one matching the given name


  • add support for defining and automating subviews on a view


MIT © Kevin Jantzer - Blackstone Publishing


Extends Backbone.View with support for nested subviews that can be reused and cleaned up when need be.




No releases published
You can’t perform that action at this time.