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+ Discussion :

Rafraichir une fenêtre avec image


Sujet :

GTK+

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Invité
    Invité(e)
    Par défaut Rafraichir une fenêtre avec image
    Bonjour,

    J'essaie de faire un démineur en GTK, et c'est la première fois que j'utilise cette librairie donc j'y connais vraiment rien.
    Donc voilà, mon démineur marchait bien dans la console uniquement avec les printf, mais un affichage graphique c'est toujours mieux. Donc j'ai fait les fonctions principales du démineur le problème étant que j'arrive pas à rafraîchir les cases que j'ai découvert. En gros, je veux qu'à chaque clicks de l'utilisateur, la programme réexécute ma fonction aff2 (qui permet d'afficher les images dans un grid). J'ai testé en faisant un affichage console et en cliquant sur la fenêtre GTK, ça marche, le problème vient donc de ma fonction aff je pense.
    Voilà le code simplifié du programme:
    https://pastebin.com/qfcUPt4S

    Cordialement.

  2. #2
    Expert confirmé
    Avatar de gerald3d
    Homme Profil pro
    Conducteur de train
    Inscrit en
    Février 2008
    Messages
    2 308
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Côte d'Or (Bourgogne)

    Informations professionnelles :
    Activité : Conducteur de train
    Secteur : Transports

    Informations forums :
    Inscription : Février 2008
    Messages : 2 308
    Billets dans le blog
    5
    Par défaut
    Bonjour.

    Le principe d'un affichage fenêtré repose sur celui des poupées russes. On crée une fenêtre principale dans la quelle on insère un widget quelconque et ainsi de suite...

    Au premier affichage tu insères dans ta table des GtkImage*. Pour pouvoir "rafraîchir" ta table il te faut supprimer ces GtkImage avant de pouvoir en insérer de nouveaux.

    Tu ne respectes pas le principe des poupées russes si tu essayes de mettre deux GtkWidget dans le même conteneur.

  3. #3
    Expert confirmé
    Avatar de gerald3d
    Homme Profil pro
    Conducteur de train
    Inscrit en
    Février 2008
    Messages
    2 308
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 55
    Localisation : France, Côte d'Or (Bourgogne)

    Informations professionnelles :
    Activité : Conducteur de train
    Secteur : Transports

    Informations forums :
    Inscription : Février 2008
    Messages : 2 308
    Billets dans le blog
    5
    Par défaut
    Pendant que j'y suis quelques remarques .

    Tu as créé une structure s_data. C'est une bonne chose . Elle contient le pointeur sur la fenêtre principale et le pointeur sur la table.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    struct s_data {
      GtkWidget *window;
      GtkWidget *table;
    };
    Pourquoi alors la fonction aff2(); à ce prototype : void aff2(GtkWidget * window, GtkWidget*table); ? Il suffit de transmettre le pointeur de data. Le prototype serait plutôt void aff2(struct s_data *data);. Tout ceci serait vrai bien entendu si tu initialises data avant l'appel à aff2();

    Histoire de pousser un peu plus loin, évite tant que faire ce peut les déclarations de variable en global, c'est à dire en dehors de toute fonction. Pour un code de 200 lignes ce n'est pas très génant, on arrive à retrouver nos petits, mais si tu codes un projet beaucoup plus gros et que tu gardes cette habitude, tu vas rapidement t'y perdre. Il serait peut être intéressant d'insérer dans la structure les deux tableaux :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    struct s_data {
      GtkWidget *window;
      GtkWidget *table;
     
      int tdj[12][12];
      int tdv[12][12];
    };
    Ainsi, il te suffit de propager data à toutes tes fonctions pour accéder aux données nécessaires. Et il n'y a plus de variables globales !

    Pour finir, tu charges les images depuis le disque dur à chaque rafraîchissement. Ce n'est pas très performant. Essaye de faire en sorte de ne les charger qu'une seule fois lors de l'initialisation. Tu les places dans un tableau auquel tu peux faire référence dans aff2 ();.

    J'arrête là mes petites remarques, constructives je l'espère .

  4. #4
    Modérateur

    Homme Profil pro
    Développeur informatique
    Inscrit en
    Juin 2009
    Messages
    1 395
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Développeur informatique
    Secteur : Industrie

    Informations forums :
    Inscription : Juin 2009
    Messages : 1 395
    Par défaut
    Bonjour, voilà quelques conseils:
    • - sépare le fond (l'état de test cases) de la forme (la manière dont tu les affiches)
    • - précharge et mets de côté toutes les images donc tu auras besoin
    • - utilise gtk_image_set_from_pixbuf pour mettre à jour le contenu des cases. Comme tu as déjà l'état de la case et chargé les images, tu as très peu de choses à faire dans cette fonction
    • - utilise snprintf pour générer le nom du fichier d'image ou g_strdup_printf, ça évite les d'écrire 15 fois la même chose avec just un chiffre qui change:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    image = gtk_image_new_from_file("0.png");
    Autre remarque, à quoi servent tdj et tdv ? On dirait que tu gères le contenu de la table et sa visibilité dans des tables différentes. Utilise plutôt une table unique et un masque de bits pour savoir si une case a été découverte. Pas besoin d'un int pour l'état d'une case, tu as 10 états possibles seulement (4 bits), et pour chaque état savoir si la case est découverte ou pas (1 bit). Donc un guint8 (équivalent d'un unsigned char) est suffisant.

    Coté GTK+, le delete-event ne te sert à rien, tu n'as que le signal destroy à gérer. Pour celà, on appelle en général gtk_main_quit() directement en tant que callback:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    g_signal_connect(window, "destroy", G_CALLBACK (gtk_main_quit), NULL);

  5. #5
    Invité
    Invité(e)
    Par défaut
    Bonjour,

    J'ai réussi à faire fonctionner mon code aujourd'hui, mais je vais l'améliorer avec tout ce que vous avez cité.
    Merci beaucoup.

    Cordialement.

Discussions similaires

  1. [WD14] Actualisation d'une fenêtre avec un champ image
    Par Raptor92 dans le forum WinDev
    Réponses: 1
    Dernier message: 01/11/2009, 17h06
  2. [C#] Imprimer le contenu d'une fenêtre avec ascenseur
    Par biglong dans le forum Windows Forms
    Réponses: 6
    Dernier message: 06/08/2007, 23h29
  3. rafraichir une liste avec un <SELECT>
    Par karibouxe dans le forum Général JavaScript
    Réponses: 4
    Dernier message: 20/02/2006, 09h05
  4. coordonnées d'une fenêtre avec window.open
    Par neecolas dans le forum Général JavaScript
    Réponses: 4
    Dernier message: 25/05/2005, 09h08
  5. [eclipse][plugin] Comment avoir une fenêtre avec focus
    Par relivio dans le forum Eclipse Java
    Réponses: 1
    Dernier message: 07/04/2004, 15h54

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