Skip to content

Instantly share code, notes, and snippets.

@alejandroiglesias
Created August 14, 2012 19:05
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save alejandroiglesias/3351782 to your computer and use it in GitHub Desktop.
Save alejandroiglesias/3351782 to your computer and use it in GitHub Desktop.
(function( window ) {
'use strict';
_.templateSettings = {
interpolate: /\{\{(.+?)\}\}/g,
escape: /\{\{\{(.+?)\}\}\}/g
};
/*****************************
* EXTENSIONS
******************************/
Backbone.View.prototype.close = function () {
if (this.beforeClose) {
this.beforeClose();
}
this.remove();
this.unbind();
};
/*****************************
* APPLICATION
******************************/
var App = Backbone.Router.extend({
routes: {
'': 'list',
'wines/new': 'newWine',
'wines/:id': 'wineDetails'
},
list: function () {
var self = this;
this.wineList = new App.WineCollection();
this.wineList.fetch({
success: function () {
self.wineListView = new App.WineListView({ model: self.wineList });
self.showView('#sidebar', self.wineListView);
if (self.requestedId) {
self.wineDetails(self.requestedId);
}
}
});
},
wineDetails: function (id) {
if ( ! this.wineList) {
this.requestedId = id;
this.list();
return;
}
this.wine = this.wineList.get(id);
if (this.wineView) {
this.wineView.close();
}
this.wineView = new App.WineView({ model: this.wine });
this.showView('#content', this.wineView);
},
newWine: function () {
if ( ! this.wineList) {
this.list();
}
if (this.wineView) {
this.wineView.close();
}
this.wineView = new App.WineView({ model: new App.Wine() });
this.showView('#content', this.wineView);
},
showView: function (containerSelector, view) {
if (this.currentView) {
this.currentView.close();
}
$(containerSelector).html(view.render().el);
this.currentView = view;
return view;
},
// Initializes Backbone boilerplate.
initialize: function () {
Backbone.history.start();
this.showView('#header', new App.HeaderView());
}
});
/*****************************
* MODELS
******************************/
App.Wine = Backbone.Model.extend({
urlRoot: 'api/wines',
defaults: {
id: null,
name: '',
grapes: '',
country: 'Argentina',
region: '',
year: '',
description: '',
picture: ''
}
});
App.WineCollection = Backbone.Collection.extend({
model: App.Wine,
url: 'api/wines'
});
/*****************************
* VIEWS
******************************/
App.WineListView = Backbone.View.extend({
tagName: 'ul',
initialize: function () {
var self = this;
this.model.bind('reset', this.render, this);
this.model.bind('add', function (wine) {
self.$el.append(new App.WineListItemView({ model: wine }).render().el);
});
},
render: function (eventName) {
_.each(this.model.models, function (wine) {
this.$el.append(new App.WineListItemView({ model: wine }).render().el);
}, this);
return this;
}
});
App.WineListItemView = Backbone.View.extend({
tagName: 'li',
template: _.template($('#tpl-wine-list-item').html()),
initialize: function () {
this.model.bind('change', this.render, this);
this.model.bind('destroy', this.close, this);
},
render: function (eventName) {
this.$el.html(this.template(this.model.toJSON()));
return this;
}
});
App.WineView = Backbone.View.extend({
template: _.template($('#tpl-wine-details').html()),
initialize: function () {
this.model.bind('change', this.render, this);
},
render: function (eventName) {
this.$el.html(this.template(this.model.toJSON()));
return this;
},
events: {
'change input': 'change',
'click .save': 'saveWine',
'click .delete': 'deleteWine'
},
change: function (event) {
var target = event.target;
console.log('changing ' + target.id + ' from: ' + target.defaultValue + ' to: ' + target.value);
},
saveWine: function (event) {
event.preventDefault();
this.model.set({
name: $('#name').val(),
grapes: $('#grapes').val(),
country: $('#country').val(),
region: $('#region').val(),
year: $('#year').val(),
description: $('#description').val()
});
if (this.model.isNew()) {
var self = this;
app.wineList.create(this.model, {
success: function () {
app.navigate('wines/' + self.model.id, false);
}
});
}
else {
this.model.save();
}
},
deleteWine: function (event) {
event.preventDefault();
this.model.destroy({
success: function () {
alert('Wine deleted successfully');
window.history.back();
}
});
}
});
App.HeaderView = Backbone.View.extend({
template: _.template($('#tpl-header').html()),
render: function (eventName) {
this.$el.html(this.template());
return this;
},
events: {
'click .new': 'newWine'
},
newWine: function (event) {
event.preventDefault();
app.navigate('wines/new', true);
}
});
window.app = new App();
})( window );
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment