New Dogs, Old Tricks (Or: Dojo Already Did That)

New Dogs, Old Tricks (Or: Dojo Already Did That)

Backbone may be the current app development hotness, and its tiny size and focused mission stand in stark contrast to the more comprehensive philosophy of the Dojo toolkit, but developers using the new(ish) kid on the block could learn a few things from the battle-tested patterns of Dojo's templated widgets, especially when it comes to working with views. In this talk, we'll look at how we can add evented views, smarter binding and teardown, view lifecycle methods, production-optimized template support, and dependency management to Backbone apps.

0177cdce6af15e10db15b6bf5dc4e0b0?s=128

Rebecca Murphey

June 01, 2012
Tweet

Transcript

  1. New Dog, Old Tricks (Or: Dojo Already Did That) Rebecca

    Murphey @rmurphey Backbone Conf 2012 Friday, June 1, 12 rebecca, js dev at bocoup slex warned me i’d have people coming after me with pitchforks for this title, but i think you’ll be ok
  2. Friday, June 1, 12 started playing with backbone just a

    couple of months ago after working with dojo for > 2 years its data stuff is pretty powerful -- especially if your data fits neatly into a RESTful CRUD interface, which turns out is kinda hard for some stuff, but whatever its views on the other hand ... there’s some event delegation stuff, and an empty render method, and otherwise glwtd coming from the dojo world, this was hard to come to terms with. the whole thing that seduced me about dojo was its templated widgets
  3. define([ 'dijit/_WidgetBase', 'dijit/_TemplatedMixin', 'text!./my-template.html' ], function(_Widget, _Templated, tmpl) { return

    dojo.declare([ _Widget, _Templated ], { templateString : tmpl, postMixInProperties : function() { this.clicks = 0; }, postCreate : function() { this.connect(this.buttonElement, 'click', '_onButtonClick'); }, _onButtonClick : function(e) { e.preventDefault(); console.log(++this.clicks); this.onButtonClick(this.clicks); }, onButtonClick : function(clickCount) { } }); }); Friday, June 1, 12 so in dojo land, a view -- a “widget” -- might look like this
  4. <div> <h1>${title}</h1> <p>${body}</p> <button data-dojo-attach-point="buttonElement">Click me!</button> </div> Friday, June 1,

    12 plus a template that looks like this (it’s pretty easy to switch templating engines)
  5. require([ 'widgets/my-widget.js' ], function(MyWidget) { new MyWidget({ title : 'My

    Widget', body : 'So simple!' }).placeAt(document.body, 'only'); }); Friday, June 1, 12 and then we’d use it like this there are some cool things here, and i missed them when i started using backbone’s views
  6. define([ 'dijit/_WidgetBase', 'dijit/_TemplatedMixin', 'text!./my-template.html' ], function(_Widget, _Templated, tmpl) { return

    dojo.declare([ _Widget, _Templated ], { templateString : tmpl, postMixInProperties : function() { this.clicks = 0; }, postCreate : function() { this.connect(this.buttonElement, 'click', '_onButtonClick'); }, _onButtonClick : function(e) { e.preventDefault(); console.log(++this.clicks); this.onButtonClick(this.clicks); }, onButtonClick : function(clickCount) { } }); }); Friday, June 1, 12 default rendering logic -- you provide a template, and dojo knows how to turn it into a document fragment using your view’s data
  7. <div> <h1>${title}</h1> <p>${body}</p> <button data-dojo-attach-point="buttonElement">Click me!</button> </div> Friday, June 1,

    12 dojo’s widgets also let you indicate in your template that you’d like your view code to have a reference to a given element
  8. define([ 'dijit/_WidgetBase', 'dijit/_TemplatedMixin', 'text!./my-template.html' ], function(_Widget, _Templated, tmpl) { return

    dojo.declare([ _Widget, _Templated ], { templateString : tmpl, postMixInProperties : function() { this.clicks = 0; }, postCreate : function() { this.connect(this.buttonElement, 'click', '_onButtonClick'); }, _onButtonClick : function(e) { e.preventDefault(); console.log(++this.clicks); this.onButtonClick(this.clicks); }, onButtonClick : function(clickCount) { } }); }); Friday, June 1, 12 if you want to hook into the “lifecycle” of a view -- the default logic dojo uses to create a view -- there are lifecycle methods you can use to affect the process without modifying the core logic
  9. define([ 'dijit/_WidgetBase', 'dijit/_TemplatedMixin', 'text!./my-template.html' ], function(_Widget, _Templated, tmpl) { return

    dojo.declare([ _Widget, _Templated ], { templateString : tmpl, postMixInProperties : function() { this.clicks = 0; }, postCreate : function() { this.connect(this.buttonElement, 'click', '_onButtonClick'); }, _onButtonClick : function(e) { e.preventDefault(); console.log(++this.clicks); this.onButtonClick(this.clicks); }, onButtonClick : function(clickCount) { } }); }); Friday, June 1, 12 dojo’s widgets also provide `this.connect`, which handles standard event binding *and* binding to arbitrary methods of arbitrary objects -- all with teardown that avoids memory leaks of course, backbone’s standard event delegation stuff takes care of this for delegate-able DOM events, but it’s a different story when you’re binding to models/collections
  10. require([ 'widgets/my-widget.js' ], function(MyWidget) { new MyWidget({ title : 'My

    Widget', body : 'So simple!' }).placeAt(document.body, 'only'); }); Friday, June 1, 12 finally, dojo’s widgets give you a nice way to place them where you want
  11. Friday, June 1, 12 here’s another picture of my dog

    i don’t mean that backbone should add all this i mean that *you should be aware of these techniques and add them as you see fit*
  12. rendering serializing, templatizing, placing binding memory-safe setup & teardown lifecycle

    react when things happen Friday, June 1, 12 my solution: create my own “SuperView” that gives me some help with these things goal: - don’t make me think! - don’t let different teammates solve the same problem in different ways - avoid repetition - solve a problem well and solve it in a single place <to the code>
  13. Friday, June 1, 12 backbone is uncut stone; it’s up

    to you to carve it into the form that makes sense for your project you shouldn’t feel obligated to use it as-is even if you don’t want to *use* one of the other tools, you do well to learn what they offer, and incorporate what makes sense
  14. github.com/rmurphey/srchr-demo pinboard.in/u:rmurphey/t:new-dogs-old-tricks/ Friday, June 1, 12

  15. rmurphey.com • @rmurphey • bocoup.com Friday, June 1, 12 rebecca,

    sr js dev at bocoup