First of all , I'm using cocos2d 3.6
Everything works well until I press right arrow key on keyboard which execute the startRunning() function from keypress event listener,actions stopped successfully but on the next line ,this->runAction(Animate::create( runAnimation));
, I get error.
runAnimation is OK.I guess the problem is in running new Action but I dont know what is it.
here's the code:
#pragma once
#include "cocos2d.h"
using namespace cocos2d;
const int DIR_RIGHT = 1;
const int DIR_LEFT = -1;
class CPlayer: public Sprite
{
private:
Animation* idleAnimation;
Animation* runAnimation;
Animation* bowAnimation;
Animation* climbAnimation;
SpriteFrame* jumpFrame;
SpriteFrame* fallFrame;
SpriteFrame* wallJumpFrame;
boolean onGround = true;
boolean running = false;
int dir = DIR_RIGHT;
float movementSpeed = 50; //50 unit in world space
float stateTime=0;
public:
Animation* createAnimation(const char* format, float delay, bool loop){
Animation* animation = Animation::create();
char str[100] = { 0 };
int frameIndex = 1;
do
{
sprintf(str, format, frameIndex);
auto frame = SpriteFrameCache::getInstance()->getSpriteFrameByName(str);
if (frame == NULL)
break;
animation->addSpriteFrame(frame);
Texture2D::TexParams texParams = { GL_NEAREST, GL_NEAREST, GL_CLAMP_TO_EDGE, GL_CLAMP_TO_EDGE };
frame->getTexture()->setTexParameters(texParams);
frameIndex++;
} while (true);
int loops = 1;
if (loop)
loops = -1;
animation->setDelayPerUnit(delay);
animation->setLoops(loops);
return animation;
}
CPlayer(){
idleAnimation = createAnimation("Idle/player_idle_%d.png", .2f, -1);
runAnimation = createAnimation("Run/player_run_%d.png", .5f, -1);
bowAnimation = createAnimation("Bow/bow_%d.png", .2f, -1);
climbAnimation = createAnimation("Climb/player_climb_%d.png", .2f, -1);
jumpFrame = SpriteFrameCache::getInstance()->getSpriteFrameByName("Fall-Jump-WallJ/player_climb_jump.png");
fallFrame = SpriteFrameCache::getInstance()->getSpriteFrameByName("Fall-Jump-WallJ/player_climb_fall.png");
wallJumpFrame = SpriteFrameCache::getInstance()->getSpriteFrameByName("Fall-Jump-WallJ/player_climb_wall_jump.png");
this->runAction(Animate::create(idleAnimation));
}
CREATE_FUNC(CPlayer);
void startRunning(){
running = true;
if (onGround){
this->stopAllActions();
this->runAction(Animate::create( runAnimation));
}
}
void endRunning(){
running = false;
if (onGround){
this->stopAllActions();
this->runAction(Animate::create(idleAnimation));
}
}
void update(float delta){
stateTime += delta;
if (onGround && running){
this->setPositionX(this->getPositionX() + delta* movementSpeed*dir);
}
}
void headToRight(){
this->setFlipX(false);
dir = DIR_RIGHT;
}
void headToLeft(){
this->setFlippedX(true);
dir = DIR_LEFT;
}
};
Your createAnimation method returns an autoreleased animation object, which is released before you use it.
To fix this issue you need to retain your autoreleased objects after you create them, and release them in destructor or when you don't need them no more:
CPlayer(){
idleAnimation = createAnimation("Idle/player_idle_%d.png", .2f, -1);
runAnimation = createAnimation("Run/player_run_%d.png", .5f, -1);
bowAnimation = createAnimation("Bow/bow_%d.png", .2f, -1);
climbAnimation = createAnimation("Climb/player_climb_%d.png", .2f, -1);
idleAnimation->retain();
runAnimation->retain();
bowAnimation->retain();
climbAnimation->retain();
jumpFrame = SpriteFrameCache::getInstance()->getSpriteFrameByName("Fall-Jump-WallJ/player_climb_jump.png");
fallFrame = SpriteFrameCache::getInstance()->getSpriteFrameByName("Fall-Jump-WallJ/player_climb_fall.png");
wallJumpFrame = SpriteFrameCache::getInstance()->getSpriteFrameByName("Fall-Jump-WallJ/player_climb_wall_jump.png");
this->runAction(Animate::create(idleAnimation));
}
virtual ~CPlayer() {
idleAnimation->release();
runAnimation->release();
bowAnimation->release();
climbAnimation->release();
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With