Reputation: 100
I'm trying to store all my textures in an array. but the images aren't getting returned it would seem here's my code
I was under the assumption that my loadTex and loadSpri functions would return and store their data in the array that i made, but it doesn't seem to be working that way because when i run the game they don't show up, just white space. My code probably looks bad, but i'm quite the beginner still and trying to get the hang of things
Here's render.cpp
#include "render.h"
texandsprite render::textures[5];
sf::Texture loadTex(std::string);
sf::Sprite loadSpri(sf::Texture);
//Function to start the game
void render::start()
{
_mainWindow.create(sf::VideoMode(1024, 768, 32), "A New Life");
textures[1].tex = loadTex("civilian.png");
textures[1].spri = loadSpri(textures[1].tex);
GameLoop();
}
void render::GameLoop()
{
sf::Event event;
//Load(1, "civilian.png");
float x = 0;
float y = 0;
while(_mainWindow.isOpen())
{
while (_mainWindow.pollEvent(event))
{
//Check the type of event
switch (event.type)
{
//window closed
case sf::Event::Closed:
_mainWindow.close();
break;
case sf::Event::KeyPressed:
switch(event.key.code)
{
case sf::Keyboard::Up:
--y;
break;
case sf::Keyboard::Down:
y += 5;
break;
case sf::Keyboard::Right:
++x;
break;
case sf::Keyboard::Left:
--x;
break;
}
break;
default:
break;
}
}
_mainWindow.clear(sf::Color::White);
//Draw everything here
//_mainWindow.draw(...);
textures[1].spri.setPosition(x,y);
_mainWindow.draw(textures[1].spri);
//End the current frame
_mainWindow.display();
}
}
sf::RenderWindow render::_mainWindow;
sf::Texture render::loadTex(std::string filename)
{
sf::Texture temptex;
if(!temptex.loadFromFile(filename))
{
std::cout << "Error: could not load image" << filename << std::endl;
}
std::cout << filename << " Loaded" << std::endl;
return temptex;
}
sf::Sprite render::loadSpri(sf::Texture temptex)
{
sf::Sprite tempspri;
tempspri.setTexture(temptex);
return tempspri;
}
Here's render.h
#ifndef RENDER_H_INCLUDED
#define RENDER_H_INCLUDED
#include "SFML/Window.hpp"
#include "SFML/Graphics.hpp"
#include <iostream>
struct texandsprite
{
sf::Texture tex;
sf::Sprite spri;
};
class render
{
public:
static void start();
//Here will go a list of all moving entities
static texandsprite textures[5];
//Here will go a list of all nonmoving entities
//static
private:
static void GameLoop();
static void Rendering();
static sf::Texture loadTex(std::string);
static sf::Sprite loadSpri(sf::Texture);
static sf::Texture texture;
static sf::Sprite sprite;
static sf::RenderWindow _mainWindow;
};
#endif // RENDER_H_INCLUDED
Upvotes: 1
Views: 1359
Reputation: 3530
sf::Sprite render::loadSpri(sf::Texture temptex) { sf::Sprite tempspri; tempspri.setTexture(temptex); return tempspri; }
It's very related to sf::Texture as class member doesn't work?. Have a look at my answer there too.
What happens is that your sprite is set to display the temptex
but this texture is destroyed when the function returns since it is passed by value to the function.
You can fix this by using reference to sf::Texture
instead.
More details regarding your comment below. I simplify a little bit your situation and code to highlight what is really important to understand.
Generating a texture with a loadTexture()
like the following one is fine since only the returned copy is accessible to the user – he cannot set a sprite to use the original texture hence he won't suffer from the white square syndrome.
sf::Texture loadTexture(std::string name)
{
sf::Texture ret;
if (!ret.loadFromFile(name)) { doSomethingAboutIt(); }
return ret;
}
Regarding the loadSprite()
function, you can use a const ref to sf::Texture
as follow to prevent any copy and thus the white square problem.
sf::Sprite loadSprite(sf::Texture const& tex)
{
sf::Sprite ret(tex);
return ret;
}
But there is still one pitfall: you have to be careful how you store the texture returned by loadTexture()
! The life time of this texture should be as long as the life time of your sprite. Your code above (and below for reference) should work then:
void render::start()
{
_mainWindow.create(sf::VideoMode(1024, 768, 32), "A New Life");
textures[1].tex = loadTexture("civilian.png");
textures[1].spri = loadSprite(textures[1].tex);
GameLoop();
}
Upvotes: 3