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

Author Topic: [C++ and SFML 2.1] Scrolling backgrounds ( y+) [SOLVED]  (Read 20529 times)

0 Members and 1 Guest are viewing this topic.

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
[C++ and SFML 2.1] Scrolling backgrounds ( y+) [SOLVED]
« on: November 09, 2013, 01:40:32 pm »
hey, i wanted to add a scrolling background to my game and now i have an issue with the background, as the title says :D (the jpg files are 800x600 just like the window)

i show you my code and screenshots so you can see whats going wrong

#ifndef GUIMOVABLEBACKGROUNDS_H
#define GUIMOVABLEBACKGROUNDS_H

#include <SFML\Graphics.hpp>
# include <iostream>

class MovableBackground
{
public:
        MovableBackground();
        void Update(sf::RenderWindow &window, float elapsedTime);
        void Render(sf::RenderWindow &window);
       
private:
        sf::Texture bg1Tex;
        sf::Texture bg2Tex;

        sf::Sprite      bg1Sprite;
        sf::Sprite      bg2Sprite;

        float bgSpeed;
        float bg1Y;
        float bg2Y;
};
#endif
 

GUImovableBackground.cpp
#include "GUImovableBackground.h"


MovableBackground::MovableBackground()
{
        bgSpeed = 0.1;

        bg1Tex.loadFromFile("graphics//background.jpg");
        bg1Tex.setSmooth(false);
        bg1Sprite.setTexture(bg1Tex);
        bg1Y = bg1Sprite.getPosition().y;

        bg2Tex.loadFromFile("graphics//background.jpg");
        bg2Tex.setSmooth(false);
        bg2Sprite.setTexture(bg2Tex);
        bg2Sprite.setPosition(0, -799);
        bg2Y = bg2Sprite.getPosition().y;
}


void MovableBackground::Update(sf::RenderWindow &window, float elapsedTime)
{
        if (bg1Y >= window.getSize().y)
        {
                bg1Y = - 799;
        }else
        {
                bg1Y += bgSpeed * elapsedTime;
        }

        if (bg2Y >= window.getSize().y)
        {
                bg2Y = - 799;
        }else
        {
                bg2Y += bgSpeed * elapsedTime;
        }

        if (bg1Y == -799)
        {
                std::cout << bg1Y << "\t bg1" << std::endl;
        }
        if (bg2Y == -799)
        {
                std::cout << bg2Y << "\t bg2" << std::endl;
        }

        bg1Sprite.setPosition(0, bg1Y);
        bg2Sprite.setPosition(0, bg2Y);
}
void MovableBackground::Render(sf::RenderWindow &window)
{
        window.draw(bg1Sprite);
        window.draw(bg2Sprite);
 

the first screenshot:


the second screenshot:


As you can see, one time it nearly works, the other time the distance is just too high :/
and this goes on all the time... when background1 is set to - 799 the little gap is there. When background2 is set to - 799 the huge gap is there.

Maybe the mistake i made is simple, but I just dont see it :S
(if you need more code please tell me)
« Last Edit: November 10, 2013, 05:33:46 pm by nebula »

The Hatchet

  • Full Member
  • ***
  • Posts: 135
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #1 on: November 09, 2013, 01:46:29 pm »
You aren't setting an initial bg1Sprite.setPosition(x, y) is about the only simple thing standing out

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #2 on: November 09, 2013, 01:47:29 pm »
You aren't setting an initial bg1Sprite.setPosition(x, y) is about the only simple thing standing out
if i dont set this manually it sets itself to (0,0) as i know

further this does not affect the problem because it is only in the destructor and as you see it is nearly set right
(but just for you i tested it and nothing changed)

here is how i use the class in my game (not my code, that would be way too long)

MovableBackground bg;

while running:
bg.Update (window, elapsedTime);
window.clear();
bg.Render(window);
window.display();
« Last Edit: November 09, 2013, 03:06:23 pm by nebula »

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #3 on: November 09, 2013, 04:40:53 pm »
I rewrote this completely... now it works better, but i need to rework the initialization of the bg2Sprite position, because at the beginning there is still a mistake with it :/ here is the code

.h
#ifndef GUIMOVABLEBACKGROUNDS_H
#define GUIMOVABLEBACKGROUNDS_H

#include <SFML\Graphics.hpp>
#include <iostream>

class MovableBackground
{
public:
        MovableBackground();
        void Update(sf::RenderWindow &window, float elapsedTime);
        void Render(sf::RenderWindow &window);
       
private:
        sf::Texture bg1Tex;
        sf::Texture bg2Tex;

        sf::Sprite      bg1Sprite;
        sf::Sprite      bg2Sprite;

        float bgSpeed;
        float bg1Y;
        float bg2Y;
        float windowbg1diff;
};
#endif
 

.cpp
#include "GUImovableBackground.h"


MovableBackground::MovableBackground()
{
        bgSpeed = 0.3;

        bg1Tex.loadFromFile("graphics//background.jpg");
        bg1Tex.setSmooth(false);
        bg1Sprite.setTexture(bg1Tex);
        bg1Y = bg1Sprite.getPosition().y;

        bg2Tex.loadFromFile("graphics//background.jpg");
        bg2Tex.setSmooth(false);
        bg2Sprite.setTexture(bg2Tex);
        bg2Sprite.setPosition(0, 601);
        bg2Y = bg2Sprite.getPosition().y;
}


void MovableBackground::Update(sf::RenderWindow &window, float elapsedTime)
{
        windowbg1diff = bg1Y - window.getSize().y;

        if (bg1Y >= 600)
        {
                bg1Y = - 590;
        }else
        {
                bg1Y += bgSpeed * elapsedTime;
        }

        if (bg2Y >= window.getSize().y)
        {
                bg2Y = - 600;
        }else if (bg2Y < bg1Y)
        {
                bg2Y = windowbg1diff + 5;
        }else
        {
                bg2Y += bgSpeed * elapsedTime;
        }

        bg1Sprite.setPosition(0, bg1Y);
        bg2Sprite.setPosition(0, bg2Y);
}
void MovableBackground::Render(sf::RenderWindow &window)
{
        window.draw(bg1Sprite);
        window.draw(bg2Sprite);
}
 

wintertime

  • Sr. Member
  • ****
  • Posts: 255
    • View Profile
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #4 on: November 09, 2013, 06:17:32 pm »
Why dont you set the texture to be repeated? Then you should be able to only move the texture rectangle and draw a single fullscreen object.

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #5 on: November 09, 2013, 06:24:42 pm »
Why dont you set the texture to be repeated? Then you should be able to only move the texture rectangle and draw a single fullscreen object.

that sounds legit :D i will read myself through the sfml tutorials for this and replace it. thanks ;)

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #6 on: November 09, 2013, 07:18:10 pm »
okay. now the problem is that the background is supposed to move downwards as long as the game runs. and by the setRepeated function i can get a sprite within a texture that i can move to the max of the image. Or did i understand it wrong? :D

wintertime

  • Sr. Member
  • ****
  • Posts: 255
    • View Profile
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #7 on: November 09, 2013, 07:56:26 pm »
If you set the texture to repeating its as if there would be copies of it all around it until infinity. So you should be able to set a texture rectangle(x,y,800,600) for your texture of size 800x600 in the sprite of size 800x600, where x,y is the position inside the texture you want to show at screen position 0,0 and it should fill the whole screen. At least thats how it works in OpenGL and SFML would most likely translate this appropriately without imposing more constraints.
« Last Edit: November 09, 2013, 07:58:45 pm by wintertime »

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #8 on: November 09, 2013, 09:32:27 pm »
        bgTex.loadFromFile("graphics//background.jpg");
        bgTex.setSmooth(false);
        bgTex.setRepeated(true);
        bgSprite.setTexture(bgTex);
        bgSprite.setTextureRect(sf::IntRect(0,0,800,600));
        bgY = bg1Sprite.getPosition().y;
 
like this? but how do i move the background? i tried this:
        if (bgY < 600)
        {
                bgY += bgSpeed * elapsedTime;
        }else
                {
                        bgY = 0;
                }
 

wintertime

  • Sr. Member
  • ****
  • Posts: 255
    • View Profile
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #9 on: November 09, 2013, 09:46:56 pm »
More like this:
        bgTex.loadFromFile("graphics//background.jpg");
        bgTex.setSmooth(false);
        bgTex.setRepeated(true);
        bgSprite.setTexture(bgTex);
        bgSprite.setPosition(0,0);
        bgY = 0;
        bgSprite.setTextureRect(sf::IntRect(0,bgY,800,600));
 
if (bgY < 600)
{
        bgY += bgSpeed * elapsedTime;
}
else
{
        bgY = 0;
}
bgSprite.setTextureRect(sf::IntRect(0,bgY,800,600));
 
« Last Edit: November 09, 2013, 09:49:26 pm by wintertime »

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #10 on: November 09, 2013, 09:54:20 pm »
then this happens:

wintertime

  • Sr. Member
  • ****
  • Posts: 255
    • View Profile
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #11 on: November 10, 2013, 01:21:08 am »
Ahh I think that was because a Sprite gets implicitly resized with the Texture.
You can switch the type to use a RectangleShape instead and set the size of that at its construction to 800x600; everything else should be nearly the same.

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #12 on: November 10, 2013, 04:30:25 am »
i think i am doin this wrong :D does not work like i wish

header
#ifndef GUIMOVABLEBACKGROUNDS_H
#define GUIMOVABLEBACKGROUNDS_H

#include <SFML\Graphics.hpp>
#include <iostream>

class MovableBackground
{
public:
        MovableBackground();
        void Update(sf::RenderWindow &window, float elapsedTime);
        void Render(sf::RenderWindow &window);
       
private:
        sf::Texture bgTex;
        sf::Texture bg2Tex;

        sf::RectangleShape bgShape;
        sf::Vector2f bgSize;

        sf::Sprite      bgSprite;
        sf::Sprite      bg2Sprite;

        float bgSpeed;
        float bgY;
        float bg2Y;
        float windowbg1diff;
};
#endif
 

cpp
#include "GUImovableBackground.h"


MovableBackground::MovableBackground()
{
        bgSpeed = 0.3;

        bgTex.loadFromFile("graphics//background.jpg");
        bgTex.setSmooth(false);
        bgTex.setRepeated(true);

        bgY = bgShape.getPosition().y;
        bgSize.x = 800;
        bgSize.y = 600;

        bgShape.setTexture(&bgTex);
        bgShape.setSize(bgSize);
}


void MovableBackground::Update(sf::RenderWindow &window, float elapsedTime)
{
        if (bgY < 600)
        {
                bgY += bgSpeed * elapsedTime;
        }else
                {
                        bgY = 0;
                }
        bgShape.setPosition(0, bgY);
}
void MovableBackground::Render(sf::RenderWindow &window)
{
        window.draw(bgShape);
}
 

G.

  • Hero Member
  • *****
  • Posts: 1593
    • View Profile
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #13 on: November 10, 2013, 05:00:40 am »
wintertime kindly gave you a short snippet of code, almost ready to be copied/pasted, and it doesn't seem like you bothered to read it.
Why do you move your background? You're supposed to modify its TextureRect.

It works with a Sprite or a RectangleShape.
« Last Edit: November 10, 2013, 05:22:39 am by G. »

nebula

  • Jr. Member
  • **
  • Posts: 96
    • View Profile
    • Email
Re: [C++ and SFML 2.1] Scrolling backgrounds ( y+)
« Reply #14 on: November 10, 2013, 02:46:47 pm »
i did read all of it. and looked it all up in the api. i try it all again and if i got it going i will post it ;)

I found the mistake :D

what wintertime did:
Quote
    bgY = 0;
what i did:
Quote
bgY = bgShape.getPosition().y;

@wintertime thanks a lot! now it does exactly move how it is supposed to. but uhhm did you edit the post? i think the initialization of bgY was not there in first place :D

ps:
I changed       
bgY += bgSpeed * elapsedTime;
into        
bgY -= bgSpeed * elapsedTime;
because the rect needs to go upwards to get the feeling of the background moving downwards :D
« Last Edit: November 10, 2013, 03:16:40 pm by nebula »