2012-12-18 108 views
10

我正在構建一個用於管理多個子視圖的通用Backbone視圖。我有時需要執行邏輯來準備這些視圖,然後再呈現它們。我正在考慮使用骨幹活動,以使pre_render鉤,就像這樣:Backbone的觸發器()是同步的還是異步的?

view = new (this.child_view); 
this.trigger('pre_render', view); 
view.render(); 

trigger()稱爲事件同步進行,從而保證他們將在render()行之前完成的所有調用?

回答

11

基本上,是的,它是同步的。

下面是從源頭上相關章節:

trigger: function(name) { 
    if (!this._events) return this; 
    var args = slice.call(arguments, 1); 
    if (!eventsApi(this, 'trigger', name, args)) return this; 
    var events = this._events[name]; 
    var allEvents = this._events.all; 
    if (events) triggerEvents(this, events, args); 
    if (allEvents) triggerEvents(this, allEvents, arguments); 
    return this; 
}, 

導入功能是triggerEvents,這實際上調用處理程序。根據comments,它只是一個優化的調度程序。請注意,他們都致電.call().apply(),因此回調將在控制權交還給調用者之前完成。

var triggerEvents = function(obj, events, args) { 
    var ev, i = -1, l = events.length; 
    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, args[0]); 
    return; 
    case 2: while (++i < l) (ev = events[i]).callback.call(ev.ctx, args[0], args[1]); 
    return; 
    case 3: while (++i < l) (ev = events[i]).callback.call(ev.ctx, args[0], args[1], args[2]); 
    return; 
    default: while (++i < l) (ev = events[i]).callback.apply(ev.ctx, args); 
    } 
}; 

正如其他人所說,雖然觸發處理程序可以自由地安排自己的回調,如果他們如此傾向。因此,處理程序是否在返回之前完成其工作取決於處理程序代碼本身。

2

是的,它們是同步的。但是,由此事件觸發的功能可以免費使用setTimeout或發出ajax請求,如果是這樣,在trigger調用返回並且代碼繼續調用render時,這些功能將不會完成。所以是的,每個綁定的事件處理程序將被調用,但不一定完成其整個處理集。因爲觸發器API本身不使用回調或承諾,所以沒有直接瞭解所有事件處理程序何時完成的方法。如果有必要,你將不得不自己實現這樣一個API,並在包括任何異步處理在內的任何事情完成時觸發一個獨特的事件。然而,在日常編程中,大多數這些事件處理程序是同步的,如果不是這樣的話,代碼通常是這樣構造的,即程序不會導致應用程序不正常。如果你需要改變這個合約,這是一種代碼異味,你的應用程序設計不能和諧地使用事件系統,你可能想要考慮針對你的問題的不同方法。

1

根據源代碼觸發器是同步的,並不意味着所有偵聽「pre_render」事件的函數都會通過 執行同步操作。 PS:源代碼是很容易閱讀,你真的應該看看它:

http://backbonejs.org/docs/backbone.html

+1

我肯定找註明出處有用的;在回答這樣的問題時,我最喜歡留下紙條。謝謝! –

相關問題