Gestion des événements claviers
Les fonctions set_flags et grab_focus sont membres de la classe Gtk::DrawingArea ou un de ces ancètres. En l'occurence, ces fonctions sont utiles pour tous les widgets et sont membres de la classe Gtk::Widget.
Événement clavier, par une fonction virtuelle
Il faut redéfinir la fonction bool on_key_press_event(GdkEventKey*) dans la classe ZoneDeJeu. La valeur de la touche est stockée dans le membre keyval de l'événement.
Événement clavier, par un signal
Il faut ajouter une fonction membre bool GestionClavier(GdkEventKey * event) à la classe ZoneDeJeu. Une fois cette fonction créee, on la connecte au signal key_press_event :
signal_key_press_event().connect(sigc::mem_fun(*this, &ZoneDeJeu::GestionClavier));
Pause
Une variable booléenne pause dans la classe ZoneDeJeu décrit l'état du jeu (en pause ou non). Cette variable est inversée lorsque le joueur appuie sur espace. Le code de la fonction de gestion des événements clavier devient :
if(event->keyval == GDK_space) { pause = !pause; }
La fonction MiseAJour ne déplacera les mobiles que si pause est faux.
Début et fin de partie
L'état de la partie peut être décrit par un enum, membre de la classe ZoneDeJeu :
enum Etat {Debut, Jeu, Pause, Fin};
Il faut aussi bien sur une variable membre de type Etat. Le code de la fonction de gestion des événements clavier devient :
if(event->keyval == GDK_space) { switch(etat) { case Debut : etat = Jeu; break; case Jeu : etat = Pause; break; case Pause : etat = Jeu; break; case Fin : etat = Debut; score = 0; break; } }
La fonction Dessiner est modifiée de façon similaire pour prendre en compte l'état de la partie :
switch(etat) { case Debut : std::ostringstream text; text << "appuyez sur espace pour commencer"; get_window()->draw_layout(gcTexte, 10,10, create_pango_layout(text.str())); break; case Jeu : case Pause : mobile.Dessiner(); std::ostringstream text; text << "score: " << score; get_window()->draw_layout(gcTexte, 10,10, create_pango_layout(text.str())); break; case Fin : std::ostringstream text; text << "fin de partie (appuyez sur espace), score:" << score; get_window()->draw_layout(gcTexte, 10,10, create_pango_layout(text.str())); break; }
Gestion de plusieurs mobiles
Au lieu d'avoir une variable membre de type Mobile dans la classe ZoneDeJeu, on met une variable de type std::vector<Mobile*>. Les mobiles sont initialisés dans le constructeur :
for(int i=0;i<10;i++) { mobiles.push_back(new Mobile()); }
Les fonctions PlusVite, MoinsVite, on_realize, Dessiner et MiseAJour appellent les fonctions correspondantes sur l'ensembles des mobiles.
Affichage d'images
Les images sont représentées par un objet de la classe Gdk::Pixbuf, utilisée de la façon suivante :
// Entête nécessaire #include <gdkmm/pixbuf.h> // On déclare un pointeur sur un Pixbuf Glib::RefPtr<Gdk::Pixbuf> image; // On charge une image à partir d'un fichier image=Gdk::Pixbuf::create_from_file("elephant.jpeg"); // On affiche avec draw_pixbuf, de la même façon qu'un rectangle est // dessiné avec draw_rectangle. window->draw_pixbuf(gc, image, 0, 0, x, y, image->get_width(), image->get_height(), Gdk::RGB_DITHER_NORMAL, 0, 0);
La fonction Gdk::Drawable::draw_pixbuf permet en fait de dessiner une zone d'un Pixbuf, avec les paramètres suivants :
-
gc: le contexte graphique nécéssaire aux fonctions de dessin. -
image: l'image à dessiner, de typeGlib::RefPtr<Gdk::Pixbuf>. -
srcXetsrcY: deux entiers, début de la zone duPixbufqui sera dessinée. -
destXetdestY: deux entiers, coordonnées de l'endroit dans la fenêtre où est dessinée l'image. -
widthetheight: largeur et hauteur de la zone de l'image à dessiner. -
des paramètres de tramage des couleurs, à laisser comme dans l'exemple ci-dessus.