esamattis / requirejs-hbs

Simple Handlebars loader plugin for RequireJS
Other
79 stars 22 forks source link

Add support for partials #13

Open nurpax opened 10 years ago

nurpax commented 10 years ago

It'd be great to have support for partial templates.

nurpax commented 10 years ago

I saw there was #7 which asked for partials, but that was closed without actually adding partial support (right?). Issue #3 mentions someone had a work in progress patch that'd add partials (or dependencies to templates). I think this'd be something that should be supported out of the box without extra dependencies.

kusmierz commented 10 years ago

look at https://github.com/elving/swag

nurpax commented 10 years ago

This works with only handlebars.runtime when minified with r.js? Using swag means yet another library dependency and +20 KB minimized download size.

kusmierz commented 10 years ago

Yes, it works, I'm using it with r.js. Not 20, but 13kB :)

Anyway. You can also use only partial feature, but I think swag has few another useful (everyday) helpers... So it worth to spend 13kB more, I think.

nurpax commented 9 years ago

I actually found a really easy way to do partials without Swag. I'll try to put together a minimal example and send a PR against your README.

kusmierz commented 9 years ago

would be cool, thanks in advance!

chrisslater commented 9 years ago

Was this issue ever resolved? I am using your implementation and am looking to add partial support myself.

kusmierz commented 9 years ago

unfortunately only using https://github.com/elving/swag...

nurpax commented 9 years ago

Yeah, like I said above, there's an easy way to do this without Swag. I just never sent my PR for the simple example as I was unable to get the hbs example project working and was unable to send a minimal PR against the example project. See https://github.com/epeli/requirejs-hbs/issues/17.

You can pretty much just directly use Handlebars.registerPartial. Here's a use in a bigger project: https://github.com/nurpax/hswtrack/blob/3a336b95705d678ecc4209664085cff8e3d42177/static/app/stats.js. This project is nowadays rewritten in JSX but this old commit works fine.

define(['jquery', 'handlebars', 'underscore', 'app/view', 'app/model', 'hbs!templates/stats-main', 'hbs!templates/stats-history', 'hbs!templates/exercise-no-edit'], function($, Handlebars, _, view, model, templateStatsMain, templateStatsHistory, templateExercise) {
   ...

   Handlebars.registerPartial('exerciseNoEdit', templateExercise);

HTH.

chrisslater commented 9 years ago

Ok cool I see what you have done here. I was struggling to find how to precompile partials, but I see hbs can do it for me. So taking what you have, I have edited hbs-builder.js to allow me to define a partial in the require string.

'hbs!partial:path/to/templates'

and then modify the write output for precompiling requirejs.

# hbs-builder.js
var isPartial = (name.substr(0, 8) === 'partial:');
...
if (isPartial) {
  write(
    "define('hbs!" + name + "', ['handlebars'], function(Handlebars){ \n" +
      "Handlebars = Handlebars || this.Handlebars;\n" +
      "return Handlebars.registerPartial('" + name.substr(8) + "', Handlebars.template(" + compiled.toString() + ")); \n" +
    "});\n"
  );
} else {
  write(
    "define('hbs!" + name + "', ['handlebars'], function(Handlebars){ \n" +
      "Handlebars = Handlebars || this.Handlebars;\n" +
      "return Handlebars.template(" + compiled.toString() + ");\n" +
    "});\n"
  );
}
# hbs.js
...
if (isPartial) {
  onload(Handlebars.registerPartial(name, raw));
} else {
  // Just return the compiled template
  onload(Handlebars.compile(raw));
}

What are your initial thoughts?

There is definitely improvement to be made (for one the reputation of code for one) and registerPartial doesn't return anything so I may just return the template instead.