Search code examples
objective-cuikitcore-animation

UIKit game: A middle callback during game object movement animation


Currently, I'm building a game with pure UIKit. It's a game where some character is catching falling items. All the objects are moving along the three points trajectory: each object appear at point A, then move to point B and then fall to point C. For me, it is important only one moment - item in point B. I need to check, does the character is catching the item in point B. Currently, I have a timer in the main game controller that is constantly posting notifications. Game items are observers, they listen to that notification and reposition themselves (they move themselves). Now, with that timer, each item is moving by the small steps from point A to point B. When it is at point B, an item method checks, does the character is catching him. If no then I'm performing UIView animation with duration from point B to point C.

I'm thinking that the whole movement could be animated, maybe with Core Animation CAKeyframeAnimation class or smth. The only problem is, I'm not sure about how to fire a callback for checking the catch in the middle of animation - in the point B. Some say that it is impossible here and if I have the whole animation and I need to get current item position then I need to have a timer that is regularly pulling/reading the model data from presentationLayer. But I'm not sure about this approach because, now, I do not store a pointer to screen items from my main game controller - the game controller only creates an item and game timer posts notifications to those objects. But I would need to have such one in order to implement proposed solution. Also, I should read the presentationLayer from the whole bunch of screen items.

The another alternative would be to split one animation into two animations: first, animate from A to B and then to fire a completion callback for checking a catch. Then, perform another animation from B to C.

Guys, what are your opinions on that, maybe you have another proposals?


Solution

  • I think you need to split it into two animations. It's correct that you only haveanimationDidStartandanimationDidStopdelegate methods withCAAnimation. The approach to use anNSTimercould be problematic. presentationLayer values will be updated on the main thread. My guess would be that checking thepresentationLayervalues on a different thread where the timer is running could give incorrect values.

    You could get around that by usingperformSelectorOnMainThread. Then, the issue would be reliable scheduling of that method invocation. I.e., when you invoke performSelectorOnMainThread, it is up to the runtime to execute that at it's convenience.

    For the record, I'm also writing a game in pure UIKit. The biggest headache hasn't been the animations during normal play. Instead, it's stopping and resuming them during interruptions such as pausing the game, accepting calls, moving to background, etc. Especially a purge from memory while the game is in background.

    I've written a bit about this in the answer to this question:

    Restoring animation where it left off when app resumes from background

    Consequently, for the next game I'm going to have a close look at cocos2d to see what it offers in this regard.