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

Author Topic: [Solved] Sprite is drawn with additional graphics from used texture  (Read 2539 times)

0 Members and 1 Guest are viewing this topic.

Jimmyee

  • Newbie
  • *
  • Posts: 21
    • View Profile
EDIT: solved, look at the bottom of this post and thank you  :)

Hi. The challenge I have is to master the map rendering and I need help with solving this

I mean these tiles that are drawn right to the player. These additional tiles are drawn after every tile as you can see in this example where map size is 1x35. I have no clue what can cause it.

Here's the code I use to draw tiles:

/** gfxhandler.cpp */

shared_ptr<sf::Texture> GFXHandler::LoadTexture(std::string filename)
{
    map<std::string, shared_ptr<sf::Texture> >::iterator it;

    for(auto const &ent1 : textures)
    {
        if(ent1.first == filename)
        {
            return textures[filename];
        }
    }

    sf::Texture texture;
    if(!texture.loadFromFile(filename))
    {
        printf("GFXHandler: can't load texture %s\n", filename.c_str());
        return shared_ptr<sf::Texture>(0);
    }

    printf("GFXHandler: loaded %s\n", filename.c_str());
    textures[filename] = shared_ptr<sf::Texture>(new sf::Texture(texture));

    return textures[filename];
}

void GFXHandler::UnloadTexture(std::string filename)
{
    if(this->textures[filename].get())
    {
        this->textures[filename].reset();
    }
}

sf::Sprite GFXHandler::GetSprite(shared_ptr<sf::Texture> texture, unsigned int id)
{
    sf::Vector2u tsize = texture->getSize();
    sf::Sprite sprite;
    sprite.setTexture(*texture.get());

    int rectx = 0;
    int recty = 0;

    unsigned int yrows = (id * 32) / tsize.x;
    rectx = (id * 32) % tsize.x;
    recty = yrows * 32;

    sprite.setTextureRect(sf::IntRect(rectx, recty, rectx + 32, recty + 32));

    return sprite;
}

/** gfxhandler.hpp */

class GFXHandler
{
private:
map<std::string, shared_ptr<sf::Texture> > textures;

public:
shared_ptr<sf::Texture> LoadTexture(std::string filename);
void UnloadTexture(std::string filename);
sf::Sprite GetSprite(shared_ptr<sf::Texture> texture, unsigned int id);
};

/** map.cpp */
Map::Map(string filename, shared_ptr<GFXHandler> gfxhandler)
: datafile(filename)
{
    this->gfxhandler = gfxhandler;
    this->width = datafile.GetNumber();
    this->height = datafile.GetNumber();

    shared_ptr<sf::Texture> tex = this->gfxhandler->LoadTexture("gfx/map/1.png");

    this->layers[0].xrows.resize(this->width);

    for(int i = 0; i < this->width; ++i)
    {
    this->layers[0].xrows[i].yrow.tiles.resize(this->height);
        for(int ii = 0; ii < this->height; ++ii)
        {
            int id = datafile.GetNumber();
            this->layers[0].xrows[i].yrow.tiles[ii] = shared_ptr<Tile>(new Tile(id));
            shared_ptr<Tile> tile = this->layers[0].xrows[i].yrow.tiles[ii];
            if(tile->id != 0)
            {
                tile->sprite = gfxhandler->GetSprite(tex, tile->id - 1);
                tile->sprite.setPosition(sf::Vector2f(i * 32, ii * 32));
            }
            else
            {
                puts("Map: empty tile detected\n");
            }
        }
    }

    printf("Map created, %ix%i\n", this->width, this->height);
}

void Map::Draw(sf::RenderWindow *window, int x, int y)
{
    for(int i = 0; i < this->width; ++i)
    {
        for(int ii = 0; ii < this->height; ++ii)
        {
            shared_ptr<Tile> tile = this->layers[0].xrows[i].yrow.tiles[ii];
            int tile_x = i * 32 + x;
            int tile_y = ii * 32 + y;
            tile->sprite.setPosition(sf::Vector2f(tile_x, tile_y));
            window->draw(tile->sprite);
        }
    }
}

/** map.hpp */

class Map
{
public:
struct Tile
{
    unsigned int id;

    sf::Sprite sprite;

    Tile()
    : id(0)
    {
    }

    Tile(unsigned int id_)
    : id(id_)
    {

    }
};

struct Layer
{
    struct XRow
    {
        struct YRow
        {
            vector<shared_ptr<Tile>> tiles;
        } yrow;
    };

    vector<XRow> xrows;
};

private:
    DataFile datafile;
    int width;
    int height;
    Layer layers[1];

    shared_ptr<GFXHandler> gfxhandler;

public:
    Map(string filename, shared_ptr<GFXHandler> gfxhandler);
    void Draw(sf::RenderWindow *window, int x, int y);
    int Width() { return width; }
    int Height() { return height; }
};

 

Any help really appreciated...

EDIT!!!

 I've found the answer, this is not really anything serious...

In GFXHandler::GetSprite() function:
sprite.setTextureRect(sf::IntRect(rectx, recty, 32, 32));
// instead of sprite.setTextureRect(sf::IntRect(rectx, recty, rectx + 32, recty + 32));
 

Sorry for bothering anyone and it would be nice if someone delete this thread... ;)
« Last Edit: May 03, 2016, 10:58:48 am by Jimmyee »