在Meteor.js中dynamic加载模板

我希望能够dynamic加载模板,而不显式指定模板。

举个例子:

<template name="foo"> </template> 

其中'foo'是模板,我想通过调用一些方法dynamic加载它的能力:

 Meteor.render(Meteor.loadTemplate('foo')); 

这可能吗?

meteor0.9.x新的API

Dan Dascalescu指出,meteor现在已经内置了dynamic模板! 这很好,因为你不需要像以前的版本那样包含额外的代码。

 {{> Template.dynamic template=template [data=data] }} 

对于Meteor 0.8.x Legacy

没有数据的dynamic模板:Boris Kotov更新的Blaze(0.8.0)答案在正确的轨道上(取自最新的文档),但它不适用于我。 我有以下工作:

 {{> dynamicTemplate name=myDynName}} <template name="dynamicTemplate"> {{#with chooseTemplate name}} {{> template}} {{/with}} </template> Template.dynamicTemplate.chooseTemplate = function (name) { return { template: Template[name] }; }; 

我希望有一个更简单的解决scheme,但我需要将模板包装在JSON中,如图所示。 也许这会帮助别人前进。

dynamic模板数据:如果你有,并希望数据是dynamic的,一定要做一个辅助方法,可以作出反应。 请确保在某处执行Session.set()以查看效果。

 // Inside "myContainingTemplate" {{> dynamicTemplateWithData name=myDynName data=myDataHelper}} <template name="dynamicTemplateWithData"> {{#with chooseTemplate name}} {{#with ../data}} {{> ..}} {{/with}} {{/with}} </template> Template.dynamicTemplateWithData.chooseTemplate = function (name) { return Template[name]; }; Template.myContainingTemplate.helpers({ myDataHelper: function () { Session.get('myReactiveKey'); } }); 

以下是如何dynamic呈现模板,从Meteor 0.9.4 – 1.0开始。 所有其他答案在撰写本文时已经过时了。

假设您正在编辑一堆logging或创build一个新logging,并且想要根据某些Sessionvariables呈现update模板或new模板。

有两种方法可以做到这一点:

1)这是Meteor 0.9.4或更新官方推荐方法 – 它使用Template.dynamic

 <template name="records"> {{> Template.dynamic template=whichOne}} </template> <template name="recordUpdate"> ... </template> <template name="recordNew"> ... </template> Template.records.helpers({ whichOne: function () { return Session.get('edit') ? 'recordUpdate' : 'recordNew' // note that we return a string - per http://docs.meteor.com/#template_dynamic } }); 

2)这适用于不同的Meteor版本,但不是正式推荐,因为不清楚模板是否是dynamicselect的:

 <template name="records"> {{> whichOne}} </template> {{! Note how "whichOne" is indistinguishable from a constant template name... }} {{ ...like "recordUpdate" or "recordNew" below. }} <template name="recordUpdate"> ... </template> <template name="recordNew"> ... </template> Template.records.helpers({ whichOne: function () { return Session.get('edit') ? Template.recordUpdate : Template.recordNew // note that we return a Template object, not a string } }); 

要将数据上下文传递给模板,请使用:

 {{> Template.dynamic template=whichOne data=myData}} 

你已经findMeteor.render,但你缺less的是模板加载。 在文档中提到你可以调用Template.foo()来返回模板的HTML。

http://docs.meteor.com/#template_call

把它们放在一起可以访问模板foo或其他任何使用括号访问的方法:

 var templateName = "foo"; var fragment = Meteor.render( function() { return Template[ templateName ](); // this calls the template and returns the HTML. }); 

然后片段是您的Reactive片段,以便您的模板可以继续接收实时更新。 你的片段现在需要放置在网页(我使用jQuery,所以这个例子也是如此):

 $("#htmlnode").html( fragment ); 

$(“#htmlnode”)只是您想要模板呈现的DOM中的一个节点。 你现在已经在你的网页上呈现内容了。

我只是这样做,不需要jQuery:

EDITED

 Template.mainContent.showContentFromRouter = function() { return Template[Meteor.Router.page()](); }; 

在这种情况下,我使用meteor路由器,并返回我select的任何模板(从路由器),但你可以这样做:

 Template.mainContent.showDynamicContent = function() { return Template['someTemplateYouveDefined'](); }; 

火焰更新:

https://github.com/meteor/meteor/wiki/Using-Blaze#templatefoo-is-not-a-function-and-does-not-return-a-string

使用给定的数据上下文dynamic呈现模板

旧:

 {{dynamicTemplate name="templateName" data=dataContext}} Template.foo.dynamicTemplate = function (opts) { return Template[opts.name](opts.data); }; 

新:(值得注意的是,在Blaze中,包含或块助手的关键字参数被绑定到一个单独的对象中,成为新的数据上下文)

 {{> dynamicTemplate name="templateName" data=dataContext}} <template name="dynamicTemplate"> {{#with chooseTemplate name}} {{#with ../data}} {{! original 'data' argument to DynamicTemplate}} {{> ..}} {{! return value from chooseTemplate(name) }} {{/with}} {{/with}} </template> Template.dynamicTemplate.chooseTemplate = function (name) { return Template[name]; } 

顺便说一句,我真的没有玩过,但这是我从新的火焰文件。 所以我觉得应该是这样做的方法;)

https://github.com/meteor/meteor/wiki/Using-Blaze

 {{> post}} Template.foo.helpers({ post: function () { return Template[this.postName]; } }); 

模板包含现在search模板对象的助手名称空间和数据,因此可以通过编程方式轻松select要使用的模板。 这是一个强大的function,并将允许模式,如分配一个模板作为另一个帮助,以便它可以被覆盖。

meteor0.8.x遗产

使用Joc的答案作为指导,我已经实现类似的使用http://docs.meteor.com/#template_call ,但使用帮手,而不是文档build议的:

当在模板帮助器,Meteor.render的主体或其他正在生成反应式HTML的设置中调用时,生成的HTML将被注释为使其呈现为被动DOM元素

我的client.js看起来有点像这样:

 Template.myPageTemplate.helpers({ dynamicTemplate: function() { // conditional logic can be added here to determine which template to render return Template.myDynamicTemplate(); } }); 

和我的HTML看起来像这样:

 <template name="myPageTemplate"> <h1>My Template</h1> {{{dynamicTemplate}}} </template> <template name="myDynamicTemplate"> <h1>My Dynamic Template</h1> </template> 

根据Hillmark的回答,这是最容易得到的:

 Template.main.template = function() { if (some_condition) { return Template.A(); } else { return Template.B(); } }; 

与相应的.html

 <body> {{> main}} </body> <template name="main"> {{{template}}} </template> <template name="A"> <h1>Template A</h1> </template> <template name="B"> <h1>Template B</h1> </template> 

编辑在Meteor 0.8.0中不起作用

对我来说,最简单的方法就是创build一个函数get_dynamic_template,如下所示:

 var a= get_dynamic_template(template_name,data); 

返回可以呈现为普通variables{{a}}的内容

这个函数的代码很简单:

 var get_dynamic_template = function(template_name,data) { return function(){ return new Handlebars.SafeString( UI.toHTML( Template[template_name].extend({data: function () { return data; }})) ); }; } 

这将处理有和没有数据的dynamic模板:(需要Blaze / Meteor 0.8)

 {{> dynamicTemplate name=templateName}} <template name="dynamicTemplate"> {{#with chooseTemplate name }} {{#if ../data}} {{#with ../data }} {{> .. }} {{/with}} {{else}} {{> this}} {{/if}} {{/with}} <template name="dynamicTemplate"> 

模板javascript:

 Template.dynamicTemplate.chooseTemplate = function (name) { return Template[name]; };