Welcome, Guest. Please login or register. Did you miss your activation email?

Author Topic: [SFML 2.1] Sprite animation not playing  (Read 8489 times)

0 Members and 2 Guests are viewing this topic.

devilswin

  • Newbie
  • *
  • Posts: 38
    • View Profile
    • Email
[SFML 2.1] Sprite animation not playing
« on: December 04, 2014, 06:07:16 pm »
Hello, I am wondering how, with the program i have at the movement, to move the character who is smaller than the size of each tile to the end of the tile. At about line 512 in the main.cpp is where i move the sprite in a loop. The issue is that the animation does not play when he moves. It is chopped up and looks like he is flying across the map. I was wondering if anyone knew a fix or a better way to this. Whenever i use the sprites getLocalBounds() my program gets numerous memory leaks. I am using an Animated Sprite by Laurent Gomila to animate the sprite.

My code: https://github.com/devilswin/path_finder
Edit: Scroll down to other replies to find shorter amounts of code
« Last Edit: December 12, 2014, 07:18:10 pm by devilswin »

eXpl0it3r

  • SFML Team
  • Hero Member
  • *****
  • Posts: 11034
    • View Profile
    • development blog
    • Email
Re: [SFML 2.1] Sprite animation not playing
« Reply #1 on: December 05, 2014, 10:52:40 am »
If you want help, create a minimal and complete example, we won't go through your whole code base just to understand what's going on.

If you mean, that your animation is slower than it should be, you should increase the animations "fps".
Official FAQ: https://www.sfml-dev.org/faq.php
Official Discord Server: https://discord.gg/nr4X7Fh
——————————————————————
Dev Blog: https://duerrenberger.dev/blog/

devilswin

  • Newbie
  • *
  • Posts: 38
    • View Profile
    • Email
Re: [SFML 2.1] Sprite animation not playing
« Reply #2 on: December 05, 2014, 02:16:48 pm »
Ok, if i get time then i will try to recreate the example...but the issue isn't the animation is slow. It is that it is skipping frames. What i mean is that the character will move(position wise) but won't show the character animation.
 
Edit: Here are the exact lines of code where i do all of the moving, tell me if you see anything wrong, this is where i believe the bug is...

for(int i = 0; i < x_tileSize; i++)
        {
            for(int q = 0; q < 3; q++)
            animatedSprite.play(*currentAnimation);
            animatedSprite.move(sf::Vector2f(movement.x,0));
           
        }
        for(int i = 0; i < y_tileSize; i++)
        {
            for(int q = 0; q < 3; q ++ )
                animatedSprite.play(*currentAnimation);
            animatedSprite.move(sf::Vector2f(0,movement.y));
           
           
        }
« Last Edit: December 05, 2014, 02:30:16 pm by devilswin »

devilswin

  • Newbie
  • *
  • Posts: 38
    • View Profile
    • Email
Re: [SFML 2.1] Sprite animation not playing
« Reply #3 on: December 05, 2014, 02:27:23 pm »
Here ill explain what i am doing in short and see if anyone knows where i am going wrong...I make an aster path for a sprite to follow...It is in the form of a string of numbers...That string of numbers will be interpreted as a set of movements to execute. Then since the Astar algorithm does not find the parth for each individual pixel, rather a set of integers that represents a tile map. Because of this, i must use a for loop to move the character the length of the tile...however when i do that , it does not play the animation

Arcade

  • Full Member
  • ***
  • Posts: 230
    • View Profile
Re: [SFML 2.1] Sprite animation not playing
« Reply #4 on: December 06, 2014, 12:00:17 am »
It would help more if you provided a full example that replicates your problem, but I'll take a stab at it anyway.

I don't really know anything about this animateSprite class, but I took a quick look at the source on the wiki. Looking at your code I see a few potential problems.

  • Why is play being called 3 times in a loop. It looks like the only thing play does is set a flag saying the animation isn't paused. If your current animation isn't changing you probably only need to call play once before any of your loops.
  • The wiki examples shows that you should be calling animatedSprite.update() somewhere. Are you doing that?(this is an example of why a more complete example of what you have would be useful for us  ;))
  • What is movement.x and movement.y? Why are you nudging the sprite by those amounts in a loop without drawing anything on the screen in between?
Hopefully one of those questions will help you find what is going wrong  ;)

StormWingDelta

  • Sr. Member
  • ****
  • Posts: 365
    • View Profile
Re: [SFML 2.1] Sprite animation not playing
« Reply #5 on: December 06, 2014, 05:17:31 pm »
Shouldn't there be a way to combine those two loops into one?  Haven't messed around with the animation code all that much but it looks like you can make your X Loop and Y Loop into one for the tiles at least.
I have many ideas but need the help of others to find way to make use of them.

devilswin

  • Newbie
  • *
  • Posts: 38
    • View Profile
    • Email
Re: [SFML 2.1] Sprite animation not playing
« Reply #6 on: December 08, 2014, 04:42:20 pm »
Here is the shortest possible code i could come up with to reproduce the problem:
#include <iostream>
#include <iomanip>
#include <queue>
#include <string>
#include <math.h>
#include <ctime>
#include <SFML/Graphics.hpp>
#include <vector>
#include <memory>
#include <stdlib.h>
#include <stdio.h>
#include "Animation.hpp"
#include "AnimatedSprite.hpp"
#include <chrono>
#include <thread>
class TileMap : public sf::Drawable, public sf::Transformable
{
public:
 
    bool load(const std::string& tileset, sf::Vector2u tileSize, const int* tiles, unsigned int width, unsigned int height)
    {
        // load the tileset texture
        if (!m_tileset.loadFromFile(tileset))
            return false;
     
        // resize the vertex array to fit the level size
        m_vertices.setPrimitiveType(sf::Quads);
        m_vertices.resize(width * height * 4);
     
        // populate the vertex array, with one quad per tile
        for (unsigned int i = 0; i < width; ++i)
            for (unsigned int j = 0; j < height; ++j)
            {
                // get the current tile number
                int tileNumber = tiles[i + j * width];
             
                // find its position in the tileset texture
                int tu = tileNumber % (m_tileset.getSize().x / tileSize.x);
                int tv = tileNumber / (m_tileset.getSize().x / tileSize.x);
             
                // get a pointer to the current tile's quad
                sf::Vertex* quad = &m_vertices[(i + j * width) * 4];
             
                // define its 4 corners
                quad[0].position = sf::Vector2f(i * tileSize.x, j * tileSize.y);
                quad[1].position = sf::Vector2f((i + 1) * tileSize.x, j * tileSize.y);
                quad[2].position = sf::Vector2f((i + 1) * tileSize.x, (j + 1) * tileSize.y);
                quad[3].position = sf::Vector2f(i * tileSize.x, (j + 1) * tileSize.y);
             
                // define its 4 texture coordinates
                quad[0].texCoords = sf::Vector2f(tu * tileSize.x, tv * tileSize.y);
                quad[1].texCoords = sf::Vector2f((tu + 1) * tileSize.x, tv * tileSize.y);
                quad[2].texCoords = sf::Vector2f((tu + 1) * tileSize.x, (tv + 1) * tileSize.y);
                quad[3].texCoords = sf::Vector2f(tu * tileSize.x, (tv + 1) * tileSize.y);
            }
     
        return true;
    }
 
private:
 
    virtual void draw(sf::RenderTarget& target, sf::RenderStates states) const
    {
        // apply the transform
        states.transform *= getTransform();
     
        // apply the tileset texture
        states.texture = &m_tileset;
     
        // draw the vertex array
        target.draw(m_vertices, states);
    }
 
    sf::VertexArray m_vertices;
    sf::Texture m_tileset;
};
int main()
{
    // create the window
    sf::Vector2i map_dim(512,256);
    sf::RenderWindow window(sf::VideoMode(map_dim.x, map_dim.y), "Tilemap");
    sf::Texture texture;
    // window.setFramerateLimit(60);
    if (!texture.loadFromFile("FFSPRITE.gif"))
    {
        std::cout << "Failed to load player spritesheet!" << std::endl;
        return 1;
    }
   
   
   
   
    bool has_clicked = false;
   
    // set up tshe animations for all four directions (set spritesheet and push frames)
    Animation walkingAnimationDown;
    walkingAnimationDown.setSpriteSheet(texture);
    walkingAnimationDown.addFrame(sf::IntRect(47,5, 16,16)    );
    walkingAnimationDown.addFrame(sf::IntRect(65,5,16, 16)     );
    walkingAnimationDown.addFrame(sf::IntRect(47,5, 16,16)    );
   
    Animation walkingAnimationLeft;
    walkingAnimationLeft.setSpriteSheet(texture);
    walkingAnimationLeft.addFrame(sf::IntRect(83,5, 13,16 ) );
    walkingAnimationLeft.addFrame(sf::IntRect(98,5,14,16));
    walkingAnimationLeft.addFrame(sf::IntRect(83,5,13,16));
   
   
    Animation walkingAnimationRight;
    walkingAnimationRight.setSpriteSheet(texture);
    walkingAnimationRight.addFrame(sf::IntRect(150,5, 13, 16) );
    walkingAnimationRight.addFrame(sf::IntRect(165,5,14, 16)  );
    walkingAnimationRight.addFrame(sf::IntRect(150,5,13,16)   );
   
    Animation walkingAnimationUp;
    walkingAnimationUp.setSpriteSheet(texture);
    walkingAnimationUp.addFrame(sf::IntRect(114, 5, 16, 16));
    walkingAnimationUp.addFrame(sf::IntRect(132, 5, 16, 16));
    walkingAnimationUp.addFrame(sf::IntRect(114, 5, 16, 16));
   
   
    Animation* currentAnimation = &walkingAnimationDown;
   
    // set up AnimatedSprite
    AnimatedSprite animatedSprite(sf::seconds(0.2), true, false);
   
    animatedSprite.setPosition(sf::Vector2f(4.0*32.0,7.0*32.0));
    sf::Clock frameClock;
   
    float speed = 1.f;
    bool noKeyWasPressed = true;
    // define the level with an array of tile indices
    const int level[] =
    {
        0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
        0, 1, 1, 1, 3, 3, 3, 3, 0, 0, 0, 2, 0, 0, 0, 0,
        1, 1, 0, 0, 3, 0, 0, 3, 0, 3, 3, 3, 3, 3, 3, 3,
        0, 3, 3, 3, 3, 0, 3, 3, 0, 3, 1, 1, 1, 0, 0, 0,
        0, 3, 1, 0, 2, 2, 3, 0, 0, 3, 1, 1, 1, 2, 0, 0,
        0, 3, 1, 0, 2, 0, 3, 2, 0, 3, 1, 1, 1, 1, 2, 0,
        2, 3, 1, 0, 2, 0, 3, 2, 2, 3, 1, 1, 1, 1, 1, 1,
        0, 3, 3, 3, 3, 2, 3, 3, 3, 3, 0, 0, 1, 1, 1, 1,
    };
   
   
   string route = "445667077012322107666700000";
    // create the tilemap from the level definition
    TileMap map;
    if (!map.load("tileset.png", sf::Vector2u(32, 32), level, 16, 8))
        return -1;
   
    animatedSprite.play(*currentAnimation);
    sf::FloatRect as = animatedSprite.getGlobalBounds();
    // run the main loop
    while (window.isOpen())
    {
       
        sf::Event event;
        char ada;
        int qx;
        if(count < route.length())
        {
            ada = route.at(count);
            qx = atoi(&ada);
            count += 1;
        }
        while (window.pollEvent(event))
        {
            if (event.type == sf::Event::Closed)
                window.close();
            if (event.type == sf::Event::KeyPressed && event.key.code == sf::Keyboard::Escape)
                window.close();
        }
       
        sf::Time frameTime = frameClock.restart();
       
        // if a key was pressed set the correct animation and move correctly
        sf::Vector2f movement(0.f, 0.f);
       
       
        if (qx == 6)
        {
            currentAnimation = &walkingAnimationUp;
            movement.y -= speed;
            noKeyWasPressed = false;
        }
       
        if (qx == 2)
        {
            currentAnimation = &walkingAnimationDown;
            movement.y += speed;
            noKeyWasPressed = false;
        }
       
       
        if(qx == 4)
        {
            currentAnimation = &walkingAnimationLeft;
            movement.x -= speed;
            noKeyWasPressed = false;
        }
       
       
        if (qx == 0)
        {
            currentAnimation = &walkingAnimationRight;
            movement.x += speed;
            noKeyWasPressed = false;
        }
        if (qx == 1)
        {
            currentAnimation = &walkingAnimationDown;
            movement.y += speed;
            movement.x += speed;
            noKeyWasPressed = false;
        }
        if(qx==3)
        {
            currentAnimation = &walkingAnimationDown;
            movement.y += speed;
            movement.x -= speed;
            noKeyWasPressed = false;
        }
        if(qx == 5)
        {
            currentAnimation = &walkingAnimationUp;
            movement.y -= speed;
            movement.x -= speed;
            noKeyWasPressed = false;
        }
        if(qx == 7)
        {
            currentAnimation = &walkingAnimationUp;
            movement.y -= speed;
            movement.x += speed;
            noKeyWasPressed = false;
        }
        animatedSprite.play(*currentAnimation);
       
        float qy = 0;
        if(movement.x != 0){
            while (fabs(qy) < float(x_tileSize - as.width))
            {
                animatedSprite.move(sf::Vector2f(movement.x*frameTime.asSeconds(),0));
                animatedSprite.update(frameTime);
                qy += float(movement.x)*frameTime.asSeconds();
            }
        }
       
        float qxz = 0;
        if(movement.y != 0) {
            while(fabs(qxz)  < float(y_tileSize-as.height))
            {
               
                animatedSprite.move(sf::Vector2f(0,movement.y*frameTime.asSeconds()));
                animatedSprite.update(frameTime);
                qxz +=  float(movement.y)*frameTime.asSeconds();
               
            }
        }
        std::chrono::milliseconds dura( 200 );
        std::this_thread::sleep_for( dura );
        // if no key was pressed stop the animation
        if (noKeyWasPressed)
        {
            animatedSprite.stop();
        }
        noKeyWasPressed = true;
        //animatedSprite.update(frameTime);
        window.clear();
        window.draw(map);
        window.draw(animatedSprite);
       
        window.display();
    }
   
    return 0;
}

Please keep in mind you need the animated sprite by laurent gomila(excuse me if it is misspelled) that i linked earlier
« Last Edit: December 08, 2014, 04:46:07 pm by devilswin »

Arcade

  • Full Member
  • ***
  • Posts: 230
    • View Profile
Re: [SFML 2.1] Sprite animation not playing
« Reply #7 on: December 08, 2014, 05:23:54 pm »
You could probably make that example a lot shorter by removing all of the tilemap and pathing stuff and just have an animatedSprite move from one end of the screen to the other. I did look through it, though, and did see some potential issues, but I'll try to focus only on the question you asked specifically.

I think you were on the right track when you posted where you thought the problem was previously. What is expected by this part of the code?

Code: [Select]
while (fabs(qy) < float(x_tileSize - as.width))
{
   animatedSprite.move(sf::Vector2f(movement.x*frameTime.asSeconds(),0));
   animatedSprite.update(frameTime);
   qy += float(movement.x)*frameTime.asSeconds();
}

I think you are intending to move the sprite by a little bit at a time until it reaches the end of the tile size. Your problem is that you need to be moving your sprite once per GAME loop, not by making another loop here to move the sprite a bunch of times. This code is moving the sprite as you wanted, but won't display anything to the screen until after the loop ends when you eventually hit window.draw(animatedSprite) (this is what I was getting at in point 3 of my last post). In essence, Your code is only showing the sprite when it is done moving, not while it is in the process of moving.

Another problem with this is that your movement will basically be one tile size per frame instead of respecting your speed. Your speed variable and frameTime aren't doing anything useful because that loop will run as fast as possible until the animatedSprite reaches x_tileSize.

Hopefully all of that made sense. Basically, in pseudo code, what you want is:
  • If not at destination,move a little bit towards destination
  • Draw frame

But what you have is:
  • Continue moving until we reach destination
  • Draw frame

devilswin

  • Newbie
  • *
  • Posts: 38
    • View Profile
    • Email
Re: [SFML 2.1] Sprite animation not playing
« Reply #8 on: December 08, 2014, 06:02:19 pm »
okay...that makes sense. You said there were more problems that you saw, i was wondering if you could say what they are and what i can do to fix them

Arcade

  • Full Member
  • ***
  • Posts: 230
    • View Profile
Re: [SFML 2.1] Sprite animation not playing
« Reply #9 on: December 08, 2014, 06:31:47 pm »
I didn't do a vigorous code review or anything like that. Here are a few things I noticed when skimming, though.

  • The variable noKeyWasPressed doesn't seem to be used for anything.
  • Your use of atoi seems dangerous. atoi is intended to be used by c-style strings, not characters. c-style strings are required to have NUL as their last character (NUL-terminated), and that is what atoi uses to determine the end of the string. You only passed a single character so atoi might use whatever garbage memory comes after your character until it happens to hit a NUL character. Also, atoi returns 0 on error, which is probably not what you want. It would probably be better to use stringstreams or std::stoi for this conversion

There may be other problems too, but those are just the two I happened to noticed when skimming  :)

devilswin

  • Newbie
  • *
  • Posts: 38
    • View Profile
    • Email
Re: [SFML 2.1] Sprite animation not playing
« Reply #10 on: December 09, 2014, 02:32:51 pm »
So i did do some of those changes, it can move on the y-axis easily but when it starts to move on the x-axis, it gets all wonky and can't move

Here is the new code i use to move the sprite
 
        bool less_x = animatedSprite.getPosition().x >= currentx*32.0;
        bool great_x = animatedSprite.getPosition().x < (currentx*32.0)+32.0;
        bool less_y =animatedSprite.getPosition().y >= currenty*32.0;
        bool great_y =animatedSprite.getPosition().y < (currenty*32.0)+32.0;
       
        if(great_x == true && less_x == true && great_y == true && less_y == true)
        {
           
            animatedSprite.move(movement*frameTime.asSeconds());
            animatedSprite.update(frameTime);
           
        }
        else
        {
       
            cout << currentx << endl;
            cout << currenty << endl;
            count += 1;
            if(movement.x < 0)
                currentx += -1;
            else if(movement.x > 0)
                currentx += 1;
            else
                currentx += 0;
           
            if(movement.y < 0)
                currenty += -1;
            else if(movement.y > 0)
                currenty += 1;
            else
                currenty += 0;
           
            if(currenty > map_dim.y/y_tileSize)
                currenty = (map_dim.y/y_tileSize)-1;
            else if(currenty < 0)
                currenty = 1;
            if(currentx > map_dim.x/x_tileSize)
                currentx = (map_dim.x/x_tileSize)-1;
            else if (currentx < 0)
                currentx = 1;
           
        }
       
       
 

Edit: after 30 Min of debugging, it seems that the current y eventually surpass where the sprite is actually is...dont know why

Edit2 : Currentx and currenty are floats that equal 4 and 7 respectively
« Last Edit: December 09, 2014, 04:51:36 pm by devilswin »

Arcade

  • Full Member
  • ***
  • Posts: 230
    • View Profile
Re: [SFML 2.1] Sprite animation not playing
« Reply #11 on: December 09, 2014, 05:16:57 pm »
This might be another case where the code you provided isn't really enough to go off of. You said you can move in the y-axis easily, but can you move both up and down without problem? Based off of what you provided, all I can really say is that if currentx*32 or currenty*32 ever get less than the animated sprite's position, you won't be able to move because great_x or great_y will be false.

My suggestion would be to just add a bunch of prints to your code to make sure your variables are what you expect them to be. Alternatively, you can learn how to use a debugger (if you aren't familiar with one already) to step through your program and look for logic errors. Perhaps you could also search the internet or these forums for resources on tile based movement. For example, maybe you can get some ideas from this thread:
http://en.sfml-dev.org/forums/index.php?topic=9639

devilswin

  • Newbie
  • *
  • Posts: 38
    • View Profile
    • Email
Re: [SFML 2.1] Sprite animation not playing
« Reply #12 on: December 09, 2014, 09:17:24 pm »
The code given is ALL you need to reproduce the issue. i know how to use a debugger and there is no reasoning for why he cannot move left or right.

Arcade

  • Full Member
  • ***
  • Posts: 230
    • View Profile
Re: [SFML 2.1] Sprite animation not playing
« Reply #13 on: December 09, 2014, 10:55:26 pm »
It isn't quite all I need to reproduce the issue. If it were, I would be able to copy it and compile it myself to see the problem. I'll make some assumptions to try and help you out further, though.

First I'll assume this code is actually inside of some loop and that currentx starts off as 4, and currenty starts off as 7 as you said in your edit earlier. The only way your sprite can move is if you make it into your if statement. So how do we get in that if statement...
Code: [Select]
bool less_x = animatedSprite.getPosition().x >= currentx*32.0;
bool great_x = animatedSprite.getPosition().x < (currentx*32.0)+32.0;
bool less_y =animatedSprite.getPosition().y >= currenty*32.0;
bool great_y =animatedSprite.getPosition().y < (currenty*32.0)+32.0;
That means animatedSprite.getPosition().x MUST be between 128 and 160 for the sprite to move, AND
animatedSprite.getPosition().y must be between 224 and 256. Is that true? Are ALL of those conditions met when you are trying to move x?

You didn't tell me what animatedSprite.getPosition() is, but I'll assume all of those conditions are met. Lets assume animatedSprite.getPosition() is (130, 255) and you are moving down.
Code: [Select]
animatedSprite.move(movement*frameTime.asSeconds());

What happens when movement*frameTime.asSeconds() is greater than one in this scenario? We'll overshoot the end of our tile at 256. Lets say it was equal to 2 so now we're at (130, 257). So far everything is OK because we moved the sprite like we wanted, but you'll see how overshooting is about to cause a problem.

Now lets say we want to move left by changing movement.y to 0 and movement.x to -1... UH OH we are not going to make it into the if statement because great_y will be false. we never changed currenty, so it is still 7. We're going to hit the else case this time. In the else case we'll decrement currentx forever but never touch currenty. The sprite will never move again.

Because you didn't post all of the code I have no way of knowing if you are protecting against a situation like that. But hopefully this thought experiment will help you debug further.

devilswin

  • Newbie
  • *
  • Posts: 38
    • View Profile
    • Email
Re: [SFML 2.1] Sprite animation not playing
« Reply #14 on: December 10, 2014, 02:20:27 pm »
#include <iostream>
#include <iomanip>
#include <queue>
#include <string>
#include <math.h>
#include <ctime>
#include <SFML/Graphics.hpp>
#include <vector>
#include <memory>
#include <stdlib.h>
#include <stdio.h>
#include "Animation.hpp"
#include "AnimatedSprite.hpp"
#include <chrono>
#include <thread>
using namespace std;
class TileMap : public sf::Drawable, public sf::Transformable
{
public:
 
    bool load(const std::string& tileset, sf::Vector2u tileSize, const int* tiles, unsigned int width, unsigned int height)
    {
        // load the tileset texture
        if (!m_tileset.loadFromFile(tileset))
            return false;
     
        // resize the vertex array to fit the level size
        m_vertices.setPrimitiveType(sf::Quads);
        m_vertices.resize(width * height * 4);
     
        // populate the vertex array, with one quad per tile
        for (unsigned int i = 0; i < width; ++i)
            for (unsigned int j = 0; j < height; ++j)
            {
                // get the current tile number
                int tileNumber = tiles[i + j * width];
             
                // find its position in the tileset texture
                int tu = tileNumber % (m_tileset.getSize().x / tileSize.x);
                int tv = tileNumber / (m_tileset.getSize().x / tileSize.x);
             
                // get a pointer to the current tile's quad
                sf::Vertex* quad = &m_vertices[(i + j * width) * 4];
             
                // define its 4 corners
                quad[0].position = sf::Vector2f(i * tileSize.x, j * tileSize.y);
                quad[1].position = sf::Vector2f((i + 1) * tileSize.x, j * tileSize.y);
                quad[2].position = sf::Vector2f((i + 1) * tileSize.x, (j + 1) * tileSize.y);
                quad[3].position = sf::Vector2f(i * tileSize.x, (j + 1) * tileSize.y);
             
                // define its 4 texture coordinates
                quad[0].texCoords = sf::Vector2f(tu * tileSize.x, tv * tileSize.y);
                quad[1].texCoords = sf::Vector2f((tu + 1) * tileSize.x, tv * tileSize.y);
                quad[2].texCoords = sf::Vector2f((tu + 1) * tileSize.x, (tv + 1) * tileSize.y);
                quad[3].texCoords = sf::Vector2f(tu * tileSize.x, (tv + 1) * tileSize.y);
            }
     
        return true;
    }
 
private:
 
    virtual void draw(sf::RenderTarget& target, sf::RenderStates states) const
    {
        // apply the transform
        states.transform *= getTransform();
     
        // apply the tileset texture
        states.texture = &m_tileset;
     
        // draw the vertex array
        target.draw(m_vertices, states);
    }
 
    sf::VertexArray m_vertices;
    sf::Texture m_tileset;
};
int main()
{
    // create the window
    sf::Vector2i map_dim(512,256);
    sf::RenderWindow window(sf::VideoMode(map_dim.x, map_dim.y), "Tilemap");
    sf::Texture texture;
    // window.setFramerateLimit(60);
    if (!texture.loadFromFile("FFSPRITE.gif"))
    {
        std::cout << "Failed to load player spritesheet!" << std::endl;
        return 1;
    }
   
   
   
   
    bool has_clicked = false;
   
    // set up tshe animations for all four directions (set spritesheet and push frames)
    Animation walkingAnimationDown;
    walkingAnimationDown.setSpriteSheet(texture);
    walkingAnimationDown.addFrame(sf::IntRect(47,5, 16,16)    );
    walkingAnimationDown.addFrame(sf::IntRect(65,5,16, 16)     );
    walkingAnimationDown.addFrame(sf::IntRect(47,5, 16,16)    );
   
    Animation walkingAnimationLeft;
    walkingAnimationLeft.setSpriteSheet(texture);
    walkingAnimationLeft.addFrame(sf::IntRect(83,5, 13,16 ) );
    walkingAnimationLeft.addFrame(sf::IntRect(98,5,14,16));
    walkingAnimationLeft.addFrame(sf::IntRect(83,5,13,16));
   
   
    Animation walkingAnimationRight;
    walkingAnimationRight.setSpriteSheet(texture);
    walkingAnimationRight.addFrame(sf::IntRect(150,5, 13, 16) );
    walkingAnimationRight.addFrame(sf::IntRect(165,5,14, 16)  );
    walkingAnimationRight.addFrame(sf::IntRect(150,5,13,16)   );
   
    Animation walkingAnimationUp;
    walkingAnimationUp.setSpriteSheet(texture);
    walkingAnimationUp.addFrame(sf::IntRect(114, 5, 16, 16));
    walkingAnimationUp.addFrame(sf::IntRect(132, 5, 16, 16));
    walkingAnimationUp.addFrame(sf::IntRect(114, 5, 16, 16));
   
   
    Animation* currentAnimation = &walkingAnimationDown;
   
    // set up AnimatedSprite
    AnimatedSprite animatedSprite(sf::seconds(0.2), true, false);
   
    animatedSprite.setPosition(sf::Vector2f(4.0*32.0,7.0*32.0));
    sf::Clock frameClock;
    float currentx = 4;
float currenty = 4;
    float speed = 1.f;
    bool noKeyWasPressed = true;
    // define the level with an array of tile indices
    const int level[] =
    {
        0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
        0, 1, 1, 1, 3, 3, 3, 3, 0, 0, 0, 2, 0, 0, 0, 0,
        1, 1, 0, 0, 3, 0, 0, 3, 0, 3, 3, 3, 3, 3, 3, 3,
        0, 3, 3, 3, 3, 0, 3, 3, 0, 3, 1, 1, 1, 0, 0, 0,
        0, 3, 1, 0, 3, 2, 3, 0, 0, 3, 1, 1, 1, 2, 0, 0,
        0, 3, 1, 0, 3, 0, 3, 2, 0, 3, 1, 1, 1, 1, 2, 0,
        2, 3, 1, 0, 3, 0, 3, 2, 2, 3, 1, 1, 1, 1, 1, 1,
        0, 3, 3, 3, 3, 2, 3, 3, 3, 3, 0, 0, 1, 1, 1, 1,
    };
   
    float y_tileSize = 32.0;
float x_tileSize = 32.0;
int count = 0;
   string route = "445667077012322107666700000";
    // create the tilemap from the level definition
    TileMap map;
    if (!map.load("tileset.png", sf::Vector2u(32, 32), level, 16, 8))
        return -1;
   
    animatedSprite.play(*currentAnimation);
    sf::FloatRect as = animatedSprite.getGlobalBounds();
    // run the main loop
    while (window.isOpen())
    {
       
        sf::Event event;
        char ada;
        int qx;
        if(count < route.length())
        {
            ada = route.at(count);
            qx = atoi(&ada);
            count += 1;
        }
        while (window.pollEvent(event))
        {
            if (event.type == sf::Event::Closed)
                window.close();
            if (event.type == sf::Event::KeyPressed && event.key.code == sf::Keyboard::Escape)
                window.close();
        }
       
        sf::Time frameTime = frameClock.restart();
       
        // if a key was pressed set the correct animation and move correctly
        sf::Vector2f movement(0.f, 0.f);
       
       
        if (qx == 6)
        {
            currentAnimation = &walkingAnimationUp;
            movement.y -= speed;
            noKeyWasPressed = false;
        }
       
        if (qx == 2)
        {
            currentAnimation = &walkingAnimationDown;
            movement.y += speed;
            noKeyWasPressed = false;
        }
       
       
        if(qx == 4)
        {
            currentAnimation = &walkingAnimationLeft;
            movement.x -= speed;
            noKeyWasPressed = false;
        }
       
       
        if (qx == 0)
        {
            currentAnimation = &walkingAnimationRight;
            movement.x += speed;
            noKeyWasPressed = false;
        }
        if (qx == 1)
        {
            currentAnimation = &walkingAnimationDown;
            movement.y += speed;
            movement.x += speed;
            noKeyWasPressed = false;
        }
        if(qx==3)
        {
            currentAnimation = &walkingAnimationDown;
            movement.y += speed;
            movement.x -= speed;
            noKeyWasPressed = false;
        }
        if(qx == 5)
        {
            currentAnimation = &walkingAnimationUp;
            movement.y -= speed;
            movement.x -= speed;
            noKeyWasPressed = false;
        }
        if(qx == 7)
        {
            currentAnimation = &walkingAnimationUp;
            movement.y -= speed;
            movement.x += speed;
            noKeyWasPressed = false;
        }
        animatedSprite.play(*currentAnimation);
       
          bool less_x = animatedSprite.getPosition().x >= currentx*32.0;
        bool great_x = animatedSprite.getPosition().x < (currentx*32.0)+32.0;
        bool less_y =animatedSprite.getPosition().y >= currenty*32.0;
        bool great_y =animatedSprite.getPosition().y < (currenty*32.0)+32.0;
       
        if(great_x == true && less_x == true && great_y == true && less_y == true)
        {
           
            animatedSprite.move(movement*frameTime.asSeconds());
            animatedSprite.update(frameTime);
           
        }
        else
        {
       
            cout << currentx << endl;
            cout << currenty << endl;
            count += 1;
            if(movement.x < 0)
                currentx += -1;
            else if(movement.x > 0)
                currentx += 1;
            else
                currentx += 0;
           
            if(movement.y < 0)
                currenty += -1;
            else if(movement.y > 0)
                currenty += 1;
            else
                currenty += 0;
           
            if(currenty > map_dim.y/y_tileSize)
                currenty = (map_dim.y/y_tileSize)-1;
            else if(currenty < 0)
                currenty = 1;
            if(currentx > map_dim.x/x_tileSize)
                currentx = (map_dim.x/x_tileSize)-1;
            else if (currentx < 0)
                currentx = 1;
           
        }
       
       
        // if no key was pressed stop the animation
        if (noKeyWasPressed)
        {
            animatedSprite.stop();
        }
        noKeyWasPressed = true;
        //animatedSprite.update(frameTime);
        window.clear();
        window.draw(map);
        window.draw(animatedSprite);
       
        window.display();
    }
   
    return 0;
}
Besides the Animated sprite by laurent gomila (https://github.com/SFML/SFML/wiki/Source:-AnimatedSprite) this Is all of the code NEEDED to reproduce the issue.

the point of the current x, currenty stuff is that it is supposed to be a check if they are in a certain tile...

I apologize if it sounds quite rude.
« Last Edit: December 10, 2014, 02:42:34 pm by devilswin »

 

anything