Backbone is an amazing Model_View_Controller (MVC)-inspired library that handles data (Model/Collection) synchronization with a RESTful server for Object_Relational_Mapping (ORM), page routing, etc. Unfortunately, their Views become complex to maintain when dynamic Model and View synchronization is required (which is why Knockback exists).
// Model earth = new Backbone.Model({first_name: 'Planet', last_name: 'Earth'}) mars = new Backbone.Model({first_name: 'Planet', last_name: 'Mars'}) // Collection planets = new Backbone.Collection([earth, mars])
// Model var earth = new Backbone.Model({first_name: 'Planet', last_name: 'Earth'}); var mars = new Backbone.Model({first_name: 'Planet', last_name: 'Mars'}); // Collection var planets = new Backbone.Collection([earth, mars]);
Router:
class PageRouter extends Backbone.Router routes: "earth": "switchToEarth" // #earth "mars": "switchToMars" // #mars switchToEarth: -> # do something switchToMars: -> # do something # instantiate the router and start listening for URL changes page_router = new PageRouter() Backbone.history.start()
var PageRouter = Backbone.Router.extend({ routes: { "earth": "switchToEarth", // #earth "mars": "switchToMars" // #mars }, switchToEarth: function() { /* do something */ }, switchToMars: function() { /* do something */ } }); // instantiate the router and start listening for URL changes var page_router = new PageRouter() Backbone.history.start()
Knockout follows the Model_View_ViewModel (MVVM) design pattern meaning you specify a ViewModel (Controller) in addition to your data (Model) which encapsulates specific data and logic for your HTML/Template (View).
<div id='ko_basic'> <p>First name: <input class='input-small pull-right' data-bind="value: first_name, valueUpdate: 'keyup'" /></p> <p>Last name: <input class='input-small pull-right' data-bind="value: last_name, valueUpdate: 'keyup'" /></p> <p>Hello, <span data-bind="text: full_name"> </span>!</p> </div>
model = {first_name: "Planet", last_name: "Earth"} ViewModel = (model) -> @first_name = ko.observable(model.first_name) @last_name = ko.observable(model.last_name) @full_name = ko.computed((->return "#{@first_name()} #{@last_name()}"), @) return view_model = new ViewModel(model) ko.applyBindings(view_model, $('#ko_basic')[0])
var ko = kb.ko; var model = {first_name: "Planet", last_name: "Earth"}; var ViewModel = function(model) { this.first_name = ko.observable(model.first_name); this.last_name = ko.observable(model.last_name); this.full_name = ko.computed((function() {return "" + (this.first_name()) + " " + (this.last_name());}), this); }; var view_model = new ViewModel(model); ko.applyBindings(view_model, $('#ko_basic')[0]);
First name:
Last name:
Hello, !
In Knockout.js, ViewModels need to be unique instances so often you use a simple function with 'new' to create an instance to bind. Here are some equivalents:
# Form 1: Simple function-based class ViewModel = (model) -> @first_name = ko.observable(model.first_name) return view_model = new ViewModel({first_name: "Hello"}) # Form 2: CoffeeScript class (allows for inheritance) class ViewModel constructor: (model) -> @first_name = ko.observable(model.first_name) view_model = new ViewModel({first_name: "Hello"})
// Simple function-based class var ViewModel = function(model) { this.first_name = ko.observable(model.first_name); }; var view_model = new ViewModel({first_name: "Hello"});