Events
bbq supports the observer pattern or (pub/sub if you prefer) through the Watchable class. GUIWidget extends Watchable, as does Entity so you can observe most objects in bbq.
Receiving notifications
Watchable defines the registerListener method, which is used as follows:
var button = new bbq.gui.button.GUIButton({text: "Click me!"});
// register a listener function
button.registerListener("onClick", function() {
alert("button clicked!");
});
When the button is clicked, the onClick
notification is dispatched and our listener function is invoked.
Stop listening
To stop listening for notifications, call deRegisterListener:
var button = new bbq.gui.button.GUIButton({text: "Click me!"});
var listener = function(button) {
alert("button clicked!");
// we're done, stop listening
button.deRegisterListener(this);
};
// register a listener function
button.registerListener("onClick", listener);
Alternatively if you only wish to be informed once, use registerOneTimeListener:
var button = new bbq.gui.button.GUIButton({text: "Click me!"});
// register a listener function
button.registerOneTimeListener("onClick", function() {
// i will only be invoked once
alert("button clicked!");
});
Dispatching notifications
To dispatch a notification, call the notifyListeners from your observable:
myapp.foo.MyObservable = new Class.create(bbq.lang.Watchable, {
doSomething: function() {
...
this.notifyListeners("onDoSomething");
}
}
Arguments passed to notifyListeners will be passed to the observer:
myapp.foo.MyObservable = new Class.create(bbq.lang.Watchable, {
doSomething: function() {
...
this.notifyListeners("onDoSomething", "one", "two", "three");
}
}
var observable = new myapp.foo.MyObservable();
observable.registerListener("onDoSomething", function(sender, a, b, c) {
// logs "one two three"
Log.info(a + " " + b + " " + c);
});
See the JSDocs for further discussion.
Global listeners
To receive all events of a given type, register a global listener:
myapp.foo.MyObservable = new Class.create(bbq.lang.Watchable, {
doSomething: function() {
...
this.notifyListeners("onDoSomething", "one", "two", "three");
}
}
var invocations = 0;
bbq.lang.Watchable.registerGlobalListener("onDoSomething", function() {
invocations++;
});
var observable1 = new myapp.foo.MyObservable();
var observable2 = new myapp.foo.MyObservable();
observable1.doSomething();
observable2.doSomething();
// logs "2 invocations"
Log.info(invocations + " invocations");