micro templates for javascript norman white. background separate html code from data provide a...
TRANSCRIPT
Micro Templates for Javascript
Norman White
Background
• Separate HTML code from data • Provide a flexible reusable template to generate
html with embedded data• Reduce the amount of code that needs to be
written• Provide ability to develop standard templates for
web applications• Original article– http://ejohn.org/blog/javascript-micro-templating/
Original MicroTemplate• // Simple JavaScript Templating
// John Resig - http://ejohn.org/ - MIT Licensed(function(){ var cache = {}; this.tmpl = function tmpl(str, data){ // Figure out if we're getting a template, or if we need to // load the template - and be sure to cache the result. var fn = !/\W/.test(str) ? cache[str] = cache[str] || tmpl(document.getElementById(str).innerHTML) : // Generate a reusable function that will serve as a template // generator (and which will be cached). new Function("obj", "var p=[],print=function(){p.push.apply(p,arguments);};" + // Introduce the data as local variables using with(){} "with(obj){p.push('" + // Convert the template into pure JavaScript str .replace(/[\r\t\n]/g, " ") .split("<%").join("\t") .replace(/((^|%>)[^\t]*)'/g, "$1\r") .replace(/\t=(.*?)%>/g, "',$1,'") .split("\t").join("');") .split("%>").join("p.push('") .split("\r").join("\\'") + "');}return p.join('');"); // Provide some basic currying to the user return data ? fn( data ) : fn; };})();
Tricks that allow micro templates
• “Hide” the template definition in a script type that the browsers don’t recognize, then call the micro template function to dynamically fill in the data elements.
• Use Javascript’s powerful regular expression facilities to create a tiny templating expansion function that is passed a template and data, and generates an html string that can then be used somewhere.
• You can precompile the templating function for performance.
Example Template
• <script type="text/html" id="item_tmpl"> <div id="<%=id%>" class="<%=(i % 2 == 1 ? " even" : "")%>"> <div class="grid_1 alpha right"> <img class="righted" src="<%=profile_image_url%>"/> </div> <div class="grid_6 omega contents"> <p><b><a href="/<%=from_user%>"><%=from_user%></a>:</b> <%=text%></p> </div> </div></script>
Example Template
• <script type="text/html" id="item_tmpl"> <div id="<%=id%>" class="<%=(i % 2 == 1 ? " even" : "")%>"> <div class="grid_1 alpha right"> <img class="righted" src="<%=profile_image_url%>"/> </div> <div class="grid_6 omega contents"> <p><b><a href="/<%=from_user%>"><%=from_user%></a>:</b> <%=text%></p> </div> </div></script>
NAME
Example Template
• <script type="text/html" id="item_tmpl"> <div id="<%=id%>" class="<%=(i % 2 == 1 ? " even" : "")%>"> <div class="grid_1 alpha right"> <img class="righted" src="<%=profile_image_url%>"/> </div> <div class="grid_6 omega contents"> <p><b><a href="/<%=from_user%>"><%=from_user%></a>:</b> <%=text%></p> </div> </div></script>
Data Element
Usage
var results = document.getElementById("results");results.innerHTML = tmpl("item_tmpl", dataObject);
QUESTION: What is in “dataObject” ?
Many micro templates now
• Jquery Templates• Mustache• Pure• Mootools• Whiskers• …
MustachePopular micro template
Used in Dreamweaver examples
• “Logic-less”– No if, else, for , …
• 300 lines of Javascript code• Works in python, ruby or javascript– Can run on server side or browser
Typical Template
Hello {{name}} You have just won ${{value}}! {{#in_ca}} Well, ${{taxed_value}}, after taxes. {{/in_ca}}
Data Object
{ "name": "Chris", "value": 10000, "taxed_value": 10000 - (10000 * 0.4), "in_ca": true }
Result
Hello Chris You have just won $10000! Well, $6000.0, after taxes.
Usage
Mustache only uses “tags”, no logic
Tag TypesVariables
{{name}} {{{name}}} (unescape html)Sections – renders blocks of text one or more times
{{#person}} …. {{/person}}Lambdas – Callable objects, i.e. functions
Some Mustache ExamplesTemplate
{{name}} {{age}} {{company}} {{{company}}}
Hash (input data){“name”: “Chris”,“company”: “<b>GitHub</b>”{Output
Chris
<b>GitHub</b> <b>GitHub</b>
Lists(Note automatic iteration)
Template:– {{#repo}} – <b>{{name}}</b> – {{/repo}}
Hash:{ "repo": [
{ "name": "resque" },
{ "name": "hub" }, { "name": "rip" },
] }
Output:<b>resque</b> <b>hub</b> <b>rip</b>
Lambdas• Template:
– {{#wrapped}} – {{name}} is awesome. – {{/wrapped}}
• Hash:– { – "name": "Willy", – "wrapped": function() { – return function(text) { – return "<b>" + render(text) + "</b>" } – } – }
• Output:– <b>Willy is awesome.</b>
Invoking MustacheJust call Mustache.render(template, data)
• Include mustache.js
• var view = { • title: "Joe", • calc: function () { • return 2 + 4; • } • };
• var output = Mustache.render("{{title}} spends {{calc}}", view);
• Output = “Joe spends 6”
Typical Uses
• Get data from server as a JSON string• Decode JSON data and pass to a mustache
template to display.
• Many examples of Mustache on-line