Possible iphone animation timing/rendering bug?
- by David
Hi all, I have been working on an iphone apps for several weeks. Now I encounter an animation problem that I can't figure out how to resolve. Mayhbe you can help. Here is the details (a little long, bear with me):
Basically the effect I want to achieve is, when user click a button, a loading view pops up, hiding the whole screen; and then the apps does a lot of heavy computation, which takes a few seconds. Once the computation is done, soem result views (something likes checkers on a checker board) are rendered under the loading view. Once all result views are rendered, I used animation animation to remove the loading view nand show the result views to the user.
Here is what I do:
when user click a button, run this code:
[UIView beginAnimations:nil context:nil];
[UIView setAnimationDuration:1.0];
[UIView setAnimationBeginsFromCurrentState:YES];
[UIView setAnimationTransition:UIViewAnimationTransitionCurlDown forView:self.view cache:YES];
[UIView setAnimationDelegate:self];
[UIView setAnimationDidStopSelector:@selector(loadingViewInserted:finished:context:)];
// use a really high index number so it will always on top
[self.view insertSubview:loadingViewController.view atIndex:1000];
[UIView commitAnimations];
In the "loadingViewInserted" function, it calls another function doing the heavy computation work.
Once the computation is done, a lot of result views (like checkers on a checker board) are rendered under the loading view.
for(int colIndex = 1; colIndex <= result.columns; colIndex++) {
for(int rowIndex = 1; rowIndex <= result.rows; rowIndex++) {
ResultView *rv = [ResultView resultViewWithData:results[colIndex][rowIndex]];
[self.view addSubview:rv];
}
}
Once all result views are added, following animation is invoked to remove the loading view:
[UIView beginAnimations:nil context:nil];
[UIView setAnimationDuration:1.0];
[UIView setAnimationBeginsFromCurrentState:YES];
[UIView setAnimationTransition:UIViewAnimationTransitionCurlUp forView:self.view cache:YES];
[loadingViewController.view removeFromSuperview];
[UIView commitAnimations];
By doing this, most of the time (maybe 90%) it does exactly what I want. However, sometime I see some weird result: the loading view shows up first as expected, then before it disappears, some result views, which suppose to be under the loading view, suddenly appears on top of the loading view; and some of them are partial rendered. And then the loading view curled up, and everything looks normal again. The weird situation only lasts for less than a second, but already bad enough to screw up the UI.
I have tried all different kinds of thing to fix this (using another thread to remove the loading view, make the loading view non-transparent), but none of them works. The only thing that makes a little better is, I hide all the result views first; after the last animation finished, in its call back, unhide all result views. But this loses the nice effect that when curling up the loading view, the results are already there.
At this point, I really think this is a bug in iphone (I compile it with OS 3.0) OS. Or maybe you can point out what I have done wrong (or could do differently).
(thanks for finishing this long post, :-) )