Thread: [SFML C++] Sprite isn't cropped well for animation... that's the problem maybe.

  1. #1
    Registered User
    Join Date
    Nov 2012
    Location
    Brunei
    Posts
    77

    [SFML C++] Sprite isn't cropped well for animation... that's the problem maybe.

    I'm not sure myself what has caused this problem. It seems to me that the code that I wrote was right. Even when I cropped it manually (without the getSize().x function to check the sprite's width and pass it to setTextureRect(..) automatically),
    the sprite still show unwanted frame.

    Sorry if I can't explain the problem well. In short, the
    tempSprite.setTextureRect(...) should show 1 frame corresponding to user's input (WSAD movement). Instead, the sprite shown is more than 1 frames, and all of them appear to move (or do run animation) simultaneously.

    What's more confusing to me is the "line" that appears behind the character sprite (happens when the sprite 'move up', which is at the bottom of the image)

    Here's the sprite image (96 by 128):

    [SFML C++] Sprite isn't cropped well for animation... that's the problem maybe.-cloaked-dude-png

    And here's the codes:

    Main.cpp

    Code:
    #include <SFML/Graphics.hpp>
    #include <iostream>
    
    
    #define ScreenWidth 800
    #define ScreenHeight 600
    
    
    #include "Player.h"
    
    
    int main()
    {
        sf::RenderWindow Window(sf::VideoMode(ScreenWidth,ScreenHeight,32),"SFML ADVANCED SPRITE TUTORIAL 2");
    
    
        Player player;
    
    
        player.LoadTexture();
        player.Initialize();
    
    
        while(Window.isOpen())
        {
            sf::Event Event;
    
    
            while(Window.pollEvent(Event))
            {
                if(Event.type == sf::Event::Closed || sf::Keyboard::isKeyPressed(sf::Keyboard::Escape))
                {
                    Window.close();
                }
            }//END EVENT LOOP
    
    
            Window.clear();
            player.Update(Window);
            player.Draw(Window);
            Window.display();
    
    
            system("cls");
    
    
        }
    
    
        return 0;
    }

    Animation.h
    Code:
    #ifndef ANIMATION_H
    #define ANIMATION_H
    
    
    class Animation
    {
        public:
            Animation();
            virtual ~Animation();
    
    
            void setTexture(sf::Texture &tempTexture);
    
    
            void Draw(sf::RenderWindow &Window);
            void Update(sf::RenderWindow &Window);
            void Initialize(float &x, float &y, int amountOfFramesX, int amountOfFramesY, float textureWidth, float textureHeight);
    
    
            float getPositionX(float &x);
            float getPositionY(float &y);
    
    
            float getFrameHeight();
            float getFrameWidth();
    
    
            bool getMoveActive();
            void setMoveActive(bool MoveActive);
    
    
            void setCurrentFrameY(int FrameY);
    
    
        protected:
    
    
        private:
            sf::Texture tempTexture;
            sf::Sprite tempSprite;
    
    
            float x, y;
            float move_x;
            float move_y;
    
    
            float frameHeight, frameWidth;
            int amountOfFramesX, amountOfFramesY;
            int textureWidth, textureHeight;
            bool MoveActive_activated;
    
    
            int currentFrameX, currentFrameY;
    
    
    };
    
    
    #endif // ANIMATION_H

    Animation.cpp
    Code:
    #include <SFML/Graphics.hpp>
    #include <iostream>
    
    
    #include "Animation.h"
    
    
    Animation::Animation()
    {
        //ctor
    }
    
    
    Animation::~Animation()
    {
        //dtor
    }
    
    
    bool Animation::getMoveActive()
    {
        return MoveActive_activated;
    }
    
    
    void Animation::setMoveActive(bool MoveActive)
    {
        MoveActive_activated = MoveActive;
    }
    
    
    void Animation::setCurrentFrameY(int FrameY)
    {
        currentFrameY = FrameY;
    }
    
    
    
    
    void Animation::Initialize(float &x, float &y, int amountOfFramesX , int amountOfFramesY, float textureWidth, float textureHeight)
    {
        this-> x = x;
        this-> y = y;
        this-> amountOfFramesX = amountOfFramesX;
        this-> amountOfFramesY = amountOfFramesY;
        this-> textureWidth = textureWidth;
        this-> textureHeight = textureHeight;
    
    
        currentFrameY = 0;
    
    
    }
    
    
    float Animation::getFrameWidth()
    {
        frameWidth = (float) textureWidth / amountOfFramesX;
        return frameWidth;
    }
    
    
    float Animation::getFrameHeight()
    {
        frameHeight = (float) textureHeight / amountOfFramesY;
        return frameHeight;
    }
    
    
    float Animation::getPositionX(float &x)
    {
        move_x = x;
        return move_x;
    }
    
    
    float Animation::getPositionY(float &y)
    {
        move_y = y;
        return move_y;
    }
    
    
    void Animation::Update(sf::RenderWindow &Window)
    {
        std::cout << "setPosition move_x: " << move_x << std::endl;
        std::cout << "setPosition move_y: " << move_y << std::endl;
        std::cout << "frameWidth: " << getFrameWidth() << std::endl;
        std::cout << "frameHeight: " << getFrameHeight() << std::endl;
        std::cout << "Texture width: " << textureWidth << std::endl;
        std::cout << "Texture height: " << textureHeight << std::endl;
        std::cout << "Amount of frames X: " << amountOfFramesX << std::endl;
        std::cout << "Amount of frames Y: " << amountOfFramesY << std::endl;
        std::cout << "-----------" << std::endl;
        std::cout << "currentFrameX: " << currentFrameX << std::endl;
        std::cout << "currentFrameY: " << currentFrameY << std::endl << std::endl;
        std::cout << "In tempSprite.setTextureRect(sf::IntRect(x1,y1,x2,y2)) : " << std::endl << std::endl;
        std::cout << "x1: " << currentFrameX * frameWidth << std::endl;
        std::cout << "y1: " << currentFrameY * frameHeight << std::endl;
        std::cout << "x2: " << currentFrameX * frameWidth + frameWidth << std::endl;
        std::cout << "y2: " << currentFrameY * frameWidth + frameHeight << std::endl;
    
    
        if(MoveActive_activated)
        {
            std::cout <<"[MoveActive_activated is now TRUE] " << std::endl;
            currentFrameX++;
    
    
                if((frameWidth * currentFrameX) >= (frameWidth*amountOfFramesX))
                   {
                       currentFrameX = 0;
                   }
        }
        else
        {
            currentFrameX = 1;
        }
    
    
        tempSprite.setTextureRect(sf::IntRect( currentFrameX * frameWidth , currentFrameY * frameHeight , (currentFrameX * frameWidth) + frameWidth  , (currentFrameY * frameHeight) + frameHeight ));
        tempSprite.setPosition(move_x,move_y);
    
    
    }
    
    
    void Animation::setTexture(sf::Texture &tempTexture)
    {
        tempSprite.setTexture(tempTexture);
    }
    
    
    void Animation::Draw(sf::RenderWindow &Window)
    {
        Window.draw(tempSprite);
    }
    Player.h


    Code:
    #ifndef PLAYER_H
    #define PLAYER_H
    
    
    #include "Animation.h"
    
    
    class Player
    {
        public:
            Player();
            virtual ~Player();
    
    
             Animation playerAnimation;
    
    
            void LoadTexture();
            void Initialize();
            void Draw(sf::RenderWindow &Window);
            void Update(sf::RenderWindow &Window);
    
    
        protected:
        private:
    
    
            sf::Texture playerTexture;
    
    
            int textureWidth, textureHeight;
    
    
            float x , y;
            float moveSpeed;
    };
    
    
    #endif // PLAYER_H
    Player.cpp

    Code:
    #include <SFML/Graphics.hpp>
    #include <iostream>
    
    
    #include "Player.h"
    #include "Animation.h"
    
    
    Player::Player()
    {
        //ctor
    }
    
    
    Player::~Player()
    {
        //dtor
    }
    
    
    
    
    void Player::LoadTexture()
    {
        if(!playerTexture.loadFromFile("C:/Program Files (x86)/CodeBlocks/Projects/SFML ANIMATION ADVANCED TUTORIAL 2/resources/$Cloaked dude.png"))
             {
                std::cout << "Error loading image\n";
             }
             else
             {
                playerAnimation.setTexture(playerTexture);
                std::cout << "Loaded the image.png" << std::endl;
                // system("pause");
             }
    
    
    }
    
    
    void Player::Initialize()
    {
        std::cout << "Initializing from Player::Initialize()..." << std::endl;
        x = 0;
        y = 0;
        moveSpeed = 10;
        textureWidth = playerTexture.getSize().x;
        textureHeight = playerTexture.getSize().y;
    
    
        playerAnimation.Initialize(x,y,3,4,textureWidth,textureHeight);
    }
    
    
    void Player::Update(sf::RenderWindow &Window)
    {
    
    
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::W)) //UP
        {
            playerAnimation.setMoveActive(true);
            y -= moveSpeed;
            playerAnimation.setCurrentFrameY(3);
            std::cout << "Moved up" << std::endl;
        }
        else if(sf::Keyboard::isKeyPressed(sf::Keyboard::S)) //DOWN
        {
            playerAnimation.setMoveActive(true);
            y += moveSpeed;
            playerAnimation.setCurrentFrameY(0);
            std::cout << "Moved down" << std::endl;
        }
        else if(sf::Keyboard::isKeyPressed(sf::Keyboard::A)) //LEFT
        {
            playerAnimation.setMoveActive(true);
            x -= moveSpeed;
            playerAnimation.setCurrentFrameY(1);
            std::cout << "Moved left" << std::endl;
        }
        else if(sf::Keyboard::isKeyPressed(sf::Keyboard::D)) //RIGHT
        {
            playerAnimation.setMoveActive(true);
            x += moveSpeed;
            playerAnimation.setCurrentFrameY(2);
            std::cout << "Moved right" << std::endl;
        }
        else
        {
            playerAnimation.setMoveActive(false);
            std::cout <<"[MoveActive_activated is now FALSE] " << std::endl;
        }
    
    
        std::cout << "x-position: " << x << std::endl;
        std::cout << "y-position: " << y << std::endl;
        std::cout << "moveSpeed : " << moveSpeed << std::endl;
    
    
        playerAnimation.getPositionX(x);
        playerAnimation.getPositionY(y);
        playerAnimation.Update(Window);
    
    
    }
    
    
    void Player::Draw(sf::RenderWindow &Window)
    {
        playerAnimation.Draw(Window);
    }

  2. #2
    Registered User
    Join Date
    Nov 2012
    Location
    Brunei
    Posts
    77
    This is what I'm talking about:

    When facing down:
    [SFML C++] Sprite isn't cropped well for animation... that's the problem maybe.-facing-down-jpg

    When facing left:
    [SFML C++] Sprite isn't cropped well for animation... that's the problem maybe.-facing-left-jpg

    When facing right:
    [SFML C++] Sprite isn't cropped well for animation... that's the problem maybe.-facing-right-jpg

    When facing up:
    [SFML C++] Sprite isn't cropped well for animation... that's the problem maybe.-facing-up-jpg

  3. #3
    Registered User
    Join Date
    Aug 2003
    Posts
    1,218
    The IntRect constructor takes the following arguments: (x coordinate, y coordinate, width, height) while you are sending it (x coordinate start, y coordinate start, x coordinate end, y coordinate end).

    Also this line:
    Code:
    if((frameWidth * currentFrameX) >= (frameWidth*amountOfFramesX))
    
    // Can be simplified to this:
    
    if(currentFrameX >= amountOfFramesX)

  4. #4
    Registered User
    Join Date
    Nov 2012
    Location
    Brunei
    Posts
    77
    I see.. thanks a lot. I thought it was supposed to be (x1, y1, x2, y2). Or was it only applied to setSubRect (the old ver 1.6 SFML)?
    And thanks for the simplification.. I didn't think it through.

  5. #5
    Registered User
    Join Date
    Aug 2003
    Posts
    1,218
    No idea if it only applied to setSubRect, but when in doubt always go to the documentation SFML - Simple and Fast Multimedia Library

  6. #6
    Registered User
    Join Date
    Nov 2012
    Location
    Brunei
    Posts
    77
    Thanks

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. SFML Audio Problems...
    By JM1082 in forum Game Programming
    Replies: 1
    Last Post: 02-22-2012, 02:55 PM
  2. )': Visual C++ & SFML compilation problems! :'(
    By JM1082 in forum Game Programming
    Replies: 12
    Last Post: 02-20-2012, 08:48 AM
  3. Allegro sprite animation?
    By godly 20 in forum C++ Programming
    Replies: 2
    Last Post: 01-20-2011, 10:18 AM
  4. Moving sprite relative to another sprite
    By Akkernight in forum Game Programming
    Replies: 5
    Last Post: 04-13-2009, 05:00 PM
  5. any good way to write sprite/animation classes for a game?
    By compjinx in forum Game Programming
    Replies: 2
    Last Post: 03-28-2002, 01:22 AM