1: <?php
2:
3: 4: 5: 6: 7: 8: 9: 10: 11:
12:
13:
14:
15: 16: 17: 18: 19: 20:
21: final class NObjectMixin
22: {
23:
24: private static $methods;
25:
26:
27:
28: 29: 30:
31: final public function __construct()
32: {
33: throw new NStaticClassException;
34: }
35:
36:
37:
38: 39: 40: 41: 42: 43: 44: 45:
46: public static function call($_this, $name, $args)
47: {
48: $class = new NClassReflection($_this);
49:
50: if ($name === '') {
51: throw new MemberAccessException("Call to class '$class->name' method without name.");
52: }
53:
54:
55: if ($class->hasEventProperty($name)) {
56: if (is_array($list = $_this->$name) || $list instanceof Traversable) {
57: foreach ($list as $handler) {
58: callback($handler)->invokeArgs($args);
59: }
60: } elseif ($list !== NULL) {
61: throw new UnexpectedValueException("Property $class->name::$$name must be array or NULL, " . gettype($list) ." given.");
62: }
63: return NULL;
64: }
65:
66:
67: if ($cb = $class->getExtensionMethod($name)) {
68: array_unshift($args, $_this);
69: return $cb->invokeArgs($args);
70: }
71:
72: throw new MemberAccessException("Call to undefined method $class->name::$name().");
73: }
74:
75:
76:
77: 78: 79: 80: 81: 82: 83: 84:
85: public static function callProperty($_this, $name, $args)
86: {
87: if (strlen($name) > 3) {
88: $op = substr($name, 0, 3);
89: $prop = strtolower($name[3]) . substr($name, 4);
90: if ($op === 'add' && property_exists($_this, $prop.'s')) {
91: $_this->{$prop.'s'}[] = $args[0];
92: return $_this;
93:
94: } elseif ($op === 'set' && property_exists($_this, $prop)) {
95: $_this->$prop = $args[0];
96: return $_this;
97:
98: } elseif ($op === 'get' && property_exists($_this, $prop)) {
99: return $_this->$prop;
100: }
101: }
102: self::call($_this, $name, $args);
103: }
104:
105:
106:
107: 108: 109: 110: 111: 112: 113: 114:
115: public static function callStatic($class, $name, $args)
116: {
117: throw new MemberAccessException("Call to undefined static method $class::$name().");
118: }
119:
120:
121:
122: 123: 124: 125: 126: 127: 128:
129: public static function & get($_this, $name)
130: {
131: $class = get_class($_this);
132:
133: if ($name === '') {
134: throw new MemberAccessException("Cannot read a class '$class' property without name.");
135: }
136:
137: if (!isset(self::$methods[$class])) {
138:
139:
140:
141:
142: self::$methods[$class] = array_flip(get_class_methods($class));
143: }
144:
145:
146: if (isset(self::$methods[$class][$name])) {
147: $val = create_function('', 'extract(NCFix::$vars['.NCFix::uses(array('_this'=>$_this,'name'=> $name)).'], EXTR_REFS);
148: return call_user_func_array(array($_this, $name), func_get_args());
149: ');
150: return $val;
151: }
152:
153:
154: $name[0] = $name[0] & "\xDF";
155: $m = 'get' . $name;
156: if (isset(self::$methods[$class][$m])) {
157:
158:
159:
160: $val = $_this->$m();
161: return $val;
162: }
163:
164: $m = 'is' . $name;
165: if (isset(self::$methods[$class][$m])) {
166: $val = $_this->$m();
167: return $val;
168: }
169:
170: $type = isset(self::$methods[$class]['set' . $name]) ? 'a write-only' : 'an undeclared';
171: $name = func_get_arg(1);
172: throw new MemberAccessException("Cannot read $type property $class::\$$name.");
173: }
174:
175:
176:
177: 178: 179: 180: 181: 182: 183: 184:
185: public static function set($_this, $name, $value)
186: {
187: $class = get_class($_this);
188:
189: if ($name === '') {
190: throw new MemberAccessException("Cannot write to a class '$class' property without name.");
191: }
192:
193: if (!isset(self::$methods[$class])) {
194: self::$methods[$class] = array_flip(get_class_methods($class));
195: }
196:
197:
198: $name[0] = $name[0] & "\xDF";
199:
200: $m = 'set' . $name;
201: if (isset(self::$methods[$class][$m])) {
202: $_this->$m($value);
203: return;
204: }
205:
206: $type = isset(self::$methods[$class]['get' . $name]) || isset(self::$methods[$class]['is' . $name])
207: ? 'a read-only' : 'an undeclared';
208: $name = func_get_arg(1);
209: throw new MemberAccessException("Cannot write to $type property $class::\$$name.");
210: }
211:
212:
213:
214: 215: 216: 217: 218: 219: 220:
221: public static function remove($_this, $name)
222: {
223: $class = get_class($_this);
224: throw new MemberAccessException("Cannot unset the property $class::\$$name.");
225: }
226:
227:
228:
229: 230: 231: 232: 233: 234:
235: public static function has($_this, $name)
236: {
237: if ($name === '') {
238: return FALSE;
239: }
240:
241: $class = get_class($_this);
242: if (!isset(self::$methods[$class])) {
243: self::$methods[$class] = array_flip(get_class_methods($class));
244: }
245:
246: $name[0] = $name[0] & "\xDF";
247: return isset(self::$methods[$class]['get' . $name]) || isset(self::$methods[$class]['is' . $name]);
248: }
249:
250: }
251: