题
我正在使用backbone.marionette并具有以下CollectionView ItemView组合:
PlansListItemView = PlansApp.ItemView.extend
tagName: "tbody"
template: "#plansRow"
events:
'click th.expander': 'expandDocuments'
expandDocuments: (e) =>
# do stuff
PlansCollectionView = PlansApp.CollectionView.extend
tagName: "table"
itemView: PlansListItemView
我从嵌入在页面上的初始 json 集合创建视图。事件哈希中的事件完美运行。
然后,在下拉更改事件中,我对集合调用 fetch() 以检索新的对象集合。DOM 被重建,但事件处理程序不会重新附加/
有谁知道为什么会发生这种情况?
解决方案
虽然我不知道确切的原因,但你的设置中有一些有趣的东西让我认为这可能是问题的一部分。
笔记:根据您发布的内容,我对您的代码和模板做出了一些巨大的假设。可能发生的许多事情都会使我所说的大部分内容无效。不过,根据您发布的内容,以下是我对如何组织此代码的想法,这可能有助于解决您所看到的问题。
HTML 输出错误?
您将每个项目视图设置为 <tbody>
标签,但看起来你有一些 <th>
该视图呈现的标签 - 至少基于您配置的事件。
这将产生无效的 HTML,例如:
<table>
<tbody>
<th></th>
</tbody>
</table>
没有看到模板很难说 #plansRow
, ,但我猜想会出现类似的情况。
问题是集合视图不擅长生成表。他们可以很好地在表中生成行以及表标签包装器,但他们无法获取良好的表结构所需的表头、页脚、正文或其他标签,因为集合视图不呈现模板他们自己的。他们只是创建一个包装标签,然后渲染集合中的每个子项。
要纠正此问题,请使用 CompositeView,它是一个也呈现自己的模板的 CollectionView。
具有复合视图的更好的表结构
使用 Marionette 构建表格的更合适的设置是使用 CompositeView 作为父级,并让每个项目视图呈现一个 tr
标签。例如:
RowView = Backbone.Marionette.ItemView.extend({
template: "#row-template",
tagName: "tr"
});
TableView = Backbone.Marionette.CompositeView.extend({
template: "#table-template",
tagName: "table",
appendHtml: function(cv, iv){
cv.$("tbody").append(iv.el);
}
});
这将设置一个 <table>
与复合视图。该视图的模板将包含适当的 <thead><th>...</th></thead><tbody></tbody>
标签来定义表格。
行视图呈现为 <tr>
标签,并填充它需要的任何数据,包括适当的数据 <td>
标签。
这 appendHtml
复合视图上的方法处理将每个项目视图插入到 <tbody>
父复合视图的标签。
您可以在 JSFiddle 中看到该版本的实时版本: http://jsfiddle.net/derickbailey/me4NK/
还有一篇博客文章介绍了 CompositeView 的这一用途和其他用途,如下: http://lostechies.com/derickbailey/2012/04/05/composite-views-tree-structs-tables-and-more/