0
votes

I am currently working on a demo, just to get to grips of how to make a game. It might turn into something in the future, but for now, it's just for learning.

My demo is, I guess, influenced by The Legend of Zelda. It has that top-down look that TLoZ has.

My sprite is a 32x32 pixel image, the demo runs at 60fps and I have already worked out how fast I want my sprite to animate using PyxelEdit. Each animation frame is being displayed every 170ms when my character walks. He moves 4 pixels every frame, so he is moving and animating at the speed I want him to.

The problem I have got is that I want my character to finish the animation loop when my key has been released and he won't. When I have released a movement key, he will sometimes stop on the wrong animation frame, like say his left or right foot is forward when I want him to be still. I'm just not sure how to do it. I've tried checking the animation count when the Event::KeyReleased event occurs and incrementing the animation count until it reaches a certain number so that it stops on say the number 1 so he's standing still, it just doesn't work.

I don't think this requires a look at my code, just need a general idea on how to go about making sure that when the a movement key is released, animate him until he is on frame 1 and move him a certain amount of pixels each time until he stops.

2

2 Answers

0
votes

You could use a FSM so something along the lines of.

// Visual states of the character.
enum class State { WALKING, STANDING, ATTACK, };
State character_state = State::STANDING;

// Change on input (or other things like impact.)
if(input.up() || input.down() || input.left() || input.right)
   character_state = State::WALKING;
else
   character_state = State::STANDING;

// Render based on the current state.
switch(character_state)
{
   case(State::WALKING):
      render(cycle_walk_animation(frame_time));
      break;
   case(State::STANDING):
      render(standing_still_frame());
      break;
}

I've done this with 2D and 3D.

0
votes

If I understand correctly, you need something like this:

// The game loop
while (game_running)
{
    // ...
    // Your code
    // ...

    // Advance the animation while moving, or if not, cycle through
    // the animation frames until frame 1 is reached
    if (keyPressed(somekey) || currentAnimationFrame != 1)
    {
        advanceAnimationFrame();
    }

    // ...
    // Your code
    // ...
}

Of course, this is not SFML code, but it should get the general idea across