所以我将这个子模型关联到我视图的1个列表项,当我编辑这个模型时,视图重新正确呈现。
但是当完整的列表模型发生变化时,我还得到了父做的其他事情,并且更改事件没有在aprent级别触发,这很奇怪,
如果我手动触发model.change(),我会看到从子模型更新的内容(意味着父模型已有效更改)。
是否有自动方式将更改事件传播到父模型?
答案 0 :(得分:4)
您的“父母”是子模型所属的集合吗?如果是,则只要子模型的属性发生更改,集合就会收到更改通知。这是一个演示模型/集合更改事件的示例:
var Product = Backbone.Model.extend({});
var Products = Backbone.Collection.extend({
model: Product
});
var ProductsView = Backbone.View.extend({
initialize: function () {
this.collection.bind('change', this.onProductChange, this);
},
onProductChange: function (product) {
console.log('product with ID ' + product.get('id') + ' changed to ' + product.get('name'));
}
});
var products = new Products([{ id: 1, name: 'Book' }, { id: 2, name: 'Toy' }, { id: 3, name: 'Shirt'}]);
new ProductsView({collection:products});
products.get(1).set({ name: 'TV' }); // console: product with ID 1 changed to TV
另一方面,如果您的“父母”不是您的子模型的集合,并且只有父/子关系,那么Backbone无法知道这种关系,因此您需要触发更改每当孩子改变时父母的事件。例如:
var Parent = Backbone.Model.extend({
includeChild: function (child) {
child.bind('change', this.onChildChange, this);
},
onChildChange: function (child) {
console.log('Child with name ' + child.get('name') + ' changed.');
}
});
var Child = Backbone.Model.extend({});
var parent = new Parent();
var child = new Child({ name: 'Bob', parent: parent });
parent.includeChild(child);
child.set({name: 'Joe'}); // console: Child with name Joe changed.
以下是Backbone事件的完整列表:http://documentcloud.github.com/backbone/#FAQ-events
答案 1 :(得分:1)
我喜欢JohnnyO的解决方案,并且我已经使用他的解决方案在我的应用程序中创建了一个通用的“SuperModel”类。以下是此类的Coffeescript版本,它允许使用父级注册子模型并自动传播所有事件:
class Model.SuperModel extends Backbone.Model
includeChild: (id, model) ->
@set id, model
@listenTo model, 'all', @trigger
就是这样。使用它很容易:
parent = new Model.SuperModel()
parent.includeChild('child', new Backbone.Model())
view = new Backbone.View()
view.listenTo(parent, 'change', -> console.log "parent changed!")
parent.get('child').set('foo', 'bar')
这将打印出“父改变”,正如您所期望的那样。