I been working in the animation of a 2D platformer game in C++/SDL/OpenGL, and my team and I reach the point where we need to establish that every animation of the player (Walking, Running, etc..) needs a different framerate for our concept, but I use as a guideline the Game Programming All In One as a example for the smooth animation, and in the book recommend have variables that limits the movement and the changes of frames.
To clarify what I mean I have in my Sprite class these parameters:
std::vector< Vector2f > delayMovementSprite;
std::vector< int > frameDelayPerAnimation;
GLfloat countX, countY;
Where the vector delayMovementSprite contains all the values for the differents animations and countX increment in every frame until it's equal or greater than the value that correspond in the vector delayMovementSprite.
Something like this:
void Sprite::movePosXWithSpeed()
{
playerMoveInX = false || playerMoveInX;
countX++;
if ( countX > delayMovementSprite.at(getCurrentState()).x )
{
countX = 0;
if ( handlerAnimation->getAnimationDirection() == SpriteData::RIGHT )
{
if ( position.x + getSpeedX() + width < 6368.f )
{
position.x += getSpeedX();
playerMoveInX = true;
return;
}
}
else if ( position.x + getSpeedX() + width > 0 )
{
position.x += getSpeedX();
playerMoveInX = true;
return;
}
playerMoveInX = false;
}
}
And for the frames I have a class Animation which handles the following information:
Uint32 frameRate, oldTime;
int frameDelay;
int frameCount;
And in the function that animates I do the following, much like the MoveX in Sprite:
int Animation::animate()
{
if( oldTime + frameRate > SDL_GetTicks() )
{
return -1;
}
oldTime += frameRate;
frameCount++;
if ( frameCount > frameDelay )
{
animationAlreadyEnd = false;
frameCount = 0;
currentFrame += incrementFrame;
if( currentFrame > maxFrames)
{
animationAlreadyEnd = true;
currentFrame = returnFrame;
}
}
return currentFrame;
}
I got working all that and everything executes apparently fine, but in some points of the game the animation doesn't look really smooth when in other points it is.
I leave the video of the "gameplay" so everyone could see what I mean.
http://www.youtube.com/watch?v=uoxKEYzwkcQ
I currently using during the execution of the game a general Timer in 60 FPS.
If anyone needs more information, don't hesitate in ask.
At first look Animation::animate
doesn't look right. Let me explain: Assuming you have a fixed display frame rate (for a sprite based game this will hold), you want a linear mapping from frame counter to sprite frame. If you graph this, this was a line. And in this case one over a discrete sampling grid. Whenever one thinks "discrere line sampling" one should think "Bresenham", and in fact you can and should use Bresenham's algorithm for advancing your animation, if you want to keep a incremental scheme. The other possibility was, simply evaluating the affine equation f_anim = framerate_anim/framerate_game * (framecounter_game - startframe_animation)
.