25

我广泛使用模板,我喜欢使用完整的模板。我的意思是我想在模板代码中看到所有的 DOM 元素,包括元素,像这样:

<script type="text/template" id="template-card">
  <div class="card box" id="card-<%= id %>">
    <h2><%= title %></h2>
    <div><%= name %></div>
  </div>
</script>

但是 Backbone 喜欢这样的模板

<script type="text/template" id="template-card">
  <h2><%= title %></h2>
  <div><%= name %></div>
</script>

并在 JS 代码中定义元素及其属性。我认为是丑陋和令人困惑的。

那么,有什么好方法可以避免我的 Backbone 视图用额外的 DOM 元素包装我的模板?

我一直在检查这个问题线程:https ://github.com/documentcloud/backbone/issues/546 ,我知道没有任何官方方法可以做到这一点..但也许你可以推荐我一个非官方的方法。

4

3 回答 3

42

您可以利用view.setElement渲染一个完整的模板并将其用作视图元素。

setElement view.setElement(element)
如果您想将 Backbone 视图应用到不同的 DOM 元素,请使用 setElement,它还将创建缓存的 $el 引用并将视图的委托事件从旧元素移动到新元素

您必须考虑两点:

  1. setElement调用undelegateEvents,处理视图事件,但要小心删除您可能自己设置的所有其他事件。
  2. setElement不会将元素注入 DOM,您必须自己处理。

也就是说,您的视图可能看起来像这样

var FullTemplateView = Backbone.View.extend({

    render: function () {
        var html, $oldel = this.$el, $newel;

        html = /**however you build your html : by a template, hardcoded, ... **/;
        $newel = $(html);

        // rebind and replace the element in the view
        this.setElement($newel);

        // reinject the element in the DOM
        $oldel.replaceWith($newel);

        return this;
    }
});

还有一个使用http://jsfiddle.net/gNBLV/7/的工作示例

于 2012-07-22T07:41:00.377 回答
0

现在您还可以将视图的tagName定义为一个函数并创建一个如下所示的类:

var MyView = Backbone.View.extend({
   template: '#my-template',
   tagName: function() {
     // inspect the template to retrieve the tag name
   },
   render: function() {
     // render the template and append its contents to the current element
   }
});

这是一个工作示例

于 2015-08-20T10:11:49.597 回答
0

Backbone.Decarative.Views为您提供了另一种方法来执行此操作,而无需依赖setElement. 有关更多信息,请在此处查看我的答案

于 2015-10-20T09:42:59.700 回答