2017-10-09 77 views
1

我在Backbone中构建网站,并且网站结构与Youtube相似,因为当您使用页面链接更改页面时,只有一部分DOM(即非 - 导航组件)被重新加载而不是整个文档。在骨干中多次初始化视图

因此,当用户访问使用我的网站上的链接子页面,骨干会发出一个AJAX调用和接收HTML的子页面,这将是这个样子:

<section id="SubpageView">...</section> 
<script> 

// Defines the view that controls #SubpageView. 
if(typeof SubpageView !== 'undefined') { 

    // If this is the first time the page is loaded, create class. 
    var SubpageView = Backbone.Model.extend({ 
     el: '#SubpageView', 
     ... 
    }); 

} 

MainView.currentSubpage = new SubpageView(); 
</script> 

是任何缺点(即僵尸视图,内存泄漏等)多次调用SubpageView()?在我看来,定义一个视图元素使用el而不是tagName适用于仅使用一次的元素。

注意:我知道单页网络应用程序通常会将其所有模板都烘焙到持久性DOM中,并且所有HTML均使用客户端模板进行处理。但是因为我设计的网站在不使用pushState()的情况下降级到传统的服务器端呈现,或者Javascript被禁用时,我不想将所有模板都烧到持久性DOM中。

+0

你可以使用jQuery来多次注入View。例如你有标签'elems'div元素和循环创建一个视图。 。'$( “elems的”)追加(yourElem);' –

回答

2

这是一个很好的问题 - 我认为很多人忽略了这个问题,它会导致问题。 “僵尸意见”是一个很好的描述符。我想说你是对的,他们可以导致问题:

  • 您正在维护(可能很大)不再需要的对象实例。
  • 您的僵尸视图实例仍然可以引用仍在使用的现有对象,并可能导致意外的行为。

,如果你使用主干的事件散,像最后一点尤为重要:所有的僵尸意见

events: { 
    'click .someButton': 'someMethod', 
    // ... 
}, 

因为你是重用el选择(因为我认为你应该),事件将保持活跃,并在他们无意中触发意见的功能。这可能意味着重复的行为或其他完全意想不到的结果。


至于解决方案,我认为你有两个选择:一个是在更新之前销毁旧的视图实例。默认remove方法实际上删除el,你不想要... undelegateEvents可能会有所帮助。骨干网并没有一个干净的方式去完成所需的任务,所以你最终会自己写一些代码。我想一个更好的选择是重新使用您的现有视图实例与新的数据(collection,model,其他实例数据,或其他适当的东西)。

当你改变你的页面的子视图,你很可能通过某些变量,说取出的HTML:

$.get('/templates/someView.html', function(html) { 
    Mainview.currentSubpage = new SubpageView(html); 
}); 

...或者类似的东西。相反,我建议你在写作的方法,而不是更新现有的实例,如:

$.get('/templates/someView.html', function(html) { 
    Mainview.currentSubpage.resetPage(html); 
}); 

你写的resetPage方法到您SubpageView做你需要的东西。这当然可以适用于很多,当然,我只是用它作为例子。