I need to play frame based animations. I tried the UIImageView with animationImages but it doesn't give me any control over my animation. I can't pause it, I can't mask it, I can't know the current frame etc.
So I subclassed UIView and created something I called AnimationView which takes the array of images and does the animation using an NSTimer. In the drawRect: I can then do all the masking and everything else I want.
However this method is way too slow. I can't run an animation at 30fps, maybe not even at 10fps and I am testing on a 3GS. (I am only doing masking and blending on every frame :) - and using the same images plays fine at 30fps on a UIImageView).
So, what is the most efficient way to achieve this? Is the NSTimer a bad choice? Is there a better way around it?
Thanks :)
In this answer to this question Mo DeJong provides a link to a source code implementation of a class that manually animates PNG image frames. He claims to get 15 FPS for 480x320 images animating on a non-3GS iPhone.
The NSTimer is fine. The problem is that you're touching a lot of pixels using the CPU in every frame using Quartz (the drawRect:). What you want to do is either use OpenGL if you have to compose images using a mask or cache your images in CALayers or CGImages.
Related
I'm trying to create a crossword app. The game runs in a UIScrollView, because the player should be able to zoom, scroll etc. The largest crossword are 21x21 which means there need to be 441 touchable tiles. What i've tried so far were to create an UIView and added it as a subView to the UIScrollView. Then I call a method that creates 441 custom UIButtons and set the backgroundImage.
Some of the UIButtons need to have a custom label overlay, so i added a UILabel and set it on top of the UIButton.
When I run the app in simulator all works as it should, but when i test it on an iPhone 4 the UIScrollView lags a lot.
I don't know if this the way to do it? Can you maybe try to guide me in the right direction of how to do this so the UIScrollView won't lag on a device.
Thanks in advance.
Big UIScrollViews are difficult to make smooth without some sort of caching mechanism, such as the one provided by UITableView.
One thing you can do, however, to make life easier for your rendering, is to make sure to use opaque backgrounds whenever possible. In stead of making a view transparent you should make it the same color as its underlying view. This is something that does help.
Also, I have experienced better performance using imageWithContentsOfFile: in stead of imageNamed: for initializing images to be used in a UIScrollView.
In order to not keep all those buttons in memory, you should work with reusable table view cells, this will really improve the scroll performance. Here's one component that could make your life easier: DTGridView, there are also others (you can check Cocoa Controls)
I can not animate many images with animationImages and startAnimating as it uses too much memory and crashes. What is the best way to animate 100 images in a portion of my iPhone screen (not full screen)? Is there an example?
I think you have two solutions :
1°) Subclass UIView and in the drawRect you draw each time another image. You add a NSTimer to create the animation ^^
2°) Do the same as 1°) but with OpenGL ^^
Good Luck ! :-)
I got a UIView subclass that draws a UIImage as its background. The image is created using the stretchableImageWithLeftCapWidth:topCapHeight: method, it has round edges.
I also use an animation block inside of which I resize my view. I had hoped that during animation, the drawRect:method would get called sometimes, which would result in the background image getting drawn correctly.
Unfortunately, the animation seems to render the image and then just rescale it during the animation, which obviously makes the formerly round edges getting nastily stretched.
The only workaround I can imagine is put three separate UIImageViews (top cap, middle fill, bottom cap) above my original background image and then reposition the caps images and scaling the fill image. However, this seems quite complicated...
Is there any better way I can prevent this from happening?
EDIT: Found this. Sounds bad...
While digging through some Apple docs, I coincidentally found the solution to my problem. All you have to do is play with UIView's contentStretch parameter. It allows you to manually specify the area of your view that gets stretched during animation.
I'm trying to display a series of images in a animation where the duration between the images changes frame to frame. I can successfully animate images where the duration is the same. I've looked into subclassing UIImageView but it doesn't seem to allow you access anything that could be helpful.
I've also looked into subclassing UIView directly but it seems like I'd have to write a lot of the stuff that UIImageView already does for me.
Is there a way to do this with UIImageView? Or if I am going to have to build my own UIView animation can someone point me the right direction to get started? Thanks.
You could have many UIImageViews next to one another, each representing one image, and animate them inside a UIView or UIScrollView, depending on what exactly you need to do. Animations with the help of UIView are very straightforward to implement.
Is there anything faster than UIView Animations? Mine are not keeping up,
I want to play a series of images, very fast. (i.e 10 in 80 milliseconds)
Any ideas?
As usual, greatly appreciated.
Sam
If you are looking for a replacement for UIImageView's animationImages property, the second example on this page presents an alternative (as pointed out in this question).
Do you mean the UIImageView animation images? Do you want transitions between your images? If not, there is no reason to use UIView Animations.
Now to play frame-based animations, I would suggest using the UIImageView object and add your images in its animationImages array. Not sure it will keep up with the framerates you require of course, especially if the images are large.