0
\$\begingroup\$

I have created a kind of framework for a game that combines box2d and sfml. All game scenes are stored in the Game class. The scenes also contain information about static and dynamic objects: StaticObject and Object, which combine the capabilities of box2d and sfml. As well as the background class created for some tests. in general, when creating and playing a scene, background textures are displayed normally, but white rectangles are drawn instead of object and static object. And I don't understand what my problem is.

https://github.com/slverwolf/boxandsfmlClass

in the main loop, I create a Game class that contains a list of all the scenes and runs one of them using the update() method. class Game:

class Game
{
private:
    std::vector<std::unique_ptr<Scene>> GAME;
    std::vector<bool> isSceneActive;
public:
    //Функция добавляет сцену
    void addScene(std::unique_ptr<Scene> scene);
    //Выбрать проигрываемую сцену
    void setActiveScene(int num);
    //апдейт проигрываемой сцены
    void update(b2World& world, sf::RenderWindow &window);
};
void Game::update(b2World& world, sf::RenderWindow& window)
{
    for (int i = 0; i < GAME.size(); i++)
    {
        if (isSceneActive[i] == 1)
        {
            GAME[i].get()->update(world,window);
            return;
        }
    }
}

next, I create a child class of the Scene class, which describes what should happen in the scene

class Scene1 : public Scene
{
public:
    Scene1(b2World &world,sf::RenderWindow &window)
    {
        m_backGround.createSprite("Images\\Use\\Terrain\\back.png");
        Object box(world, "box", "Images\\Use\\Terrain\\box.png", 21, 16, 300, 100);
        Object box1(world, "box", "Images\\Use\\Terrain\\box.png", 21, 16, 400, 100);
        Object box2(world, "box", "Images\\Use\\Terrain\\box.png", 21, 16, 500, 100);
        this->addObject(box);
        this->addObject(box1);
        this->addObject(box2);
        StaticObject ground(world,"","Images\\Use\\Terrain\\wall.png",
            75*30,96,75*30/2,300,0);
        this->addStaticObject(ground);

    }
    virtual void update(b2World& world, sf::RenderWindow& window) override
    {
        std::cout << "children";
        m_backGround.update(window);

        for (int i = 0; i < m_staticObjects.size(); i++)
        {
            m_staticObjects[i].update(window);
        }

        for (int i = 0; i < m_objects.size(); i++)
        {
            m_objects[i].update(world, window);
        }

    }
};

Scene class, if necessary :

class Scene
{
protected:
    std::vector<Object> m_objects;
    std::vector<bool> m_isObjectLive;
    std::vector<StaticObject> m_staticObjects;
    BackGround m_backGround;
public:
    Scene() {};
    //Функция добавления в сцену объекта
    void addObject(Object &obj);
    void addStaticObject(StaticObject& obj);
    //Функция обновления сцены
    virtual void update(b2World& world, sf::RenderWindow& window);
    //метод удаляет все элементы вектора m_isobjLive,которые == 0
    //а так же соответствующий элемент m_objects
    void deleteDeadObj();
};

as you can see, as a result, there should be 5 objects in the scene: a rendered background, 3 boxes and one static platform. And they are. The background is drawn and box2d bodies are created. But instead of the textures of boxes and platforms, white squares are drawn.

backgroun class:

class BackGround
{
private:
    sf::Image m_image;
    sf::Texture m_texture;
    sf::Sprite m_sprite;
public:
    //Задать картинку бекгрануда
    BackGround();
    void update(RenderWindow& window);
    void createSprite(std::string imageWay);
};
BackGround::BackGround()
{

}

void BackGround::update(RenderWindow& window)
{
    window.draw(m_sprite);
}

void BackGround::createSprite(std::string imageWay)
{
    m_image.loadFromFile(imageWay);
    m_image.createMaskFromColor(sf::Color(255, 255, 255));
    m_texture.loadFromImage(m_image);
    m_texture.setRepeated(true);
    m_sprite.setTexture(m_texture);
    m_sprite.setTextureRect(IntRect(0, 0, 2000, 2000));
    m_sprite.setPosition(0, 0);
}

Object class:

class Object
{
private:
    //box2d
    FixtureUserData* m_Data;
    b2PolygonShape m_shape;
    b2BodyDef m_bDef;
    b2FixtureDef m_fDef;
    b2Body* m_body;
    //sfml
    sf::Image m_image;
    sf::Texture m_texture;
    sf::Sprite m_sprite;

    bool m_isDeleted = 0;

public:
    Object();
    ~Object();
    Object(b2World& world, std::string string, std::string imageWay,
        int w, int h, int x, int y);

    void setPos(b2World& world, int x, int y);
    void createSprite(std::string imageWay, int w, int h);
    void update(b2World& world, sf::RenderWindow& window);
    void draw(sf::RenderWindow& window);
    void del(b2World& world);

    b2Body* getBody();
};

Object::Object()
{

}

Object::~Object()
{

}

Object::Object(b2World &world,std::string string,std::string imageWay,int w,int h,int x,int y)
{
    m_shape.SetAsBox( PtoM(w/2), PtoM(h/2));
    m_bDef.type = b2_dynamicBody;
    m_bDef.position.Set(PtoM(x), PtoM(y));
    m_fDef.shape = &m_shape;
    m_fDef.density = 1;

    m_Data = new FixtureUserData;
    m_Data->objectType = "box";
    m_fDef.userData.pointer = reinterpret_cast<uintptr_t>(m_Data);

    m_body = world.CreateBody(&m_bDef);
    m_body->CreateFixture(&m_fDef);

    m_image.loadFromFile(imageWay);
    m_image.createMaskFromColor(sf::Color(255, 255, 255));
    m_texture.loadFromImage(m_image);
    m_sprite.setTexture(m_texture);
    m_sprite.setOrigin(w / 2, h / 2);
}

void Object::update(b2World &world, sf::RenderWindow& window)
{
    if (m_Data->shouldBeDeleted == 1)
        this->del(world);
    b2Vec2 pos = m_body->GetPosition();
    m_sprite.setPosition(MtoP(pos.x), MtoP(pos.y));
    this->draw(window);
}
void Object::draw(sf::RenderWindow &window)
{
    window.draw(m_sprite);
}

and finally the StaticObject class:

class StaticObject
{
private:
    FixtureUserData* m_Data;
    b2PolygonShape m_shape;
    b2BodyDef m_bDef;
    b2FixtureDef m_fDef;
    b2Body* m_body;
    //sfml
    sf::Image m_image;
    sf::Texture m_texture;
    sf::Sprite m_sprite;
public:
    //string- строка в userData
    //sence - осязаемость
    //w,h-Высота и ширина объекта
    //x,y - координаты центра . 
    //Объект - сенсор?
    //все в пикселях
    StaticObject(b2World& world, std::string string, std::string imageWay,
        int w, int h, int x, int y, bool sence);
    void createSprite(std::string imageWay, int x, int y, int w, int h);
    void update(sf::RenderWindow& window);
};
StaticObject::StaticObject(b2World& world, std::string string, std::string imageWay,
    int w, int h, int x, int y, bool sence)
{
    m_shape.SetAsBox(PtoM(w / 2), PtoM(h / 2));
    m_bDef.position.Set(PtoM(x), PtoM(y));
    m_fDef.shape = &m_shape;
    m_fDef.isSensor = sence;

    m_Data = new FixtureUserData;
    m_Data->objectType = string;
    m_fDef.userData.pointer = reinterpret_cast<uintptr_t>(m_Data);

    m_body = world.CreateBody(&m_bDef);
    m_body->CreateFixture(&m_fDef);

    this->createSprite(imageWay, x, y, w, h);
}

void StaticObject::createSprite(std::string imageWay, int x, int y, int w, int h)
{
    m_image.loadFromFile(imageWay);
    m_image.createMaskFromColor(sf::Color(255, 255, 255));
    m_texture.loadFromImage(m_image,sf::IntRect(0,0,75,96));
    m_texture.setRepeated(true);
    m_sprite.setTexture(m_texture);
    m_sprite.setTextureRect(sf::IntRect(0, 0, w, h));
    m_sprite.setOrigin(w / 2, h / 2);
    m_sprite.setPosition(x, y);
}



 void StaticObject::update(sf::RenderWindow& window)
    {
        window.draw(m_sprite);
    }
\$\endgroup\$
4
  • \$\begingroup\$ Unfortunately, we can't go to your project's page and browse all of your code to find that tiny problem. You need to provide an MCVE here on the site so that we can help you. \$\endgroup\$
    – Vaillancourt
    Sep 30 '21 at 16:11
  • \$\begingroup\$ @Vaillancourt, you are absolutely right. I have tried to fully describe the essence and as briefly as possible \$\endgroup\$
    – slverwolf
    Sep 30 '21 at 16:47
  • \$\begingroup\$ Start off by reading The white square problem. That'll give you a few clues. Namely, the way SFML shows how to use the code. They use stack objects but you should really use heap allocated objects (using new and delete (but preferably std::make_shared or std::make_unique)). \$\endgroup\$
    – Vaillancourt
    Sep 30 '21 at 17:14
  • \$\begingroup\$ (You could probably achieve this by making your objects non-copyable, non-movable by making them heap allocated objects.) \$\endgroup\$
    – Vaillancourt
    Sep 30 '21 at 18:25

You must log in to answer this question.

Browse other questions tagged .