IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

SDL Discussion :

Boutons qui ne marchent qu'en debug (maintenant aide création mini gui SDL2) [SDL 2.0]


Sujet :

SDL

  1. #1
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2014
    Messages
    183
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 23
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2014
    Messages : 183
    Points : 60
    Points
    60
    Par défaut Boutons qui ne marchent qu'en debug (maintenant aide création mini gui SDL2)
    bonjour,
    je me suis rendu compte qu'on ne pouvait pas faire de boutons avec la SDL j'ai donc voulu créer une classe bouton moi-même.
    pour la tester j'ai fait une sorte de menu avec 4 boutons en debug tout marche parfaitement mais en release seulement 1 bouton est fonctionel (le bouton option) les autres apparaissent mais ne font rien
    voici mon code :
    main :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    #include <SDL2/SDL.h>
    #include <iostream>
    #include <SDL2/SDL_image.h>
    #include <SDL2/SDL_mixer.h>
    #include "button.h"
     
    void replay(); //pour relancer la musique
    void replay()
    {
        Mix_HaltMusic();
        Mix_PlayMusic(Mix_LoadMUS("./resources/musique.ogg"), -1);
    }
    int main(int argc, char **argv)
    {
        // Notre fenêtre
     
        SDL_Window* fenetre(0); //creation de la fenetre
        char* path = "./resources/fond.jpg"; //images (pour les boutons et le fond)
        char* resumebTex = "./resources/continuer.png";
        char* newbTex = "./resources/new.png";
        char* optbTex = "./resources/opt.png";
        char* quitbTex = "./resources/quit.png";
        char* onbTex = "./resources/on.png";
        char* clickbTex = "./resources/click.png";
        SDL_Event event;
        bool quit(false);
        // Initialisation de la SDL
     
        if(SDL_Init(SDL_INIT_VIDEO) < 0) //initialisation de la SDL
        {
            std::cout << "Erreur lors de l'initialisation de la SDL : " << SDL_GetError() << std::endl;
            SDL_Quit();
     
            return -1;
        }
     
     
        // initialisation de la fenêtre
     
        fenetre = SDL_CreateWindow("menu jeu", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, 450, 590, SDL_WINDOW_SHOWN);
        //fond
        SDL_Surface* imageDeFond;
        imageDeFond = IMG_Load(path);
        if ( imageDeFond )
        {
            SDL_Rect dest = { 450/2 - imageDeFond->w/2,590/2 - imageDeFond->h/2, 0, 0};
            SDL_BlitSurface(imageDeFond,NULL,SDL_GetWindowSurface(fenetre),&dest); // Copie du sprite
        }
        else
        {
            std::cout << "Échec de chargement du fond : " << SDL_GetError() << std::endl;
        }
        //creation des boutons
        button resumeb(225, 50, 324, 71, &resumebTex, &onbTex, &clickbTex, SDL_GetWindowSurface(fenetre));
        button newb(225, 170, 324, 71, &newbTex, &onbTex, &clickbTex, SDL_GetWindowSurface(fenetre));
        button optb(225, 290, 324, 71, &optbTex, &onbTex, &clickbTex, SDL_GetWindowSurface(fenetre));
        button quitb(225, 410, 324, 71, &quitbTex, &onbTex, &clickbTex, SDL_GetWindowSurface(fenetre));
     //initialisation musique    
    if( Mix_OpenAudio( 22050, MIX_DEFAULT_FORMAT, 2, 4096 ) == -1 )
        {
            return false;
        }
      //musique    
    Mix_PlayMusic(Mix_LoadMUS("./resources/musique.ogg"), -1);
    //boucle principale    
    while( quit == false )
        {
        SDL_PollEvent(&event);
     
     
    // Switch sur le type d'évènement
     
        switch(event.type)
        {
            case SDL_KEYDOWN:
     
            // Gestion des touches
     
                switch(event.key.keysym.scancode)
                {
                    case SDL_SCANCODE_ESCAPE:
                        quit=true;
                    break;
                }
            break;
            // Cas de la fermeture de la fenêtre
     
            case SDL_WINDOWEVENT:
                if(event.window.event == SDL_WINDOWEVENT_CLOSE)
                    quit = true;
     
            break;
            }
     //test effectués par les boutons 
            if(resumeb.check(&event))
            {
                SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_INFORMATION, "aucune partie", "vous n'avez pas de partie en cours", NULL);
            }
            if(optb.check(&event))
            {
                SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_INFORMATION, "option", "coming soon !", NULL);
            }
            if(newb.check(&event))
            {
                //c'était aussi pour montrer a ma soeur que n'importe qui pouvait faire un faux menu qui installe un virus (elle voulait en telecharger un) d'où le message qui suit
                SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_ERROR, "VIRUS", "j'aurais pu t'installer un virus", NULL);
            }
            if(quitb.check(&event))
            {
                quit = true;
            }
            //test musique finie
            Mix_HookMusicFinished(replay);
            //actualisation fenetre
            SDL_UpdateWindowSurface(fenetre);
        }
        //fermeture de la fenetre
        SDL_FreeSurface(imageDeFond);
        SDL_DestroyWindow(fenetre);
        Mix_CloseAudio();
        SDL_Quit();
        return 0;
    }
    button.h :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    #ifndef BUTTON_H
    #define BUTTON_H
    #include <SDL2/SDL.h>
    #include <SDL2/SDL_image.h>
    class button
    {
        public:
            button(int, int, int, int, char*[], char*[], char*[], SDL_Surface*);
            ~button();
            int m_x;
            int m_y;
            int m_w;
            int m_h;
            char* m_texture;
            char* m_on;
            char* m_click;
            bool check(SDL_Event*);
            SDL_Surface* m_onWhat; //best nom de variable ever
            SDL_Surface* imgTexture;
            SDL_Surface* imgOn;
            SDL_Surface* imgClick;
            SDL_Rect dest;
            bool clicked;
            bool onIt;
        protected:
        private:
    };
     
    #endif // BUTTON_H
    button.cpp :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    button::button(int x, int y, int w, int h, char* texture[], char* on[], char* click[], SDL_Surface* onWhat) : m_x(x-w/2), m_y(y+h/2), m_w(w), m_h(h), m_texture(*texture), m_on(*on), m_click(*click), m_onWhat(onWhat), onIt(false)
    {
        //chargement des images
        imgTexture = IMG_Load(m_texture);
        imgOn = IMG_Load(m_on);
        imgClick = IMG_Load(m_click);
        SDL_SetSurfaceAlphaMod(imgOn, 64);
        SDL_SetSurfaceAlphaMod(imgClick, 64);
        dest = { m_x, m_y, 0, 0};
        //texture du bouton ("on" et la couleur que va prendre le bouton quandon passe dessus et click quand on clique dessus)
        SDL_BlitSurface(imgTexture, NULL, m_onWhat, &dest);
    }
    button::~button()
    {
    }
    bool button::check(SDL_Event* event)
    {
        //cette fonction detecte quand la souris est sur le bouton ou quand on clique dessus (et applique une image dessus) et renvoie true si on a cliqué
        if(clicked == false)
        {
        if (event->button.y > m_y
         && event->button.y <= m_y+m_h  // si souris sur le boutton
         && event->button.x > m_x
         && event->button.x <= m_x+m_w)
         {
             //pour eviter d'appliquer la couleur 400 fois
             if(onIt == false)
             {
                SDL_BlitSurface(imgOn, NULL, m_onWhat, &dest);
                onIt = true;
             }
         }
         else
         {
                SDL_FreeSurface(m_onWhat);
                SDL_BlitSurface(imgTexture, NULL, m_onWhat, &dest);
                onIt = false;
         }
         }
        switch(event->type)
            {
     
                  case SDL_MOUSEBUTTONDOWN:
                  if (clicked == false && onIt == true)
                  {
                      SDL_FreeSurface(m_onWhat);
                      SDL_BlitSurface(imgTexture, NULL, m_onWhat, &dest);
                      SDL_UpperBlit(imgClick, NULL, m_onWhat, &dest);
                      clicked = true;
                  }
                  break;
                  case SDL_MOUSEBUTTONUP:
                  {
                     if(clicked == true && onIt == true)
                     {
                            clicked = false;
                            SDL_FreeSurface(m_onWhat);
                            SDL_BlitSurface(imgTexture, NULL, m_onWhat, &dest);
                            onIt = false;
                            return true;
                     }
                  }
            }
            return false;
     
    }
    si quelqu'un peut m'aider se serait cool
    merci

  2. #2
    Expert éminent sénior
    Avatar de Médinoc
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Septembre 2005
    Messages
    27 369
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 40
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2005
    Messages : 27 369
    Points : 41 518
    Points
    41 518
    Par défaut
    Ça, ça sent très mauvais:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
        imgTexture = *IMG_Load(m_texture);
        imgOn = *IMG_Load(m_on);
        imgClick = *IMG_Load(m_click);
    Généralement, quand une fonction de Load() retourne un pointeur, on est censé garder ce pointeur, et non pas ripper à la barbare les données pointées et leaker le pointeur.
    SVP, pas de questions techniques par MP. Surtout si je ne vous ai jamais parlé avant.

    "Aw, come on, who would be so stupid as to insert a cast to make an error go away without actually fixing the error?"
    Apparently everyone.
    -- Raymond Chen.
    Traduction obligatoire: "Oh, voyons, qui serait assez stupide pour mettre un cast pour faire disparaitre un message d'erreur sans vraiment corriger l'erreur?" - Apparemment, tout le monde. -- Raymond Chen.

  3. #3
    Membre émérite
    Avatar de skeud
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2011
    Messages
    1 091
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 1 091
    Points : 2 724
    Points
    2 724
    Billets dans le blog
    1
    Par défaut
    Salut, étrange en effet, tu utilise quel éditeur?
    Tu recompile toute les source lorsque tu passes en release?
    Rien ne se passe c'est a dire? pas de messageBox? Pas de changement d'état du bouton?
    Tu as essayer de mettre du debug dans la fonction de test de click sur tes bouton? Genre pour afficher sur la sortie standard lorsque tu clique sur un bouton?
    Pas de solution, pas de probleme

    Une réponse utile (ou +1) ->
    Une réponse inutile ou pas d'accord -> et expliquer pourquoi
    Une réponse à votre question


  4. #4
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2014
    Messages
    183
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 23
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2014
    Messages : 183
    Points : 60
    Points
    60
    Par défaut
    merci de me repondre aussi vite
    alors pour les pointeurs c'était juste un test j'ai oublié de remettre comme avant (j'avais oublié de mettre un dll et sa faisait des sigsegv donc j'ai cru que je m'était planté avec les pointeurs essayé de les enlever) je vais les remettre mais je ne pense pas que le problème vienne de la.

    j'utilise code::block et oui je recompile tout.
    pour les boutons sa fait comme si je n’appelait pas check() donc pas de changement ni de message box.
    Tu as essayer de mettre du debug dans la fonction de test de click sur tes bouton?
    tu veut dire qu'on peut mettre seulement une partie du code en debug ? si oui comment fait-on ?
    edit : je viens de remettre les pointeurs et maintenant plus aucun bouton ne marche o_O

  5. #5
    Membre émérite
    Avatar de skeud
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2011
    Messages
    1 091
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 1 091
    Points : 2 724
    Points
    2 724
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par RedSkidy Voir le message
    tu veut dire qu'on peut mettre seulement une partie du code en debug ? si oui comment fait-on ?
    Tout dépend de comment est configuré CB, normalement, en mode debug il doit définir _DEBUG ou un truc du genre, du coup il te suffit de:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    #ifdef _DEBUG
    std::cout << "mondebug" << std::endl;
    #endif
    Ce code ne sera compilé que en mode débug (ou tout du moins que si tu as un #define _DEBUG).
    Bref, essaye de mettre du debug dans ta fonction check pour voir par ou il passe .

    PS: n'hésiste pas dans les projet graphique comme ça d'utiliser un logger (->boost::log est génial pour ça). ça permet de déboguer très facilement, et beaucoup plus rapidement en activant les level de log.

    EDIT: houlalalalala, je viens juste de voir, dis moi, tu oublierais pas d'initialisé ta variable clicked par hasard sur tes boutons?
    Pas de solution, pas de probleme

    Une réponse utile (ou +1) ->
    Une réponse inutile ou pas d'accord -> et expliquer pourquoi
    Une réponse à votre question


  6. #6
    Expert éminent sénior

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 186
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 186
    Points : 17 126
    Points
    17 126
    Par défaut
    Ce qu'on veut dire par mettre du debug, c'est faire du debug à la main: mettre des cout<< là où on espère passer, et là où on veut vérifier des valeurs.
    Mes principes de bases du codeur qui veut pouvoir dormir:
    • Une variable de moins est une source d'erreur en moins.
    • Un pointeur de moins est une montagne d'erreurs en moins.
    • Un copier-coller, ça doit se justifier... Deux, c'est un de trop.
    • jamais signifie "sauf si j'ai passé trois jours à prouver que je peux".
    • La plus sotte des questions est celle qu'on ne pose pas.
    Pour faire des graphes, essayez yEd.
    le ter nel est le titre porté par un de mes personnages de jeu de rôle

  7. #7
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2014
    Messages
    183
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 23
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2014
    Messages : 183
    Points : 60
    Points
    60
    Par défaut
    si je fait sa en release cette partie seras en debug ou elle ne seras pas lue ?

  8. #8
    Membre émérite
    Avatar de skeud
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2011
    Messages
    1 091
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 1 091
    Points : 2 724
    Points
    2 724
    Billets dans le blog
    1
    Par défaut
    Si tu compile en debug, cette partie ne sera pas compiler donc non présent dans ton exécutable donc non exécuter, donc rien du tout. J'ai édité mon message par rapport à ta variable clicked, tu devrais vérifier . Je mets ma main à couper que le problème vient de la .
    Pas de solution, pas de probleme

    Une réponse utile (ou +1) ->
    Une réponse inutile ou pas d'accord -> et expliquer pourquoi
    Une réponse à votre question


  9. #9
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2014
    Messages
    183
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 23
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2014
    Messages : 183
    Points : 60
    Points
    60
    Par défaut
    ha c'est possible je vais voir sa peut poser problème ?

  10. #10
    Expert éminent sénior

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 186
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 186
    Points : 17 126
    Points
    17 126
    Par défaut
    En fait, avant toute chose, tu va dans les options de compilations, et tu actives les warnings:
    -Wall -Wextra

    Avec ca, tu va certainement avoir des tas de warnings.
    Il faut tous les régler "intelligemment", c'est à dire pas à grand coup de cast.
    Mes principes de bases du codeur qui veut pouvoir dormir:
    • Une variable de moins est une source d'erreur en moins.
    • Un pointeur de moins est une montagne d'erreurs en moins.
    • Un copier-coller, ça doit se justifier... Deux, c'est un de trop.
    • jamais signifie "sauf si j'ai passé trois jours à prouver que je peux".
    • La plus sotte des questions est celle qu'on ne pose pas.
    Pour faire des graphes, essayez yEd.
    le ter nel est le titre porté par un de mes personnages de jeu de rôle

  11. #11
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2014
    Messages
    183
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 23
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2014
    Messages : 183
    Points : 60
    Points
    60
    Par défaut
    ha oui c'était bien sa c'est bon sa marche !
    maintenant que tu le dit c'est vrai que mes tests avaient tous besoin de la valeur de clicked donc forcement...
    c'est assez destabilisant les valeurs par defaut en debug.
    enfin bref merci beaucoup

  12. #12
    Membre émérite
    Avatar de skeud
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2011
    Messages
    1 091
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 1 091
    Points : 2 724
    Points
    2 724
    Billets dans le blog
    1
    Par défaut
    Correction, en debug tu n'as pas de valeur par défault, rien à voir. C'est juste un coup de chance extraordinaire que ta variable soit initialisé à false.

    Lorsque tu compile, et qu'une variable n'est pas initialisé, elle va prendre une valeur au hasard parmis les valeur disponible (false et true pour un bool). Donc tu as eu de la chance qu'en debug, la zone mémoire allouer à ton bool contienne la valeur false et qu'en release elle contienne la valeur true et false suivant le bouton.

    Encore une bonne pratique à adopter: toujours initialiser les variabes, et comme précisé un peu plus haut, les option de compilation -Wall -Werror (-Wextra, perso je suis pas fan) te permettent de detecter les variable non initialisé (-Wall) et de traiter les warnings comme des erreur (-Werror).
    Pas de solution, pas de probleme

    Une réponse utile (ou +1) ->
    Une réponse inutile ou pas d'accord -> et expliquer pourquoi
    Une réponse à votre question


  13. #13
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2014
    Messages
    183
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 23
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2014
    Messages : 183
    Points : 60
    Points
    60
    Par défaut
    ce qui est bizarre c'est que j'ai tout recompilé 3 fois et j'avais toujours les mêmes resultats en debug et en release...
    sinon je voulais savoir est-ce que c'est possible de faire en sorte que le bouton "s'auto-check" pour que je ne soit pas obligé d'appeller check dans mon main pour chaque bouton (je sais pas avec un thread ?)

  14. #14
    Expert éminent sénior

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 186
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 186
    Points : 17 126
    Points
    17 126
    Par défaut
    Il faudrait qu'il démarre déjà checké? ajoute un argument optionnel au constructeur du bouton:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    button(int x, int y, int w, int h, char* texture[], char* on[], char* click[], SDL_Surface* onWhat, boolean checked=false)
    Et si possible utilise des std::string, ou à la rigueur des char const*
    Mes principes de bases du codeur qui veut pouvoir dormir:
    • Une variable de moins est une source d'erreur en moins.
    • Un pointeur de moins est une montagne d'erreurs en moins.
    • Un copier-coller, ça doit se justifier... Deux, c'est un de trop.
    • jamais signifie "sauf si j'ai passé trois jours à prouver que je peux".
    • La plus sotte des questions est celle qu'on ne pose pas.
    Pour faire des graphes, essayez yEd.
    le ter nel est le titre porté par un de mes personnages de jeu de rôle

  15. #15
    Membre émérite
    Avatar de skeud
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2011
    Messages
    1 091
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 1 091
    Points : 2 724
    Points
    2 724
    Billets dans le blog
    1
    Par défaut
    Non, comme tu décide de tout faire à la main, il faut que tu fasses tout à la main.

    Si tu veux des choses automatique il faut utiliser ce qu'on appelle des gui (cegui en est une excellente, ou Qt).

    Si tu veux quand meme faire à la main, il faut que tu fasse un système de gui, pour ça regarde, il y a plein de tuto la dessus .
    Pas de solution, pas de probleme

    Une réponse utile (ou +1) ->
    Une réponse inutile ou pas d'accord -> et expliquer pourquoi
    Une réponse à votre question


  16. #16
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2014
    Messages
    183
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 23
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2014
    Messages : 183
    Points : 60
    Points
    60
    Par défaut
    leternel :
    non la fonction check() est appellée a chaque event dans le main elle sert a verifier si on a cliqué sur le bouton
    skeud :
    tu t'est pas trompé de discution ?
    j'ai jamais dit que je voulais tout faire a la main (sinon j'utiliserais pas la SDL) je demandais en gros si je pouvais avoir un objet qui fait une boucle dans son coin en même temps que le main fait la sienne sans qu'il est besoin d'intervenir

  17. #17
    Membre émérite
    Avatar de skeud
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2011
    Messages
    1 091
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 1 091
    Points : 2 724
    Points
    2 724
    Billets dans le blog
    1
    Par défaut
    Citation Envoyé par RedSkidy Voir le message
    tu t'est pas trompé de discution ?
    j'ai jamais dit que je voulais tout faire a la main (sinon j'utiliserais pas la SDL) je demandais en gros si je pouvais avoir un objet qui fait une boucle dans son coin en même temps que le main fait la sienne sans qu'il est besoin d'intervenir
    Nop du tout . Ce que tu veux faire c'est un système de gui, la sdl n'est qu'un moteur graphique 2D (ne fait que l'affichage et la gestion des évènements). Ce que tu veux faire est un moteur de widget (qui gère l'affichage des boutons, le clique des bouton, les callback lorsque tu appuie sur un bouton etc.....). Pour faire ce que tu demandes, comme je t'ai dis deux solutions: à la main (donc créer ton moteur de widget) ou utilisé un moteur déjà existant s'appuyant sur ton moteur graphique (CEGUI s'applique sur la sdl pour afficher ses widgets).

    Comme tu semble parti pour le faire à la main, voici quelques indices:

    Un moteur de widget possède en général son propre thread afin de gérer les événements.
    Il possède aussi une classe de base contenant les information des widget (on va l'appeler "Widget") contenant ces informations: position du wiget, taille du widget et une fonction d'affichage.
    Tu peux donc créer une classe bouton, qui va venir redéfinir la fonction affichage pour dessiner comme tu le veux ton bouton, en rajoutant des information du style clicked, imgClicked (comme tu l'as fait). Plus un petit pointeur sur fonction OnButtonClicked, pour avoir une interaction lorsque l'on clique sur le bouton.

    Ensuite ton moteur de widget doit avoir une classe principale (on va l'appeler "App") qui fera tout le bazar de gestion des évènement clavier etc .....
    Voici rapidement un petit exemple de classe App:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    class App
    {
      public:
        App(int winx, int winy); // Construit ta fenêtre et fait appel à l'initialisation de la SDL
        ~App();
     
        AddWidget(Widget* add); // Rajoute une widget dans ton moteur
        Draw(); // Dessine les widget, cette fonction fera appel à la fonction d'affichage des widget
        RemoveWidget(Widget* remove); // Bah oui, faut bien pouvoir les supprimer quand meme :)
        GestionEvenement(); // Fonction qui gérera les événement de la sdl
        Run();  //Fonction principale qui se lance après l'ajout des widget
      private:
        std::list<Widget*> _List; // liste des widget, on la parcourra pour les évènement
    }
    Ensuite une petite class pour les bouton:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    class Button: public Widget
    {
      public:
        Button(int x, int y, int width, int height) : Widget(x, y, width, height); // Créer le bouton
        ~Button();
        Draw(); // Dessine le bouton, cette fonction est appelé par la fonction Draw de App lors du parcoure des widget
        GestionEvenement(SDL_Event &event); // Gère les évènement, c'est à cette endroit que tu mets ta gestion de click (la fonction check que tu avait faite)
      private:
        bool clicked;
        SDL_Surface * img_clicked;
        .... // Je te remet pas la suite, tu l'as déjà faite
    }
    Maintenant avec cette exemple, tu devrais comprendre comment faire un petit moteur simple avec plusieurs widget. Pour la gestion du clicked, un pointeur sur fonction dans le bouton devrait suffire.
    Ainsi ton moteur s'occupera de géré l'état de ton bouton pour l'afficher correctement en fonction du click.
    Le bouton s'occupera tout seul de géré les évènement transmit par la classe App. Et dans la classe App, lors d'un évènement, tu parcours tout les widget et tu effectue un test pour savoir si l’événement rentre dans l'espace de ta widget (en utilisant les attribut de la classe widget x, y, width, height).

    Si tu as d'autre question la dessus, je te répondrais, j'ai justement eu à faire un moteur de widget dans une ancienne boite, donc je connais bien le fonctionnement .

    En esperant avoir été clair .
    Pas de solution, pas de probleme

    Une réponse utile (ou +1) ->
    Une réponse inutile ou pas d'accord -> et expliquer pourquoi
    Une réponse à votre question


  18. #18
    Expert éminent sénior

    Femme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Juin 2007
    Messages
    5 186
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France, Essonne (Île de France)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Juin 2007
    Messages : 5 186
    Points : 17 126
    Points
    17 126
    Par défaut
    J'ai enfin compris ta question.

    actuellement, tu as le comportement suivant:
    1. une boucle infinie dans main cherche des événements.
    2. à chaque événement trouvé, main le transmet à chaque composant qu'il sait susceptible d'y réagir.
    3. chaque composant en fait ce qu'il veut.


    Ce qu'il te faut, c'est une collection de clickables
    Idéalement, je passerai par un EventManager du style suivant.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    class ClicAction{
        public:
            //généralement, je choisis de retourner un booléan pour signaler l'acceptation du clic
            virtual bool clic(int x, int y) const;
    };
     
    class EventManager {
        private:
            vector<std::unique_ptr<const ClicAction>> clic_handlers;
            SDL_Event event;
     
        public:
            //enregistrement
            void onClic(std::unique_ptr<const ClicAction> clickable) {clic_handlers.push_back(clickable);}
     
     
            //retourne true tant que l'application devrait continuer, et false pour l'arreter.
    	bool poll() const {
    		SDL_PollEvent(&event);
     
    		switch(event.type) {
    			case SDL_KEYDOWN:
    				// Gestion des touches
    				if(event.key.keysym.scancode == SDL_SCANCODE_ESCAPE) return false;
    				break;
     
    				// Cas de la fermeture de la fenêtre
    			case SDL_WINDOWEVENT:
    				if(event.window.event == SDL_WINDOWEVENT_CLOSE) return false;
    				break;
     
    			case SDL_MOUSEBUTTONDOWN:
    				clic(button.x, button.y);
    		}
     
    		return true;
    	}
     
            bool operator()() const {return poll();}//pour pouvoir écrire while (event_manager())
            operator bool () const {return poll();} //opérateur de conversion vers bool, pour pouvoir écrire while (event_manager)
            bool operator!() const {return !poll();} //opérateur de négation vers bool, pour pouvoir écrire if(!event_manager)
        private:
            //activation
            bool clic(int x, int y) const {
                bool accepted = false;
                for (auto clickable : clic_handlers) if (clickable->clic(x,y)) accepted = true;
                return accepted;
            }
    };
    ton code deviendrai alors proche de:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    int main() {
        EventManager event_manager;
     
        //creation des boutons
        button resumeb(225, 50, 324, 71, &resumebTex, &onbTex, &clickbTex, SDL_GetWindowSurface(fenetre));
        button newb(225, 170, 324, 71, &newbTex, &onbTex, &clickbTex, SDL_GetWindowSurface(fenetre));
     
        event_manager.onClic(resumeb);
        event_manager.onClic(newb);
     
     
        while(event_manager.poll()){
            //ici, les événements ont été gérés, ne reste qu'à manipuler le jeu.
        }
     
    }
    En améliorant un peu, tu peux créer une classe état, représentant les différents phases du jeu (menu principal, partie, options...).
    Cette classe contiendrait un EventManager et une UI.


    ps: @skeud j'aime notre facon de croiser les coups de mains.
    Mes principes de bases du codeur qui veut pouvoir dormir:
    • Une variable de moins est une source d'erreur en moins.
    • Un pointeur de moins est une montagne d'erreurs en moins.
    • Un copier-coller, ça doit se justifier... Deux, c'est un de trop.
    • jamais signifie "sauf si j'ai passé trois jours à prouver que je peux".
    • La plus sotte des questions est celle qu'on ne pose pas.
    Pour faire des graphes, essayez yEd.
    le ter nel est le titre porté par un de mes personnages de jeu de rôle

  19. #19
    Membre du Club
    Homme Profil pro
    Étudiant
    Inscrit en
    Mars 2014
    Messages
    183
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 23
    Localisation : France

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Mars 2014
    Messages : 183
    Points : 60
    Points
    60
    Par défaut
    skeud :
    je ne veut pas vraiment recréer une bibliothèque de GUI je fait juste une classe bouton (peut-être éventuellement une classe slider plus tard ainsi qu'une barre pour rentrer du texte/des chiffres dont je ne connais plus le nom) et en faisant moi-même je sais l'utiliser j'ai toutes les fonctionnalitées dont j'ai besoin et comme je ne code que ce dont j'ai besoin les classes devraient être plus rapide (devraient mais bon... on pourrait parfois remmetre en question l'optimisation de mes programmes)

    leternel :
    c'est bon j'ai utilisé SDL_Thread dans la classe bouton pour faire tourner en boucle la fonction check en même temps que le main mais sa fait un moment que je cherche comment avoir une fonction de callback qui peut prendre des arguments un peut comme sa :

    button b(arguments...,ma_fonction(a, b));
    c'est possible ?
    j'ai regardé les pointeurs sur fonction, les foncteurs, std::fonction mais j'ai rien trouvé qui me permettait de le faire ou alors j'ai pas compris comment.
    je pense qu'un pointeur sur fonction pourrait marcher mais je ne sait pas comment gérer les arguments

    dernière question : il faut que je fasse un thread pour tous les widget ou un par widget sa va ?

  20. #20
    Membre émérite
    Avatar de skeud
    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2011
    Messages
    1 091
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : France, Loire Atlantique (Pays de la Loire)

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2011
    Messages : 1 091
    Points : 2 724
    Points
    2 724
    Billets dans le blog
    1
    Par défaut
    L'idéal c'est de prendre un objet qui te servira de conteneur à callback :

    Tu as la classe Button : OK
    La classe ButtonEvent :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    class ButtonEvent
    {
      public:
        ButtonEvent();
        ~ButtonEvent();
        virtual void ButtonClicked() = 0;
    }
    il suffit que dans ta classe button tu ajoutes ceci:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    void addCallback(ButtonEvent* gestionnaire);
    ButtonEvent* GestionnaireDuBouton;
    Et dans ta fonction click:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    GestionnaireDuBouton->ButtonClicked();
    Ensuite tu créer les classe dont tu as besoin qui hérite de ButtonEvent.

    Sinon 2eme solution:

    un pointeur sur fonction:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    class Button
    {
      ....
      void addCallback (void(*func)(void*), void *param) {_func = func; _param = param};
      void click() {_func(_param)};
      ....
      private:
        void (*_func)(void*);
        void *_param;
    }
    et dans le main:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
     
    void callbackCfg(void *param)
    {
       ClassQuiFaitDesTrucs *CQFDT = (ClassQuiFaitDesTrucs *)param
       // le code que tu veux excuter lorsque l'on appuie sur le bouton et où tu peux utiliser la classe CQFDT :)
    }
     
    main(int ac, char **av)
    {
      ...
      ClassQuiFaitDesTrucs CQFDT;
      Button cfgButton;
      toto.AddCallback(&callbackCfg, &CQFDT);
      ...
    }
    Ensuite le fonctionnement est le meme pour les pointeur sur fonction, un peu de recherche sur internet ne te ferais pas de mal .

    EDIT:

    Un thread par widget? mais ça va pas non.XD
    Juste un thread pour le App comme dans mon exemple suffit largement (d'ailleur ton système de thread sur la fonction du bouton, c'est hyper mega pas du tout comme il faut ).

    PS: Si t'es vraiment feignant et que tu veux avoir du code (qui compile ptetre pas, jsuis pas un génie) pour un moteur simple avec juste des bouton, je peux t'en pondre un rapido cette aprem que tu auras à adapté en fonction de ce que tu veux .
    Pas de solution, pas de probleme

    Une réponse utile (ou +1) ->
    Une réponse inutile ou pas d'accord -> et expliquer pourquoi
    Une réponse à votre question


+ Répondre à la discussion
Cette discussion est résolue.
Page 1 sur 5 12345 DernièreDernière

Discussions similaires

  1. [swing][JButton] Des boutons qui disparaissent!
    Par soulhouf dans le forum Débuter
    Réponses: 12
    Dernier message: 19/08/2005, 13h51
  2. Api Win32 : boutons "qui bougent" au passage de la
    Par Spartan03 dans le forum Windows
    Réponses: 9
    Dernier message: 07/06/2005, 00h52
  3. Réponses: 10
    Dernier message: 10/06/2004, 17h20
  4. Réponses: 2
    Dernier message: 26/09/2003, 17h49

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo