Forum de la communauté SFML

Aide => Graphique => Discussion démarrée par: Kitsu Hokkaido le Mars 25, 2017, 04:54:48 pm

Titre: Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 25, 2017, 04:54:48 pm
Bonjour,
Mon probléme est simple. Lorsque j'utilise un tableau de sf::Vertex et que je lui donne une taille supérieur à 100*100*4 (40 000), il y a un overflow. Mais si j'utilise sf::VertexArray et que je lui met une taille supérieur il n'y a aucun probléme. >:(
Merci de votre réponse.
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Laurent le Mars 25, 2017, 07:32:01 pm
Si ton tableau est déclaré sur la pile (sf::Vertex[100*100*4] dans une fonction), alors c'est normal. Si ce n'est pas le cas, alors montre nous comment et où il est déclaré.
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 25, 2017, 09:31:42 pm
Merci pour votre réponse.
Il n'est pas déclaré dans une fonction : (dans un fichier .h sous private)

#pragma once
#include "Include.h"

class TileMap : public sf::Drawable, sf::Transformable
{
public:
   bool loadMap(const std::string& image1, sf::Vector2u sizeTuile, const int* jeuxTuile, unsigned int posX, unsigned int posY);
   void cupTo(int x, int y, int carre, int width);

private:
   sf::Texture image;
   sf::Vertex quadV[100*100*4];

   int positionTuile;
   int reste;
   int division;
   int square, tailleMap, start, start1;

   virtual void draw(sf::RenderTarget& target, sf::RenderStates states) const
   {
      states.transform *= getTransform();
      states.texture = ℑ
      for (int i = start; i <start+square; i++)
      {
         for (int j = start1; j<start1+square; j++)
         {
            target.draw(&quadV[(i + j*tailleMap) * 4], 4, sf::Quads, states);
         }
      }
   }
};
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Laurent le Mars 26, 2017, 10:19:18 am
Ca ne fait que déplacer le problème, la question est maintenant : où et comment est déclarée ton instance de TileMap ?
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 26, 2017, 11:13:41 am
Voici comment je l'implémente: (je n'ai fais que suivre le cours en l'adaptant à un tableau non dynamique)

#include "TileMap.h"

bool TileMap::loadMap(const string& image1, sf::Vector2u sizeTuile, const int* jeuxTuile, unsigned int posX, unsigned int posY)
{
        if (!image.loadFromFile(image1))
        {
                return false;
        }

        for (unsigned int x = 0; x < posX; ++x)
        {
                for (unsigned int y = 0; y < posY; ++y)
                {
                        positionTuile = jeuxTuile[x + y*posX];

                        reste = positionTuile % (image.getSize().x / sizeTuile.x);
                        division = positionTuile / (image.getSize().x / sizeTuile.x);

                        sf::Vertex *quad;
                        quad = &quadV[(x + y * posX) * 4];

                        quad[0] = sf::Vertex(sf::Vector2f(x * sizeTuile.x, y * sizeTuile.y), sf::Vector2f(reste * sizeTuile.x, division * sizeTuile.y));
                        quad[1] = sf::Vertex(sf::Vector2f((x + 1) * sizeTuile.x, y * sizeTuile.y), sf::Vector2f((reste + 1) * sizeTuile.x, division * sizeTuile.y));
                        quad[2] = sf::Vertex(sf::Vector2f((x + 1)* sizeTuile.x, (y + 1)* sizeTuile.y), sf::Vector2f((reste + 1)* sizeTuile.x, (division + 1)* sizeTuile.y));
                        quad[3] = sf::Vertex(sf::Vector2f(x * sizeTuile.x, (y + 1) * sizeTuile.y), sf::Vector2f(reste * sizeTuile.x, (division + 1) * sizeTuile.y));
                }
        }

        return true;
}

void TileMap::cupTo(int x, int y, int carre, int width)
{
        square = carre;
        start = x;
        start1 = y;
        tailleMap = width;
}

Je sais qu'il y a des pertes de donnés au niveau de mon implémentation, (conversion de 'unsigned int' en 'float'). Ce doit être les répétions, mon probléme.
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Laurent le Mars 26, 2017, 02:43:28 pm
Je n'ai pas demandé comment était fait le reste de TileMap, mais où et comment tu en créais des instances.
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 26, 2017, 07:47:35 pm
Désolé, je ne comprends pas, vous voulez dire où est ce que je remplis mes fonctions ? Quand je les utilises ?
Dans ce cas comme ce ci :

#include "Main.h"

const int carte[]=
{/*je ne vais pas le remplir*/};

Main::Main()
{
        map.loadMap("Tiles.png", sf::Vector2u(32, 32), carte, 500, 500);
}

void Main::game()
{
        sf::RenderWindow window(sf::VideoMode(800, 600), "VertexTableau");
        while (window.isOpen())
        {
                sf::Event event;
                while (window.pollEvent(event))
                {
                        if (event.type == sf::Event::Closed)
                                window.close();
                }
                window.clear();
                map.cupTo(0, 0, 10, 500);
                window.draw(map);
                window.display();
}

int main(void)
{
      Main *main;
      main = new Main;

      main->game();

      delete main;
      return 0;
}

Et au cas ou le .h :

#include "TileMap.h"
#include "Include.h"

class Main
{
public:
        Main();
        ~Main();
        void game();
private:
        TileMap map;
};
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Laurent le Mars 26, 2017, 08:22:49 pm
Ok nous y voilà. Ton instance de TileMap est membre de la classe Main, et l'instance de Main est allouée sur le tas, donc... ton tableau de sf::Vertex n'est pas alloué sur la pile. Donc le problème ne vient pas de là.

Par contre le problème pourrait venir du fait que tu essayes de faire rentrer 500x500 cases dans un tableau de 100x100... ;)
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 26, 2017, 09:21:16 pm
Non, désolé, il se trouve que j'ai réssayé entre temps et que j'ai fais un copié collé du mauvais fichier. De plus, je viens de réssayer et ça ne marche toujours pas.
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 26, 2017, 09:26:12 pm
J'ajoute que ce n'est pas la même erreur qui se créer, il y a violation d'accés, mais pas un overflow.
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Laurent le Mars 26, 2017, 10:09:02 pm
Dans ce cas utilise ton debugger et regarde ce qu'il te dit. Ca sert à ça.
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 27, 2017, 03:39:14 pm
Il n'écrit rien à part des attentions. Mais aucune erreur, c'est quand je lance le jeu qu'il me dit Stack overflow
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Laurent le Mars 27, 2017, 06:26:08 pm
Toi tu parles du compilateur. Moi je te parle bien du debugger : le truc qui te dit où, quoi et comment ça plante à l'exécution.

Citer
Stack overflow
Information importante que tu aurais pu préciser plus tôt ;)
Donc c'est bien un dépassement de pile. Donc le debugger saura te dire où ça se passe, normalement.
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 28, 2017, 03:25:17 pm
Merci beaucoup, mais je l'ai dit au début (sans stack ).  :)
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Laurent le Mars 28, 2017, 05:50:16 pm
Citer
je l'ai dit au début (sans stack )
... stack ("pile" en anglais) étant bien entendu le mot important ;)

Sinon, toujours pas de debugger ?
Titre: Re : Probléme de Mémoire avec sf::Vertex
Posté par: Kitsu Hokkaido le Mars 30, 2017, 06:32:02 pm
Lorsque je l'utilise il m'ouvre une nouvelle page : "chkstk.asm", où je comprends rien, mais j'ai trouvé une solution, qui ne me plait pas trop. Je déclare mon tableau en dehors de la classe TileMap, mais du coup il est public(le tableau), ca m'embète un peu !!! :-\ :'( Si vous avez une autre solution !?

Re: Il semble que private soit une pile car, si je déclare mon tableau à l'intérieur :

class TileMap: public sf::Drawable, sf::Transformable
{
public:
        TileMap();
        ~TileMap();
private:
        sf::Vertex quadV[500 * 500 * 4];
};
Ca ne marche que si je déclare ma classe en dehors d'une autre classe :
class Main
{
public:
        Main();
        ~Main();
private:
};
TileMap carte;

peut être que je me tompe mais comme ça, ça marche.

Re: c'est bon j'ai trouvé, il faut que je le mettent en pointeur :
class Main
{
public:
        Main();
        ~Main();
private:
        TileMap *carte;
};
 

Donc, je ne vous embête plus, merci beaucoup pour votre aide !!