Backbone js重新渲染使视图无事件

时间:2011-10-03 21:26:22

标签: backbone.js

所有

我正在使用Backbone JS建立一个应用程序,根据我的方法,如果第一个模型查找太旧,我会向服务器发出一个更新我的本地存储的请求。

所以我要处理的是这个。

(hashchange) -> 
  fetch model -> 
    (if model expired [eg: grabbed from LS], fetch again in background)
    render

在视图中,我将一个更改事件绑定到指向渲染的模型,以便当第二个请求返回时,页面只是重新渲染。

对于男士和女士们,我问为什么第一页加载时所有事件都有效(点击等)但是如果视图重新渲染,他们就不再了?

一些代码可以帮助您查看视图,有一个带嵌套请求的嵌套视图:

class ShowView extends Backbone.View
  template: +some template+
  initialize: ->
    this.render()
    @model.bind('change', this.render)

  render: ->
    $(@el).html(this.template(@model.toJSON())
    items = new ItemCollection
    @model.set(items: items, {silent: true})
    @$items = new ItemsView(collection: items, el: @$('#posts'))
    items.fetch()
    +displayPage @el+
    @

 class ItemsView extends Backbone.View
   template: +some template+
   initialize: ->
     @collection.bind('reset', this.render)

   render: =>
     @collection.each( (model) -> new ItemView(model: model))
     @

......我还发誓......

 class ItemView extends Backbone.View
   template: +some template+
   events:
     'click .inner': 'showItem'

   initialize: ->
     this.render()

   render: ->
     $(@el).html(this.template(@model.toJSON()))
     @

所有这些都已被概括,但概念是相同的。

当更改事件触发并且所有内容都刷新并且我点击.inner时,没有任何反应。

连连呢?我尝试在新渲染发生之前取消绑定并删除视图,我也尝试在所有渲染方法的末尾委托事件。

由于

- UPDATE -

ItemView模板:

<a class="inner">
  <img src="item/image.gif" />
  <h3><%= title %></h3>
  <p><%= description %></p>
</a>

ItemView中的showItem方法只是对实际项目的简单重定向:

showItem: ->
  window.location.hash = "#/posts/#{@model.id}/show"

我忘了提到ItemView的tagName是'li'而ItemsView tagName是'ul',所以这一切都是在页面上制作一个列表。

2 个答案:

答案 0 :(得分:1)

将此代码放入渲染函数中:

this.delegateEvents();

阅读解释here

答案 1 :(得分:0)

好的,所以这就是我为解决这个烦人的错误所做的:

Backbone.View附带Backbone.Events中的unbind方法。

所以我在本质上做的是跟踪我创建的每个视图,当我创建不同的视图或重新渲染samve视图时,我解除了DOM中所有先前的视图。

在我上面的示例中,以下是适用于我的代码:

class ShowView extends Backbone.View
  template: +some template+
  initialize: ->
    this.render()
    @model.bind('change', this.render)

  render: ->
    $(@el).html(this.template(@model.toJSON())
    items = new ItemCollection
    @model.set(items: items, {silent: true})
    @$items.unbind() if @$items             # for the subview events
    items.fetch()
    @$items = new ItemsView(collection: items, el: @$('#posts'))
    this.delegateEvents()                   # For the current view events
    +displayPage @el+
    @

    unbind: ->
      super
      @$items.unbind() if @$items

class ItemsView extends Backbone.View
   template: +some template+
   initialize: ->
     @collection.bind('reset', this.render)

   render: =>
     @collection.each( (model) -> new ItemView(model: model))
     this.delegateEvents()                 # For the current view events
     @

干杯,  Cbarton