Reputation: 3
I am creating an app which has around 15 different animations. Some animations are played on button taps while some are played on certain event. As I am new to cocos2d I just cannot figure out how to initialize these animations. I have separate sprite sheets for each animation. What I have done is created a convenience class that has as a data member, a CCSprite object. And in the init function I have placed all the code to create animations. But as soon as the init function is called I get memory warning.
I even tried to initialize the animations only when the request for playing the animation is sent, but I still get the memory warning. Also if I do so the animation doesn't play until the whole sprite sheet is loaded.
Please check the following code for reference
- (void)initEntryAnimation
{
[[CCSpriteFrameCache sharedSpriteFrameCache] addSpriteFramesWithFile:@"entry.plist"];
CCSpriteBatchNode *spriteSheet = [CCSpriteBatchNode batchNodeWithFile:@"entry.png"];
[self.sardarSprite addChild:spriteSheet];
NSMutableArray *entryFrames = [NSMutableArray array];
for(int i = 0; i < 77; i++) {
if([[CCSpriteFrameCache sharedSpriteFrameCache] spriteFrameByName:
[NSString stringWithFormat:@"enter in scene%04i.png", i+1]])
[entryFrames addObject:[[CCSpriteFrameCache sharedSpriteFrameCache] spriteFrameByName:
[NSString stringWithFormat:@"enter in scene%04i.png", i+1]]];
}
self.entryAnimation = [CCAnimation animationWithFrames:entryFrames delay:0.05f];
}
- (void)playEntryAnimation
{
[CCSpriteFrameCache purgeSharedSpriteFrameCache];
[self.sardarSprite runAction:[CCAnimate actionWithAnimation:self.entryAnimation restoreOriginalFrame:NO]];
}
I have created similar functions for all the 15 animations. I call all the initialization functions one after another. And the play functions are called whenever a request for the animation is sent.
I desperately need some expert advise. Any help would be highly appreciated.
Upvotes: 0
Views: 307
Reputation: 4276
The problem is the size of your sprite sheets. The sprite sheet file size (the size of the png) may be very small, but that is the size on disk. Once your app has loaded that into memory, it is stored uncompressed so that's 2048x2048x8 per sprite sheet.
You can reduce the colour depth to RGBA4444, for example which may help. See TexturePacker for more details. There are other tools available (I am not affiliated with TexturePacker in any way).
Other options you have are to reduce the colour depth further or to use one of the other formats available. You could also look at your animations and see if there is any way to break them down into more discrete components. For example, if you have an animation of a man running, perhaps instead of having the full screen frames, you could have one frame of the torso and then different leg animations and arm animations which you then use.
Without knowing the exact animation, it's difficult to advise.
Upvotes: 0
Reputation: 2256
Try adding NSAutoreleasePool like this
- (void)initEntryAnimation
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
[[CCSpriteFrameCache sharedSpriteFrameCache] addSpriteFramesWithFile:@"entry.plist"];
CCSpriteBatchNode *spriteSheet = [CCSpriteBatchNode batchNodeWithFile:@"entry.png"];
[self.sardarSprite addChild:spriteSheet];
NSMutableArray *entryFrames = [NSMutableArray array];
for(int i = 0; i < 77; i++) {
if([[CCSpriteFrameCache sharedSpriteFrameCache] spriteFrameByName:
[NSString stringWithFormat:@"enter in scene%04i.png", i+1]])
[entryFrames addObject:[[CCSpriteFrameCache sharedSpriteFrameCache] spriteFrameByName:
[NSString stringWithFormat:@"enter in scene%04i.png", i+1]]];
}
self.entryAnimation = [CCAnimation animationWithFrames:entryFrames delay:0.05f];
[pool release];
}
Upvotes: 0