Reputation: 241
I am using the second part of the iphone games tutorial, and I am confused about the ccTouchesEnded
method's implementation. It is where the 'shooting' is implemented: the player (a cannon) is turned to the touched direction, and the projectile is shot.
The part that's unclear to me is: _nextProjectile
seems to be released while it could still be in use (by the code right below it - _nextProjectile runAction
).
Could you please explain why is it safe to release the object at this point?
- (void)ccTouchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
[_player runAction:
[CCSequence actions:
[CCRotateTo actionWithDuration:rotateDuration angle:cocosAngle],
[CCCallBlock actionWithBlock:^{
// OK to add now - rotation is finished!
[self addChild:_nextProjectile];
[_projectiles addObject:_nextProjectile];
// Release
[_nextProjectile release];
_nextProjectile = nil;
}],
nil]];
// Move projectile to actual endpoint
[_nextProjectile runAction:
[CCSequence actions:
[CCMoveTo actionWithDuration:realMoveDuration position:realDest],
[CCCallBlockN actionWithBlock:^(CCNode *node) {
[_projectiles removeObject:node];
[node removeFromParentAndCleanup:YES];
}],
nil]];
}
Upvotes: 2
Views: 164
Reputation: 2581
Earlier on in ccTouchesEnded:withEvent: you increased the retain count of _nextProjectile on this line:
_nextProjectile = [[CCSprite spriteWithFile:@"projectile2.png"] retain];
So at some point later on you have to decrease the retain count to prevent a memory leak. In other words: you are responsable for releasing this retain. That is where this line is coming from:
[_nextProjectile release];
Why is it safe to release it at that point? The pieces of code you posted in your question are both actually actions in a sequence of actions.
[_player runAction:[CCSequence actions:...]];
Performing an action on an object increases the retain count on that object. This means the action object itself creates and holds another reference to _nextProjectile. The sequence of actions is created before the actions are actually performed, hence the action object already has its own reference to _nextProjectile. So releasing it in one of the actions is actually safe. They waited with releasing _nextProjectile until these lines passed:
[self addChild:_nextProjectile];
[_projectiles addObject:_nextProjectile];
A release before these lines would probably (I haven't looked at any other code than ccTouchesEnded:withEvent:) result in a EXC_BAD_ACCESS runtime error.
Here is some more info about the retain count: cocos2d forum
Upvotes: 1