Skip to content

Instantly share code, notes, and snippets.

@marlun78
Last active April 23, 2023 20:55
Show Gist options
  • Star 7 You must be signed in to star a gist
  • Fork 3 You must be signed in to fork a gist
  • Save marlun78/2701678 to your computer and use it in GitHub Desktop.
Save marlun78/2701678 to your computer and use it in GitHub Desktop.
Underscore.js templates as a standalone implementation
/*!
Underscore.js templates as a standalone implementation.
JavaScript micro-templating, similar to John Resig's implementation.
Underscore templates documentation: http://documentcloud.github.com/underscore/#template
Modifyed by marlun78
*/
(function () {
'use strict';
// By default, Underscore uses ERB-style template delimiters, change the
// following template settings to use alternative delimiters.
var settings = {
evaluate: /<%([\s\S]+?)%>/g,
interpolate: /<%=([\s\S]+?)%>/g,
escape: /<%-([\s\S]+?)%>/g
};
// When customizing `templateSettings`, if you don't want to define an
// interpolation, evaluation or escaping regex, we need one that is
// guaranteed not to match.
var noMatch = /.^/;
// Certain characters need to be escaped so that they can be put into a
// string literal.
var escapes = {
'\\': '\\',
"'": "'",
'r': '\r',
'n': '\n',
't': '\t',
'u2028': '\u2028',
'u2029': '\u2029'
};
for (var p in escapes) {
escapes[escapes[p]] = p;
}
var escaper = /\\|'|\r|\n|\t|\u2028|\u2029/g;
var unescaper = /\\(\\|'|r|n|t|u2028|u2029)/g;
var tmpl = function (text, data, objectName) {
settings.variable = objectName;
// Compile the template source, taking care to escape characters that
// cannot be included in a string literal and then unescape them in code
// blocks.
var source = "__p+='" + text
.replace(escaper, function (match) {
return '\\' + escapes[match];
})
.replace(settings.escape || noMatch, function (match, code) {
return "'+\n_.escape(" + unescape(code) + ")+\n'";
})
.replace(settings.interpolate || noMatch, function (match, code) {
return "'+\n(" + unescape(code) + ")+\n'";
})
.replace(settings.evaluate || noMatch, function (match, code) {
return "';\n" + unescape(code) + "\n;__p+='";
}) + "';\n";
// If a variable is not specified, place data values in local scope.
if (!settings.variable) {
source = 'with(obj||{}){\n' + source + '}\n';
}
source = "var __p='';var print=function(){__p+=Array.prototype.join.call(arguments, '')};\n" + source + "return __p;\n";
var render = new Function(settings.variable || 'obj', source);
if (data) {
return render(data);
}
var template = function (data) {
return render.call(this, data);
};
// Provide the compiled function source as a convenience for build time
// precompilation.
template.source = 'function(' + (settings.variable || 'obj') + '){\n' + source + '}';
return template;
};
window.tmpl = tmpl;
}());
@jdalton
Copy link

jdalton commented Jul 27, 2012

You can create a custom Lo-Dash build that's just _.template via lodash include=template:
http://lodash.com/#custom-builds

@emkayy
Copy link

emkayy commented Aug 2, 2017

@jdalton The only difference is, that the lodash custom build is 10 times the size of this one.

marlun78, thanks for sharing this!

@coderofsalvation
Copy link

thx for sharing this.

NOTE: the _.escape can be replaced with a simple escape

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment