1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196
|
<?php //-*-php-*-
rcs_id('$Id: WikiCallback.php,v 1.3 2004/11/01 10:43:56 rurban Exp $');
/**
* A callback
*
* This is a virtual class.
*
* Subclases of WikiCallback can be used to represent either
* global function callbacks, or object method callbacks.
*
* @see WikiFunctionCb, WikiMethodCb.
*/
class WikiCallback
{
/**
* Convert from Pear-style callback specification to a WikiCallback.
*
* This is a static member function.
*
* @param $pearCb mixed
* For a global function callback, $pearCb should be a string containing
* the name of the function.
* For an object method callback, $pearCb should be a array of length two:
* the first element should contain (a reference to) the object, the second
* element should be a string containing the name of the method to be invoked.
* @return object Returns the appropriate subclass of WikiCallback.
* @access public
*/
function callback ($pearCb) {
if (is_string($pearCb))
return new WikiFunctionCb($pearCb);
else if (is_array($pearCb)) {
list($object, $method) = $handler;
return new WikiMethodCb($object, $method);
}
trigger_error("WikiCallback::new: bad arg", E_USER_ERROR);
}
/**
* Call callback.
*
* @param ? mixed This method takes a variable number of arguments (zero or more).
* The callback function is called with the specified arguments.
* @return mixed The return value of the callback.
* @access public
*/
function call () {
return $this->call_array(func_get_args());
}
/**
* Call callback (with args in array).
*
* @param $args array Contains the arguments to be passed to the callback.
* @return mixed The return value of the callback.
* @see call_user_func_array.
* @access public
*/
function call_array ($args) {
trigger_error('pure virtual', E_USER_ERROR);
}
/**
* Convert to Pear callback.
*
* @return string The name of the callback function.
* (This value is suitable for passing as the callback parameter
* to a number of different Pear functions and methods.)
* @access public
*/
function toPearCb() {
trigger_error('pure virtual', E_USER_ERROR);
}
}
/**
* Global function callback.
*/
class WikiFunctionCb
extends WikiCallback
{
/**
* Constructor
*
* @param $functionName string Name of global function to call.
* @access public
*/
function WikiFunctionCb ($functionName) {
$this->functionName = $functionName;
}
function call_array ($args) {
return call_user_func_array($this->functionName, $args);
}
function toPearCb() {
return $this->functionName;
}
}
/**
* Object Method Callback.
*/
class WikiMethodCb
extends WikiCallback
{
/**
* Constructor
*
* @param $object object Object on which to invoke method.
* @param $methodName string Name of method to call.
* @access public
*/
function WikiMethodCb(&$object, $methodName) {
$this->object = &$object;
$this->methodName = $methodName;
}
function call_array ($args) {
$method = &$this->methodName;
//$obj = &$this->object;
// This should work, except PHP's before 4.0.5 (which includes mine)
// don't have 'call_user_method_array'.
if (check_php_version(4,0,5)) {
return call_user_func_array(array(&$this->object, $method), $args);
}
// This should work, but doesn't. At least in my PHP, the object seems
// to get passed by value, rather than reference, so any changes to the
// object made by the called method get lost.
/*
switch (count($args)) {
case 0: return call_user_method($method, $obj);
case 1: return call_user_method($method, $obj, $args[0]);
case 2: return call_user_method($method, $obj, $args[0], $args[1]);
case 3: return call_user_method($method, $obj, $args[0], $args[1], $args[2]);
case 4: return call_user_method($method, $obj, $args[0], $args[1], $args[2], $args[3]);
default: trigger_error("Too many arguments to method callback", E_USER_ERROR);
}
*/
// This seems to work, at least for me (so far):
switch (count($args)) {
case 0: return $this->object->$method();
case 1: return $this->object->$method($args[0]);
case 2: return $this->object->$method($args[0], $args[1]);
case 3: return $this->object->$method($args[0], $args[1], $args[2]);
case 4: return $this->object->$method($args[0], $args[1], $args[2], $args[3]);
default: trigger_error("Too many arguments to method callback", E_USER_ERROR);
}
}
function toPearCb() {
return array($this->object, $this->methodName);
}
}
/**
* Anonymous function callback.
*/
class WikiAnonymousCb
extends WikiCallback
{
/**
* Constructor
*
* @param $args string Argument declarations
* @param $code string Function body
* @see create_function().
* @access public
*/
function WikiAnonymousCb ($args, $code) {
$this->function = create_function($args, $code);
}
function call_array ($args) {
return call_user_func_array($this->function, $args);
}
function toPearCb() {
trigger_error("Can't convert WikiAnonymousCb to Pear callback",
E_USER_ERROR);
}
}
// (c-file-style: "gnu")
// Local Variables:
// mode: php
// tab-width: 8
// c-basic-offset: 4
// c-hanging-comment-ender-p: nil
// indent-tabs-mode: nil
// End:
?>
|