Change log
[June 26 2013]: (bugfix) There was a bug in the class(es) where it always tried to return a value from event::trigger even when there were no parameters. [June 24 2013]: I uploaded the wrong zip file. Fixed now.
Features Use static class or instantiate multiple event objects or simply use the trait to add event handling for your other classes (I have examples for all of them below!) Listen & Trigger events Temporarily suppress and unsuppress events if needed Programmatically clear listeners on specific events Have multiple listeners on the same event, ordered by a custom priority from 0-100 Trigger events and pass any number of parameters/arguments to the listeners (modifications are “gathered” through all the listeners) and the final parameters are returned, modified or not. Why use an event/hook class? and how does it work? The use of event-driven programming allows you to modularize your core code or allow parts of the system to alter the behavior of other parts. If you have ever used a CMS like Wordpress or Drupal, you have used a CMS with a event/hook system. In the drupal community there is a saying that goes “Never hack core!” and for a good reason because whenever you update your drupal installation from say 7.0 to 7.1, if any of the files you have changed is updated - You lose your changes! Here the event (or hook) system solves that problem. Using the eventObject class (eventObject.php) Ok, consider the following You have a website of some sort and in profile.php you tell the visitor about a person (this could be a social site or forum etc) Now, if you want to allow other parts of the system to modify the output of that, one way is using an event class. profile.php $person->name = 'John'; $person->age = 20; echo $person->name; Here we output the name of a person. Now, if we want to allow modules/plugins or other parts of the system to modify that, we can use the event class. Let’s say we have an index.php (Main file). index.php require('event.php');//we load the event class $event = new event();//Semantically, "new event()" may sound like we're creating ONE event. We're not, we're creating an entire event system. Now, let’s say we have a module (which has been enabled and loaded up and what not) module_modifyprofile.php //here, we set up a "listener", a function that "listens" for the event, in this case the event is "person_modify". $event->listen('person_modify', function($person){ $person->name .= ' Smith'; }); So our module_modifyprofile is enabled, and is being run. Now let’s return to our profile.php, here we “trigger” an event. profile.php $person->name = 'John'; $person->age = 20;
//anyone want to modify this? $event->trigger('person_modify', $person);
echo $person->name; Final Output John Smith Note The name of the events you listen on and trigger are up to you, they can be any arbitrary string. Using the “static” event class (event.static.php) The static class is great, it solves two problems: one is it’s easier to use in that you will always have access to it wherever you are (Avoiding the need for a registry class or the use of “global”), secondly it allows your site to have one site-wide “master event” system across your entire application. Here’s how to use it require_once('event.static.php'); event::listen('404', function($message) { die($message); }); //... //... event::trigger('404', 'something went wrong'); I advice you to use this class for “main” events that lie at the root of your application and then consider either the eventObject which I talked about previously or the trait for events on specific objects or other parts of the system. Which leads me to the next section, the eventTrait! Using the eventTrait trait (event.trait.php) Consider a person object again.. actually, the class. This time we’ll add a “display” function/method. This could be the function that displays the profile to the user.. something like that class person { public $name = 'John'; public $age = 20;
public function display() { echo 'name: ' .$this->name .'<br />'; echo 'age: ' .$this->age .'<br />'; } } This might not be a very good example of a person class but bare with me. Let’s make this display function modular and extendable so that other modules/plugins can modify it’s behavior… Let’s try using the static class: class person { public $name = 'John'; public $age = 20;
public function display() { event::trigger('person_display_before', $person); echo 'name: ' .$this->name .'<br />'; echo 'age: ' .$this->age .'<br />'; event::trigger('person_display_after', $person); } } Sure, that works. we simply event::listen('person_display_before', function(){//...}) But wait.. what if there are several dfferent “users” being displayed through this person class, and suppose the ‘admin’ users should look a bit different according to say.. a module or plugin in our system? – We might be able to ask “is this an admin?” inside the event listeners but that would give some overhead (it would require more if statements and more logic…). Let’s try creating a new event object in the person class. So each person has it’s own event object. class person { public $name = 'John'; public $age = 20; public $event;
public function __construct() { $this->event = new eventObject(); }
public function display() { $this->event->trigger('display_before'); echo 'name: ' .$this->name .'<br />'; echo 'age: ' .$this->age .'<br />'; $this->event->trigger('display_after'); } } < That’s a bit better, but what if we could change ”$this>event->trigger()” and consequently ”$person->event->listen()” to something easier to write? Here’s where the trait comes in. If you don’t know how to use traits, refer to the php documentation. A trait is basically a list of members (properties and functions) that can be used in a class. Like this: class person { public $name = 'John'; public $age = 20;
use eventTrait;
public function display() { echo 'name: ' .$this->name .'<br />'; echo 'age: ' .$this->age .'<br />'; } } Now, the “person” class is actually an event class too! It has the “listen” and “trigger” (and more) methods. Using it is super simple: class person { public $name = 'John'; public $age = 20;
use eventTrait;
public function display() { $this->trigger('display_before', $this); echo 'name: ' .$this->name .'<br />'; echo 'age: ' .$this->age .'<br />'; $this->trigger('display_after', $this); } } You might ask, why not use inheritance? (class person extends eventObject). Sure, that would work but using traits allows your person class to extend other classes as well. In conclusion I hope that helps you get up and running with events! Now go make something awesome If you have any questions feel free to ask, feedback is welcome too of course!