首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Backbone.js:我如何最有效地将共享胡子模板应用于视图的el?

Backbone.js:我如何最有效地将共享胡子模板应用于视图的el?
EN

Stack Overflow用户
提问于 2013-01-22 23:35:23
回答 2查看 561关注 0票数 3

骨干JS视图非常“有用”,因为它们总是为您创建一个DOM节点,带有一个可配置的标记、id和类。这很好,也很方便,但我发现它造成了一种不幸的情况:视图创建的DOM节点是一个隐藏的模板。

在我们当前的项目中,这一点对我来说是显而易见的,我们在前端和后端之间共享胡子模板。当您想要一个如下所示的DOM时,需要使用主干:

代码语言:javascript
复制
<section class="note">
  <textarea>
  ...
  </textarea>

  <input type="button" class="save-button" value="Save">
  <input type="button" class="cancel-button" value="Cancel">
</section>

最后创建的模板如下所示:

代码语言:javascript
复制
<textarea>
{{& content}}
</textarea>

<input type="button" class="save-button" value="Save">
<input type="button" class="cancel-button" value="Cancel">

但是现在模板被绑定到主干视图中的秘密根节点模板,这需要在服务器端复制。干封装就这么多了!

除了在呈现时将setElement()与呈现的模板一起使用之外,我没有看到一种立即解决这个问题的显而易见的方法,但这带来了其他问题,比如必须在每个render()之后替换DOM中新呈现的子树。

你是如何处理这个问题的?

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2013-01-23 01:09:21

这是个有趣的问题。我从来没有解决过这个特殊的问题,但我尝试了几个选择,我想我找到了一个我喜欢的。

首先,下面是代码:

代码语言:javascript
复制
//A base view which assumes the root element of its
//template (string, DOM node or $) as its el.
var RootlessView = Backbone.View.extend({

    //override the view constructor
    constructor: function(options) {

        //template can be provided by constructor argument or
        //as a subclass prototype property
        var template = options.template || this.template;

        //create a detached DOM node out of the template HTML
        var $el = Backbone.$(template).clone()

        //set the view's template to the inner html of the element
        this.template = $el.html(); 

        //set the element to the template root node and empty it
        this.el = $el.empty()[0];

        //call the superclass constructor
        Backbone.View.prototype.constructor.apply(this, arguments);
    }
});

本质上,您定义了一个基本视图,它期望每个派生视图都具有一个template属性,或者在选项哈希中将一个template作为参数。模板可以是字符串、DOM节点或jQuery/Zepto -wrapped DOM节点。该视图假定模板的根节点为其el,并将template属性重新定义为根节点的contents

您可以将其用作正常视图:

代码语言:javascript
复制
var View = RootlessView.extend({
    template: templateHtml,
    render: function() {
        this.$el.html(Mustache.render(this.template, this.model));
        return this;
    }
}); 

el属性在启动时是可用的,并且在重新呈现时不会分离和重新附加。普通Backbone.View行为的唯一例外是,如果定义了idcssClasstagName属性或参数,它们将被忽略,因为模板提供根元素。

这不是广泛测试,但似乎通过了大多数简单的测试用例。我能想到的唯一缺点是,template html字符串存储在每个视图实例(而不是原型)上,浪费了宝贵的内存字节,但这一点也不难解决。

这是一个在JSFiddle上的工作演示

票数 3
EN

Stack Overflow用户

发布于 2013-01-23 00:10:22

解决方案是将根节点本身(在本例中是节标记)包含在共享基模板(没有子模板)中,然后在实例化时初始化视图的"el“属性:

代码语言:javascript
复制
var existingElement = $('section.note')[0];
new View({el: existingElement}) 

然后,您可以继续将表单模板按常规方式附加到el属性。

票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/14470014

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档