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

GTK+ avec C & C++ Discussion :

Argument de callback erroné ?


Sujet :

GTK+ avec C & C++

  1. #1
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Février 2007
    Messages
    32
    Détails du profil
    Informations personnelles :
    Âge : 34
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 32
    Points : 35
    Points
    35
    Par défaut Argument de callback erroné ?
    Bonjour à tous !

    J'ai un petit souci avec un callback appelé lors de deux événements différents mais ne réagissant pas de la même façon. Le problème vient apparemment de la structure que je passe en argument supplémentaire ("data") qui ne contiendrais rien lors d'un appel, et ce qu'elle devrait lors de l'autre.

    Voici donc mes deux fonctions servant à lier le signal au callback :

    La première, pour la connexion du signal de déstruction de ma fenêtre :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    g_signal_connect( G_OBJECT( pApp->pWindow ), "delete_event", G_CALLBACK( onExit ), (gpointer) pApp );
    Avec cet appel au callback onExit, ma structure dont pApp est un pointeur ne contient rien, ou du moins pas ce qu'elle devrait (cf plus bas).

    Par contre, lorsque j'utilise la création de menus avec GtkUiManager, je n'ai aucun problème
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    gtk_action_group_add_actions( pApp->pActionGroup, menuEntries, G_N_ELEMENTS( menuEntries ), (gpointer) pApp );
    voici ma fonction onExit (les différents tests m'ont servi à me rendre compte du problème) :
    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
    void onExit( GtkWidget *widget, gpointer data ) {
       MainWindow *pApp = (MainWindow*) data;
     
       if ( GTK_IS_WINDOW( pApp->pWindow ) ) {
          /* si pApp->pWindow est bien une GTK_WINDOW, pas de pb */
          printf( "OK (window)\n" );
       }
       else {
          /* sinon, ça veux probablement dire que pApp n'est pas bon */
          fputs( "WW: pApp->pWindow is NOT a GtkWindow\n", stderr );
       }
       if ( GTK_IS_NOTEBOOK( pApp->pNotebook ) ) {
          /* si pApp->pNotebook est bien une GTK_NOTEBOOK, pas de pb */
          printf( "OK (notebook)\n" );
       }
       else {
          /* sinon, ça veux probablement dire que pApp n'est pas bon */
          fputs( "WW: pApp->pNotebook is NOT a GtkNotebook\n", stderr );
       }
     
       /* cette fonction n'est a besoin du paramètre data (pApp), d'où le problème réel */
       onCloseAll( widget, data ); 
     
       gtk_main_quit();
    }

    • Si j'appelle cette fonction via le menu de mon application, je n'ai aucun problème ("OK (window)" et "OK (notebook)" s'affichent pour le confirmer) ;
    • Mais par contre, lors de la fermeture de la fenêtre par un "delete_event", pApp->pWindow et pApp->pNotebook ne contienne plus ce qu'ils devraient, et les erreurs s'affichent ("WW: pApp->"...).



    Aurais-je fait une erreur dans la connexion du signal "delete_event" ?

    Merci d'avance !

  2. #2
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Février 2007
    Messages
    32
    Détails du profil
    Informations personnelles :
    Âge : 34
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 32
    Points : 35
    Points
    35
    Par défaut
    Rebonjour !

    J'ai avancé dans mon problème, du moins j'ai compris ce qui fait que ça ne marche pas.
    En fait, lorsque je clique sur la croix au coin (où ALT+F4), ma fenêtre est détruite, puis seulement man fonction est appelée. Ce qui fait forcement que mon paramètre devient obsolète

    Donc maintenant ma question, à laquelle je n'ai pas trouvé de réponse non plus, est : comment faire pour appeler une fonction lorsque l'utilisateur ferme la fenêtre, mais avant que celle-ci ne soit détruite ?

    J'ai bien trouvé que si la fenêtre est détruite, le widget ayant appelé la fonction existe toujours, mais ma fenêtre a quand-même disparu, et je n'arrive plus à la faire réapparaître si l'utilisateur le demande...
    (en pratique, je veux pouvoir arrêter la fermeture si le(s) fichiers ne sont pas enregistrés, et demander confirmation à l'utilisateur)


    Merci d'avance !

  3. #3
    Membre du Club

    Inscrit en
    Avril 2002
    Messages
    49
    Détails du profil
    Informations personnelles :
    Âge : 38

    Informations forums :
    Inscription : Avril 2002
    Messages : 49
    Points : 43
    Points
    43
    Par défaut
    Oui c'est normal , une fois ta fentre detruite elle n'existe plus donc forcement tu ne peux pas la faire reapparaitre. C'est un probeleme courant donc plutot facile a resoudre.

    La solution consiste tout simplement a renvoyer TRUE dans ta callback appellee par le signal "delete-event". En faisant ca ta window ne sera pas detruite lorsque tu clique sur la case de fermeture.

    Si tu veux la faire disparaitre utilise simplement la fonction suivante avant de faire ton return TRUE : gtk_widget_hide()

    Voila sa devrait resoudre ton probleme...;-)

  4. #4
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Février 2007
    Messages
    32
    Détails du profil
    Informations personnelles :
    Âge : 34
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 32
    Points : 35
    Points
    35
    Par défaut
    Bonsoir !

    Merci bien, ça marche parfaitement avec mon application de test

    Par contre, mon problème n'est pas tout à fait résolu...
    Le pointeur de données que je passe à ma fonction (data, dans l'exemple ci-dessus) est un pointeur vers une structure, contenant notamment mon pointeur vers la fenêtre, et un vers un notebook.

    Le problème est que j'ai besoin du notebook dans la fonction onExit (cf ci-dessus), mais que le pointeur data est apparemment totalement inutilisable lorsque je "ferme" (action de fermer, alt+F4 par ex.) là fenêtre. Y a-t-il une solution "miracle" pour que mon pointeur survive ?
    Faut-il que je crée plusieurs variable globales pour garder le notebook de côté ?

    Au passage, voici ma structure si besoin est :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    struct _MainWindow {
       GtkWidget *pWindow;
       GtkUIManager *pUiManager;
       GtkActionGroup *pActionGroup;
       GtkAccelGroup *pAccel;
       GtkWidget *pVBox;
       GtkWidget *pToolbar;
       GtkWidget *pNotebook;
       GtkWidget *pStatusBar;
    };
    Merci d'avance, et bonne soirée !

  5. #5
    Membre du Club

    Inscrit en
    Avril 2002
    Messages
    49
    Détails du profil
    Informations personnelles :
    Âge : 38

    Informations forums :
    Inscription : Avril 2002
    Messages : 49
    Points : 43
    Points
    43
    Par défaut
    Ben en fait lorsque tu detruis ta window qui est le container de ton notebook , GTK va automatique le detruire avec ainsi que tous les autre widget inclut dans la window.

    Alors je pense que la procedure devrait etre la meme que lorsque tu enleve un wigdte d'un container, la aussi GTK detruit le widget. Si on veux le reutiliser plus tard il faut ajouter une reference dessus en utilisant la fonction suivante : g_object_ref()

    Donc avant de detruite ta fenetre tu ajoute une reference sur le ou les objects que tu souhaaite garder. je pense que ca devrait marcher..;-)

  6. #6
    Nouveau membre du Club
    Profil pro
    Inscrit en
    Février 2007
    Messages
    32
    Détails du profil
    Informations personnelles :
    Âge : 34
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 32
    Points : 35
    Points
    35
    Par défaut
    Bonsoir !

    Merci de ta réponse ! Mais ça ne marche pas


    Mais j'ai trouvé la raison de mon problème, et par la même occasion la solution
    C'était effectivement les donnés que ma fonction recevait qui étaient erronées.

    En fait, lorsque la fenêtre reçoit le signal "delete_event", elle appelle une fonction du type
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    gboolean    user_function                  (GtkWidget *widget,
                                                GdkEvent  *event,
                                                gpointer   user_data)      : Run last
    (cf tout simplement la doc : delete_event)

    Ce qui fait que lorsque la fenêtre reçoit le signal, le paramètre que je croyais être un pointeur vers ma structure est en fait le GdkEvent du signal Alors fatalement, ça ne contient pas du tout ce que je veux :-°

    Par contre, pour mes menus, je dois garder une fonction de la forme
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    void        user_function                  (GtkButton *button,
                                                gpointer   user_data)      : Run first / Action
    ...


    Pour le moment, j'ai résolu le problème en créant deux fonctions semblables, une pour les boutons, l'autre pour le delete-event, simplement pour respecter les paramètres.
    Si vous avez une meilleur solution à me proposer qui me permettrai de n'avoir qu'une fonction, je serait fort heureux, mais je note en résolu car ça l'est, il faut l'avouer


    Merci et à bientôt !

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Passer un argument au callback
    Par kap dans le forum jQuery
    Réponses: 1
    Dernier message: 10/10/2013, 16h53
  2. fonction callback avec arguments
    Par YuGiOhJCJ dans le forum GTK+ avec C & C++
    Réponses: 12
    Dernier message: 12/04/2013, 08h42
  3. [Débutant] Arguments fonction callback
    Par Ayoub Khelifi dans le forum Interfaces Graphiques
    Réponses: 1
    Dernier message: 28/05/2012, 18h45
  4. Ajouter un évènement onclick avec un argument au callback
    Par _jey_ dans le forum Général JavaScript
    Réponses: 22
    Dernier message: 17/07/2009, 15h24
  5. Fonction callback avec arguments ?
    Par sorry60 dans le forum GTK+ avec C & C++
    Réponses: 39
    Dernier message: 07/11/2005, 10h41

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