2013-05-31 82 views
1

我有Task秒的集合。我在集合声明中添加了一些过滤方法,以便在新实例中返回集合的一个子集。我想要做的是在原始集合中创建一个模型,并将add(和任何其他)事件筛选到Tasks集合的任何新实例,以便我的查看部分可以相应地更新。复制事件,以新的实例

Here is a JSBin demonstrating my problem。请注意,当我在最后一行的原始集合中添加新模型时,列表不会更新,因为显然,筛选器方法会返回该集合的新实例(这对我来说似乎很干净),因此任何侦听器都不会被触发 - 该视图使用与添加了项目的视图不同的集合。

我如何语义和干净筛选集合,但保持势必被过滤设定的约束对模型的子集返回的任何事件?

例如,不烧成下面的代码的add事件notAsManyTasks(在alert()从来没有显示):

// Task model 
var Task = Backbone.Model.extend(); 

// Tasks collection 
var TasksCollection = Backbone.Collection.extend({ 
    model: Task, 
    byProject: function(projectId) { 
     var matches = this.filter(function(task) { 
      return task.get('projectId') == projectId; 
     }); 

     return new TasksCollection(matches); 
    }, 
    complete: function(state) { 
     return new TasksCollection(this.where({ complete: state })); 
    } 
}); 

// Example collection 
var lotsOfTasks = new TasksCollection([ 
    { id: 1, projectId: 1, complete: false }, 
    { id: 2, projectId: 1, complete: true }, 
    { id: 3, projectId: 2, complete: false }, 
    { id: 4, projectId: 2, complete: true } 
]); 

var notAsManyTasks = lotsOfTasks.byProject(1); 

notAsManyTasks.on('add', function() { 
    alert("Added"); 
}); 

// Does not fire `add` event on `notAsManyTasks` which is my problem, however 
// it _does_ fire on `lotsOfTasks`, as it should 
lotsOfTasks.add({ id: 5, projectId: 1, complete: false }); 

我如何克服这个问题?理想情况下,我不想存储集合的原始状态,返回一个子集,然后再次恢复所有模型。

+0

所以你想要一个更新的原始集合的视图?当你执行'notAsManyTasks.add({id:6,projectId:1,complete:true})'时,你想要发生什么? – Eric

+0

理想情况下,它应该在'lotsOfTasks'之间同步,因为'notAsManyTasks'是前者的“孩子”(子集)。不过,我不在乎,因为我总是可以做'lotsOfTasks.add(...)' – Bojangles

回答

1

没有做一些复杂的事情,你应该能够沿着这些线路做一些事情:

mySubset.listenTo(myCollection, 'all', function() { 
    this.trigger.apply(this, arguments); 
}); 

你听你的集合中的所有事件,并与您的子集呼应他们。虽然我猜这只是一半的解决方案,因为你的子集不会被更新,你会在监听器中为你的所有子集做过滤器。
另一种解决方案来完成这项工作只有一次将是您的收藏听自己的add事件,过滤器的新模式,并触发一个自定义事件,以便只有子集(S)实际需要(S)做某事做一点事。

+0

我不得不做一个小小的改动(通过'this作为第三个参数),你的解决方案工作得很好 - 谢谢! – Bojangles