【问题标题】:How to avoid an extra div in a Backbone Marionette Region or LayoutView如何避免 Backbone Marionette Region 或 LayoutView 中的额外 div
【发布时间】:2014-12-11 07:26:15
【问题描述】:

我们在我的应用程序中使用Backbone,Marionette and handlebars。当我尝试在Marionette.Region 中呈现我的视图时,一个额外的div 环绕模板。我怎样才能避免这种情况。

html代码:

 <div id="mainDiv"></div>
   <script type="text/x-handlebars-template" id="basic">
        <div id="first"></div>
        <div id="second"></div>
    </script>

js代码:

 //function
var templateCompilation=function(templateId,data){
   var alertCompilation=Handlebars.compile(document.getElementById(templateId).innerHTML);
   return alertCompilation(data);
};

//Application
myApp = new Backbone.Marionette.Application();
myApp.addRegions({
 mainContainer:"#mainDiv"
});
myApp.start();

//first view
var basicView=Marionette.ItemView.extend({
  template:function(){
     return templateCompilation("basic",{});
  }
});

//reding view
var basicViewObj=new basicView();
myApp.mainContainer.show(basicViewObj);

为了避免额外的 div,我尝试使用以下语句我的运气不好。

var basicViewObj=new basicView({el:$("#mainDiv")});
var basicViewObj=new basicView({tagName:""});

谁能帮帮我。

【问题讨论】:

标签: javascript backbone.js marionette


【解决方案1】:

重要更新:

该行下面的代码将不起作用。我没有测试就写了它(在我的手机上)。以下更新已经过测试并纳入@vzwick 建议的重要评论。

如下所述,覆盖区域中的attachHtml。我们将对attachHtml 进行三项重要更改,如下面的 cmets 中所述

myApp.mainContainer.attachHtml = function (view) {
    // empty the node and append new view
    this.el.innerHTML="";

    // All view elements are attached to that view's el, which acts as a
    // container for that view. The OP wants to get rid of that container 
    // and use the region's el instead. So first get the children of the
    // view that we want to show in the Region
    var children = view.el.childNodes;

    // Now pop each child element into the el of the Region
    // Note that Node.appendChild(Node) removes the first element from the 
    // Node array on each iteration so children[0] will be the next
    // child for each iteration
    while (children.length > 0) {
        this.el.appendChild(children[0]);
    }
     
    // Finally, assign a new el to the view:       
    // view.setElement(element, delegate) is a Backbone method
    // that reassigns the el of the *view* to the parameter *element*
    // and if delegate = true, re attaches the events to the new el
    view.setElement(this.el, true)
}

需要注意的重要一点是,OP 的 basicView 现在与 myApp.mainContainer 共享其 el。由于myApp.mainContainer 是一个区域并且它不采用event 参数,因此如果重新委派事件,则不会发生冲突。如果这与 LayoutView 一起使用也是如此,因为事件的重新委派将发生在 LayoutView Region el 上,并且不会 LayoutViewel,那么应该没有冲突。


旧帖的开头

我以前没有尝试过,但我从功能和结构层面对您的问题很敏感。我建议你做的是覆盖RegionattachHtml 函数。

默认情况下Backbone.MarionetteattachHtml 正在这样做

attachHtml: function(view) {
    // empty the node and append new view
    this.el.innerHTML="";
    this.el.appendChild(view.el);
}

要更改此功能,您可以在 Region 中定义一个新的 attachHtml,如下所示:

attachHtml: function(view) {
    // empty the node and append new view
    this.el.innerHTML="";
    this.el.appendChild(view.el.childNodes);
}

现在Region el 将直接附加您在该区域中显示的视图的内部节点。

要覆盖mainContainer 区域的原始attachHtml,您可以使用Application 变量,即

myApp.mainContainer.attachHtml = function (view) { ... }

上面写的代码示例。

【讨论】:

  • 这很可能(无法验证,因为我现在在移动设备上)因为来自 events 散列的 Backbone 的 View 事件绑定被限定为视图的 el。因此,虽然您的 hack 会在没有容器的情况下附加 DOM 节点,但 Backbone 的 DOM 事件模型会被破坏而无法修复。
  • 优秀点@vzwick。我也没有对此进行测试,但我想知道在mainContainer Region 中的shown 视图中使用this.setElement = MyApp.mainContainer 是否可以解决您提出的问题。当然,这意味着 mainContainer Region 的所有 Backbone 事件都必须连接到 RegionView,因为每当调用 delegateElements 时,它所做的第一件事就是 @ 987654361@,并且会导致对实际连接的事件有很多困惑。但这就是问题中 OP 所要求的。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2016-02-19
  • 1970-01-01
  • 2012-01-26
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多