Recently I needed an EventDispatcher to handle a large amount of events without loosing track of their names and their behave.
Perhaps it helps you too.
Here a simple example View:
define(['backbone', 'underscore', 'eventDispatcher'],
function(Backbone, _, dispatcher){
new (Backbone.View.extend(_.extend({
el: $('#anyViewOrWhatever'),
initialize: function () {
window.addEventListener('resize', function () {
// trigger event
dispatcher.global.windowResize.trigger();
});
// create listener
dispatcher.server.connect(this, this.doSomething);
// listen only once
dispatcher.server.connect.once(this, this.doSomething);
// remove listener:
dispatcher.server.connect.off(this, this.doSomething);
// remove all listener dispatcher.server.connect from this:
dispatcher.server.connect.off(null, this);
// remove all listener dispatcher.server.connect with this method:
dispatcher.server.connect.off(this.doSomething);
// remove all listener dispatcher.server.connect no matter what and where:
dispatcher.server.connect.off();
// do the same with a whole category
dispatcher.server.off(/* ... */);
// listen to all server events
dispatcher.server.all(this, this.eventWatcher);
},
doSomething: function(){
},
eventWatcher: function(eventName){
}
})
))();
});
Here the EventDispatcher with some example events. The events itself are predefined in the template Object. Your IDE should recognize them and lead you through the list.
As you can see, the Dispatcher run on its own. Only your View or whatever needs underlying Event methods from Backbone.
// module eventDispatcher
define(['backbone', 'underscore'], function (Backbone, _) {
var instance;
function getInstance () {
if ( !instance ) {
instance = createInstance();
}
return instance;
}
return getInstance();
function createInstance () {
// dummy function for your ide, will be overwritten
function e (eventContext, callback) {}
var eventHandler = {},
// feel free to put the template in another module
// or even more split them in one for each area
template = {
server: {
connect: e,
disconnect: e,
login: e,
logout: e
},
global: {
windowResize: e,
gameStart: e
},
someOtherArea: {
hideAll: e
}
};
// Create Events
_.each(template, function (events, category) {
var handler = eventHandler[category] = _.extend({}, Backbone.Events);
var categoryEvents = {
// turn off listener from <category>.<**all events**> with given _this or callback or both:
// off() complete purge of category and all its events.
// off(callback) turn off all with given callback, no matter what this is
// off(null, this) turn off all with given this, no matter what callback is
// off(callback, this) turn off all with given callback and this
off: function (callback, _this) {
if(!callback && _this){
handler.off();
}else{
_.each(template[category], function(v, k){
k != 'off' && template[category][k].off(callback, _this);
});
}
}
};
events.all = e;
_.each(events, function (value, event) {
// create new Listener <event> in <category>
// e.g.: template.global.onSomething(this, fn);
categoryEvents[event] = function (_this, callback) {
_this.listenTo(handler, event, callback);
};
// create new Listener <event> in <category> for only one trigger
// e.g.: template.global.onSomething(this, fn);
categoryEvents[event].once = function (_this, callback) {
_this.listenToOnce(handler, event, callback);
};
// trigger listener
// e.g.: template.global.onSomething.trigger();
categoryEvents[event].trigger = function (debugData) {
console.log('**Event** ' + category + '.' + event, debugData ? debugData : '');
handler.trigger(event);
};
// turn off listener from <category>.<event> with given _this or callback or both:
// off() complete purge of category.event
// off(callback) turn off all with given callback, no matter what this is
// off(null, this) turn off all with given this, no matter what callback is
// off(callback, this) turn off all with given callback and this
// e.g.: template.global.onSomething.off(fn, this);
categoryEvents[event].off = function (callback, _this) {
handler.off(event, callback, _this);
}
});
template[category] = categoryEvents;
});
return template;
}
});
The behavior of Backbones Event-system is not affected in any way and can be used as normal.