Javascript 主干DOM事件多次触发

Javascript 主干DOM事件多次触发,javascript,jquery,backbone.js,backbone-events,Javascript,Jquery,Backbone.js,Backbone Events,我第一次构建了一个主干应用程序,而且进展非常顺利 但是,我认为我没有以正确的方式为我的模型集合创建视图,当我绑定事件时,它们为每个视图触发,而我只希望它们为一个视图触发 以下是我的主干代码(一个片段): 这是我的视图模板 <script type="text/template" id="template-model-grid-item-view"> <div id="series-<%=seriesId%>&

我第一次构建了一个主干应用程序,而且进展非常顺利

但是,我认为我没有以正确的方式为我的模型集合创建视图,当我绑定事件时,它们为每个视图触发,而我只希望它们为一个视图触发

以下是我的主干代码(一个片段):

这是我的视图模板

<script type="text/template" id="template-model-grid-item-view">
    <div id="series-<%=seriesId%>" class="grid-item-view column-<%=column%>">
        <div class="label"><%= name %></div>
        <div class="thumbnail">
            <img src="/Content/themes/BMW/img/series/small/<%= slug %>.png"/>
        </div>
    </div>
</script>

.png“/>

视图集合正确,但当我单击一个视图时,所有视图都会触发事件。有人能为我指出正确的方向吗?

由于您在视图的
事件对象中忽略了选择器,因此以下内容适用

根据主干:
省略选择器会导致事件绑定到视图的根元素(this.el)。

问题在于
系列GridItemView
的每个绑定
点击
事件到
#model grid
,每个视图都是
#model grid
的子视图。在您的示例中,您注册了5个点击事件,当您点击任何视图时,所有5个事件都会被触发

在不更改任何其他代码的情况下,一种解决方案是设置
events
对象以返回函数,以便为每个视图指定
id
选择器

events: function() {
  var selector = '#series-' + this.model.get('seriesId'); // this id corresponds to your template id
  var ev = {};
  ev['click ' + selector] = 'toggle';
  return ev;
},
我更喜欢的另一个选项是,不要将
#model grid
指定为所有视图的根元素。它最终会显示为:

附带建议

  • render
    函数中,无需创建变量,您可以使用
    $
    访问元素:

    render: function(){
      this.template = _.template( $('#template-model-grid-item-view').html() );
      this.$el.append(this.template(this.model.toJSON())));
    },
    setState: function(){
      this.active = this.model.get('active');
      this.$el.toggleClass('active',this.active);
    },
    

  • 谢谢你,我的朋友!这太棒了。我爱你!
    events: function() {
      var selector = '#series-' + this.model.get('seriesId'); // this id corresponds to your template id
      var ev = {};
      ev['click ' + selector] = 'toggle';
      return ev;
    },
    
    SeriesGridItemView = Backbone.View.extend({
      // remove the following line
      el:'#model-grid', 
    
      // .. all else is the same ../
    });
    
    series = new SeriesCollection(window.BMW.data.series);
      series.forEach(function(m,i){
        var c = i+1;
        if(c > 3){
          c%=3;
        }
        m.set('column','1');
        $('#model-grid').append(new SeriesGridItemView({model:m}).el);
    });
    
    render: function(){
      this.template = _.template( $('#template-model-grid-item-view').html() );
      this.$el.append(this.template(this.model.toJSON())));
    },
    setState: function(){
      this.active = this.model.get('active');
      this.$el.toggleClass('active',this.active);
    },