%PDF- %PDF-
Direktori : /home/lightco1/upgrade.lightco.com.au/libraries/fof30/Event/ |
Current File : /home/lightco1/upgrade.lightco.com.au/libraries/fof30/Event/Dispatcher.php |
<?php /** * @package FOF * @copyright 2010-2017 Nicholas K. Dionysopoulos / Akeeba Ltd * @license GNU GPL version 2 or later */ namespace FOF30\Event; use FOF30\Container\Container; defined('_JEXEC') or die; class Dispatcher implements Observable { /** @var Container The container this event dispatcher is attached to */ protected $container = null; /** @var array The observers attached to the dispatcher */ protected $observers = array(); /** @var array Maps events to observers */ protected $events = array(); /** * Public constructor * * @param Container $container The container this event dispatcher is attached to */ public function __construct(Container $container) { $this->container = $container; } /** * Returns the container this event dispatcher is attached to * * @return Container */ public function getContainer() { return $this->container; } /** * Attaches an observer to the object * * @param Observer $observer The observer to attach * * @return Dispatcher Ourselves, for chaining */ public function attach(Observer $observer) { $className = get_class($observer); // Make sure this observer is not already registered if (isset($this->observers[$className])) { return $this; } // Attach observer $this->observers[$className] = $observer; // Register the observable events $events = $observer->getObservableEvents(); foreach ($events as $event) { $event = strtolower($event); if (!isset($this->events[$event])) { $this->events[$event] = array($className); } else { $this->events[$event][] = $className; } } return $this; } /** * Detaches an observer from the object * * @param Observer $observer The observer to detach * * @return Dispatcher Ourselves, for chaining */ public function detach(Observer $observer) { $className = get_class($observer); // Make sure this observer is already registered if (!isset($this->observers[$className])) { return $this; } // Unregister the observable events $events = $observer->getObservableEvents(); foreach ($events as $event) { $event = strtolower($event); if (isset($this->events[$event])) { $key = array_search($className, $this->events[$event]); if ($key !== false) { unset($this->events[$event][$key]); if (empty($this->events[$event])) { unset ($this->events[$event]); } } } } // Detach observer unset($this->observers[$className]); return $this; } /** * Is an observer object already registered with this dispatcher? * * @param Observer $observer The observer to check if it's attached * * @return boolean */ public function hasObserver(Observer $observer) { $className = get_class($observer); return $this->hasObserverClass($className); } /** * Is there an observer of the specified class already registered with this dispatcher? * * @param string $className The observer class name to check if it's attached * * @return boolean */ public function hasObserverClass($className) { return isset($this->observers[$className]); } /** * Returns an observer attached to this behaviours dispatcher by its class name * * @param string $className The class name of the observer object to return * * @return null|Observer */ public function getObserverByClass($className) { if (!$this->hasObserverClass($className)) { return null; } return $this->observers[$className]; } /** * Triggers an event in the attached observers * * @param string $event The event to attach * @param array $args Arguments to the event handler * * @return array */ public function trigger($event, array $args = array()) { $event = strtolower($event); $result = array(); // Make sure the event is known to us, otherwise return an empty array if (!isset($this->events[$event]) || empty($this->events[$event])) { return $result; } foreach ($this->events[$event] as $className) { // Make sure the observer exists. if (!isset($this->observers[$className])) { continue; } // Get the observer $observer = $this->observers[$className]; // Make sure the method exists if (!method_exists($observer, $event)) { continue; } // Call the event handler and add its output to the return value. The switch allows for execution up to 2x // faster than using call_user_func_array switch (count($args)) { case 0: $result[] = $observer->{$event}(); break; case 1: $result[] = $observer->{$event}($args[0]); break; case 2: $result[] = $observer->{$event}($args[0], $args[1]); break; case 3: $result[] = $observer->{$event}($args[0], $args[1], $args[2]); break; case 4: $result[] = $observer->{$event}($args[0], $args[1], $args[2], $args[3]); break; case 5: $result[] = $observer->{$event}($args[0], $args[1], $args[2], $args[3], $args[4]); break; default: $result[] = call_user_func_array(array($observer, $event), $args); break; } } // Return the observers' result in an array return $result; } /** * Asks each observer to handle an event based on the provided arguments. The first observer to return a non-null * result wins. This is a *very* simplistic implementation of the Chain of Command pattern. * * @param string $event The event name to handle * @param array $args The arguments to the event * * @return mixed Null if the event can't be handled by any observer */ public function chainHandle($event, $args = array()) { $event = strtolower($event); $result = null; // Make sure the event is known to us, otherwise return an empty array if (!isset($this->events[$event]) || empty($this->events[$event])) { return $result; } foreach ($this->events[$event] as $className) { // Make sure the observer exists. if (!isset($this->observers[$className])) { continue; } // Get the observer $observer = $this->observers[$className]; // Make sure the method exists if (!method_exists($observer, $event)) { continue; } // Call the event handler and add its output to the return value. The switch allows for execution up to 2x // faster than using call_user_func_array switch (count($args)) { case 0: $result = $observer->{$event}(); break; case 1: $result = $observer->{$event}($args[0]); break; case 2: $result = $observer->{$event}($args[0], $args[1]); break; case 3: $result = $observer->{$event}($args[0], $args[1], $args[2]); break; case 4: $result = $observer->{$event}($args[0], $args[1], $args[2], $args[3]); break; case 5: $result = $observer->{$event}($args[0], $args[1], $args[2], $args[3], $args[4]); break; default: $result = call_user_func_array(array($observer, $event), $args); break; } if (!is_null($result)) { return $result; } } // Return the observers' result in an array return $result; } }