Backbone.js: Collection's "change" event isn't firing

50,491

Solution 1

The change event is only fired when one of the collections' models are modified. When a model is added to the collection the add event is fired.
See Backbone.js' Collection Documentation:

You can to bind "change" events to be notified when any model in the collection has been modified, listen for "add" and "remove" events[...]

To listen for when an add occurs modify your code to be

var c = new AwesomeCollection();
c.bind("add", function(){
  console.log('Collection has changed.');
});

c.add({testModel: "Test"}); 

Solution 2

No, that only raises the "add" event. It will raise the change event if you do this:

var c = new AwesomeCollection();
c.bind("change", function() {
  console.log('Collection has changed.');
});

var model = new Backbone.Model({testModel: "Test"});
c.add(model);
model.set({testModel: "ChangedTest"});

Solution 3

If you want to know when something of significance has been done with a collection, these are the events you probably want to listen to: change add remove reset

With respect to your example, this is what your code might look like:

var c = new AwesomeCollection();
c.bind('change add remove reset', function(){
    console.log('Collection has changed.');
});

Solution 4

It may not be necessary in most cases, but you can manually trigger a change event on your object/collection:

object.trigger("change");

Solution 5

I don't find it documented anywhere but the "all" event fires on all actions, including add, remove and change.

var c = new AwesomeCollection();
c.bind("all", function(){
  console.log('Something happened');
});

c.add({testModel: "Test"}); 
Share:
50,491
Thomas
Author by

Thomas

Updated on May 13, 2020

Comments

  • Thomas
    Thomas almost 4 years

    I have a pretty simple collection, but I can't seem to bind to it's change event. In Chrome's console, I'm running:

    var c = new AwesomeCollection();
    c.bind("change", function(){
      console.log('Collection has changed.');
    });
    
    c.add({testModel: "Test"}); // Shouldn't this trigger the above log statement?
    

    Since this is one of those things that can be difficult to track down, I doubt anybody knows off the top of their head what's going on (if so, great!). So, I'm asking two questions:

    1. Should the above code work as anticipated?
    2. If so, do you have any suggestions on how to track down where this would fail?

    Thanks

  • Thomas
    Thomas over 12 years
    Changing the binding from "change" to "add" still doesn't produce this. Hmmm... the problem might be elsewhere.
  • twiz
    twiz almost 10 years
    You have a missing ")" on the c.bind call.
  • Matt Fletcher
    Matt Fletcher over 9 years
    Don't forget too that you can bind multiple events, for example: c.bind("add remove update", function() {});
  • Guy Passy
    Guy Passy about 8 years
    So, when a model within the collection is changed