简体   繁体   中英

Backbone events firing order

Say I have this:

view1.listenTo(model, 'change', function(){
    console.log('test1');
});

view2.listenTo(model, 'change', function(){
    console.log('test2');
});

Is it guaranteed that 'test1' will always print first?

I don't know any case that the listeners work in a different way. I have read the backboneJs code to be sure, and I have seen that listenTo push the callback in an array. When the event is triggered, it loops an array that contains the event callbacks.

var triggerEvents = function (events, args) {
    var ev, i = -1, l = events.length, a1 = args[0], a2 = args[1], a3 = args[2];
    switch (args.length) {
        case 0: while (++i < l) (ev = events[i]).callback.call(ev.ctx); return;
        case 1: while (++i < l) (ev = events[i]).callback.call(ev.ctx, a1); return;
        case 2: while (++i < l) (ev = events[i]).callback.call(ev.ctx, a1, a2); return;
        case 3: while (++i < l) (ev = events[i]).callback.call(ev.ctx, a1, a2, a3); return;
        default: while (++i < l) (ev = events[i]).callback.apply(ev.ctx, args);
    }
};

I think you can be sure it won't change. Always the events work in that way. When the event happens (this.model.trigger("change") or this.model.set("...)) the callbacks are launched in order that they were definned and when the callbacks are launched the execution continues in the next line of the model modification.

As @Daniel pointed out that documentation doesn't state anything particular about event ordering.

Based on my personal experience I have never seen events firing in random order.

This working DEMO confirms it.

Demo code:

   var Person = Backbone.Model.extend({ 
     initialize: function(){
            console.log("Welcome to this world");
        }
   });

  var person = new Person({ name: "Thomas", age: 67, child: 'Ryan'});

   var headerView = Backbone.View.extend({    

        initialize: function() {

             this.listenTo(person, 'change', function(){
                console.log('test1');
             });      

            this.listenTo(person, 'change', function(){
                console.log('test2');
             });      

             this.listenTo(person, 'change', function(){
                console.log('test3');
             });      

            this.listenTo(person, 'change', function(){
                console.log('test4');
             });      

             this.listenTo(person, 'change', function(){
                console.log('test6');
             });      

            this.listenTo(person, 'change', function(){
                console.log('test7');
             });      

        }        
     });

   new headerView();

setInterval(function(){
    person.unset('attr');
    person.set({'attr': 'value'});
},1000)

In its current implementation, i would say yes. The documentation does not state that, however and that can change at anytime.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM