Game Development Reference
In-Depth Information
{
CCNode* aParent = self.parent;
do
{
if ([aParent respondsToSelector:_cmd])
{
[aParent performSelector:_cmd];
break;
}
aParent = aParent.parent;
}
while (aParent != nil);
}
@end
The
shouldClose
method takes the button's parent before entering the
do/while
loop. It checks if the parent responds to the
_cmd
selector, which refers to the
shouldClose
selector. The use of
_cmd
simply makes it easier to use this code in other
buttons—you don't have to update the code to use each specific selector. In fact, this code
cries out to be added to a class method like in the
SceneManager
, or maybe a category
on
CCNode
. I'll leave this as an exercise for you.
If the given parent does respond to the same selector, that selector is performed and the
loop ends at the
break
statement. Otherwise, the
aParent
variable is set to
aPar-
ent
's parent, traversing ever closer toward the
CCScene
instance in the node hierarchy.
If, in fact, the
CCScene
instance is reached before a parent implementing the given se-
lector was found, the loop will also end because the scene's
parent
is guaranteed to be
nil
.
Tip
As with the previous use of
performSelector
, you can ignore the
“may cause a leak” warning since the selector does not return an object. (It re-
turns
void
.)
You can get rid of the warning by using
[aParent performSelect-
or:_cmd withObject:nil afterDelay:0]
instead. This tells the
compiler to set up a timer which, in turn, performs the selector when it fires.
When a timer is involved, there can't be a value returned by the selector; there-
fore, the compiler stops complaining. The extraneous
nil
object sent as para-
Search WWH ::
Custom Search