2. Manuel de référence

Pour les sources, voir ez-draw.h, ez-draw.c.

2.1. Boucle principale

int ez_init()

Initialisation générale.

Renvoie 0 succès, -1 échec.

void ez_main_loop()

Boucle principale.

Cette fonction affiche les fenêtres créées, puis attend les évènements et appelle au fur et à mesure la fonction d’évènements correspondante (la callback) de la fenêtre concernée.

Pour interrompre la boucle principale, appeler ez_quit() dans une callback. Une fois revenu de ez_main_loop(), il ne faut plus faire aucun graphisme.

void ez_quit()

Fait sortir de ez_main_loop().

void ez_auto_quit(int val)

Modifie l’effet du bouton « Fermer » de la barre de titre d’une fenêtre, pour toutes les fenêtres du programme.

Par défaut (cas où val = 1), si on clique sur le bouton « Fermer » de n’importe quelle fenêtre d’un programme, il se termine immédiatement.

Vous pouvez changer ce comportement en invoquant ez_auto_quit() avec val = 0 : si ensuite l’utilisateur clique sur le bouton « Fermer » d’une fenêtre, le programme (au lieu de se terminer) recevra l’évènement WindowClose pour cette fenêtre ; libre alors à votre programme de décider ce qu’il veut faire :

Remarque : lorsque toutes les fenêtres sont détruites, le programme s’arrête.

2.2. Fenêtres

Chaque fenêtre a un identifiant unique, de type Ez_window :

type Ez_window

Identifiant d’une fenêtre.

Les fonctions suivantes permettent de créer ou manipuler des fenêtres :

Ez_window ez_window_create(int w, int h, const char *name, Ez_func on_event)

Crée et affiche une fenêtre, de largeur w et hauteur h, avec un titre name, et une fonction on_event (la callback) appelée pour chaque évènement (on_event peut être NULL).

Renvoie l’identifiant de la fenêtre, de type Ez_window.

Toute callback est de type Ez_func :

type Ez_func

Le type des callbacks, c’est-à-dire le prototype des fonctions appelées pour chaque évènement. Ce type est défini ainsi :

typedef void (*Ez_func)(Ez_event *ev);

Autrement dit, la fonction on_event passée en paramètre à ez_create_window() doit être de cette forme :

void on_event (Ez_event *ev);
int ez_window_get_id(Ez_window win)

Renvoie le numéro de la fenêtre comme un int.

void ez_window_destroy(Ez_window win)

Détruit la fenêtre win.

void ez_window_show(Ez_window win, int val)

Rend visible (val = 1) ou cache (val = 0) la fenêtre win.

void ez_window_set_size(Ez_window win, int w, int h)

Change la taille de la fenêtre.

void ez_window_get_size(Ez_window win, int *w, int *h)

Récupère la taille de la fenêtre.

void ez_window_clear(Ez_window win)

Vide la fenêtre (avec un fond blanc) et réinitialise les paramètres de dessin (couleur, épaisseur, fonte) aux valeurs par défaut.

void ez_send_expose(Ez_window win)

Envoie un évènement Expose a la fenêtre, pour la vider et la forcer à se redessiner.

2.3. Évènements

Chaque évènement est décrit par un struct de type Ez_event :

type Ez_event

Mémorise un évènement.

Ce type est défini dans ez-draw.h de la façon suivante :

typedef struct {
    int type;                       /* Expose, ButtonPress, etc                */
    Ez_window win;                  /* Identifiant de la fenêtre               */
    int mx, my;                     /* Coordonnées souris                      */
    int mb;                         /* Numéro bouton de la souris, 0 = aucun   */
    int width, height;              /* Largeur et hauteur                      */
    KeySym key_sym;                 /* Symbole touche : XK_Space, XK_q, etc    */
    char   key_name[80];            /* Pour affichage : "XK_Space", "XK_q", .. */
    char   key_string[80];          /* Chaine correspondante : " ", "q", etc   */
    int    key_count;               /* Taille de la chaine                     */
    /* Autres champs privés */
} Ez_event;

Le premier champ permet de connaître le type de l’évènement. Les différentes valeurs possibles sont :

Expose

Il faut redessiner toute la fenêtre.

ButtonPress

Bouton souris enfoncé.

ButtonRelease

Bouton souris relaché.

MotionNotify

Souris déplacée.

KeyPress

Touche clavier enfoncée.

KeyRelease

Touche clavier relachée.

ConfigureNotify

La fenêtre a changé de taille.

WindowClose

Le bouton « fermer » a été pressé.

TimerNotify

Le timer est arrivé à échéance.

2.4. Couleurs

Chaque couleur est désignée par un entier de type Ez_uint32.

void ez_set_color(Ez_uint32 color)

Mémorise la couleur color pour les prochains dessins, ainsi que pour l’affichage de texte.

Les couleurs suivantes sont prédéfinies : ez_black, ez_white, ez_grey, ez_red, ez_green, ez_blue, ez_yellow, ez_cyan, ez_magenta.

On peut fabriquer d’autres couleurs avec les fonctions suivantes :

Ez_uint32 ez_get_RGB(Ez_uint8 r, Ez_uint8 g, Ez_uint8 b)

Renvoie une couleur calculée à partir des niveaux r,g,b donnés entre 0 et 255.

Ez_uint32 ez_get_grey(Ez_uint8 g)

Renvoie une couleur grise calculée à partir de son niveau g donné entre 0 et 255.

Ez_uint32 ez_get_HSV(double h, double s, double v)

Renvoie une couleur calculée dans l’espace Hue, Saturation, Value.

h est un angle entre 0 et 360 degrés qui représente arbitrairement les couleurs pures ; s est la saturation, entre 0 et 1 ; v est la valeur de luminosité, entre 0 et 1. Pour en savoir plus, consulter l’article Teinte Saturation Valeur dans Wikipedia.

void ez_HSV_to_RGB(double h, double s, double v, Ez_uint8 *r, Ez_uint8 *g, Ez_uint8 *b)

Convertit une couleur de l’espace HSV en RGB.

Les intervalles sont : h entre 0 et 360, s et v entre 0 et 1, *r, *g, *b entre 0 et 255.

Comme exemples, voir demo-11.c et demo-12.c.

On obtient ces fenêtres :

demo-11 demo-12

2.5. Dessins

Les coordonnées sont relatives à l’origine, qui est le point en haut à gauche de l’intérieur de la fenêtre ; x va vers la droite et y va vers le bas.

Pour les rectangles et les cercles, x1,y1 et y2,y2 sont les coordonnées en haut à gauche et en bas à droite de la boîte englobante. Pour les points, les segments de droite et les triangles, on passe les coordonnées des sommets.

Par défaut, la couleur est le noir ; elle se change avec ez_set_color().

void ez_draw_point(Ez_window win, int x1, int y1)

Dessine un point.

void ez_draw_line(Ez_window win, int x1, int y1, int x2, int y2)

Dessine un segment.

void ez_draw_rectangle(Ez_window win, int x1, int y1, int x2, int y2)

Dessine un rectangle.

void ez_fill_rectangle(Ez_window win, int x1, int y1, int x2, int y2)

Dessine un rectangle plein.

void ez_draw_triangle(Ez_window win, int x1, int y1, int x2, int y2, int x3, int y3)

Dessine un triangle.

void ez_fill_triangle(Ez_window win, int x1, int y1, int x2, int y2, int x3, int y3)

Dessine un triangle plein.

void ez_draw_circle(Ez_window win, int x1, int y1, int x2, int y2)

Dessine un cercle.

void ez_fill_circle(Ez_window win, int x1, int y1, int x2, int y2)

Dessine un cercle plein.

Les dessins réalisés avec ez_draw_point(), ez_draw_line(), ez_draw_rectangle(), ez_draw_triangle(), ez_draw_circle() ont une épaisseur par défaut de 1 pixel. On peut modifier l’épaisseur avec :

void ez_set_thick(int thick)

Mémorise l’épaisseur thick (en pixels) pour les prochains dessins.

2.6. Texte et fontes

int ez_font_load(int num, const char *name)

Charge une fonte à partir de son nom (par exemple "6x13") et la stocke pour le numéro num.

Renvoie 0 succès, -1 erreur.

Le numéro de fonte doit être inférieur à EZ_FONT_MAX. Quelques fontes fixes sont préchargées par défaut :

  • Fonte numéro 0 : "6x13"

  • Fonte numéro 1 : "8x16"

  • Fonte numéro 2 : "10x20"

  • Fonte numéro 3 : "12x24"

Remarque :

sous X11, le nom peut avoir une forme quelconque mais doit correspondre à une fonte existante. Sous Windows, le nom doit être sous la forme largeurxhauteur (une fonte approchante de taille fixe est obtenue).

void ez_set_nfont(int num)

Mémorise le numéro de fonte num pour les prochains affichages de texte.

void ez_draw_text(Ez_window win, Ez_Align align, int x1, int y1, const char *format, ...)

Affiche du texte ; s’utilise comme printf.

Exemple :

ez_draw_text (win, EZ_TL, 10, 10, "Largeur = %d\nHauteur = %d", w, h);

Les coordonnées x1,y1 sont données par rapport à align, qui prend pour valeurs :

EZ_TL (Top Left)

EZ_TC (Top Center)

EZ_TR (Top Right)

EZ_ML (Middle Left)

EZ_MC (Middle Center)

EZ_MR (Middle Right)

EZ_BL (Bottom Left)

EZ_BC (Bottom Center)

EZ_BR (Bottom Right)

Le texte est tracé par dessus le dessin actuel ; on peut aussi faire effacer le fond en même temps (avec du blanc) en utilisant pour align les constantes :

EZ_TLF (Top Left Filled)

EZ_TCF (Top Center Filled)

EZ_TRF (Top Right Filled)

EZ_MLF (Middle Left Filled)

EZ_MCF (Middle Center Filled)

EZ_MRF (Middle Right Filled)

EZ_BLF (Bottom Left Filled)

EZ_BCF (Bottom Center Filled)

EZ_BRF (Bottom Right Filled)

Par défaut :
  • le texte est affiché avec la fonte numero 0 (6x13) ; se change avec ez_set_nfont().

  • le texte est affiché en noir ; se change avec ez_set_color().

2.7. Double-buffer d’affichage

L’affichage avec double-buffer permet d’éviter que la fenêtre ne clignote pendant qu’elle est rafraichie. Le principe est de dessiner dans le double-buffer, puis d’échanger celui-ci avec le contenu de la fenêtre quand tous les dessins sont finis. Tout est automatiquement géré par EZ-Draw.

void ez_window_dbuf(Ez_window win, int val)

Active ou inactive l’affichage double-buffer pour le window win.

Par défaut, l’affichage double-buffer est désactivé (val = 0).

Si l’affichage double-buffer est activé (val = 1) pour un window, les dessins dans ce window doivent obligatoirement être faits uniquement lors des évènements Expose de ce window. Si le double-buffer est inactivé, ce n’est plus une obligation, mais cela reste fortement conseillé.

Comme exemple, voir dans jeu-nim.c les fonctions gui_init(), win1_onKeyPress(), win1_onExpose().

Dans ce jeu, on peut tester l’affichage avec et sans le double-buffer (presser la touche d pour basculer entre l’un et l’autre) :

jeu-nim-2

2.8. Timers

Armer un timer signifie mémoriser une date dans le futur, qui est la date actuelle plus un certain délai. Lorsqu’on arrive à cette date future, on dit que le timer est arrivé à échéance.

Chaque fenêtre peut être associée à un timer. À l’échéance du timer, l’application reçoit un évènement unique TimerNotify pour le window concerné, puis le timer est supprimé.

void ez_start_timer(Ez_window win, int delay)

Arme un timer pour le window win avec un délai delay en millisecondes.

Tout rappel de cette fonction avant l’échéance du timer annule et remplace le timer. Si de plus delay vaut -1, alors le timer est supprimé (remarque : ce n’est pas une erreur de supprimer un timer déjà supprimé ou inexistant).

Comme exemple, voir demo-09.c.

2.9. Client-data

Chaque fenêtre peut mémoriser une donnée arbitraire du programme, par exemple une chaîne de caractères ou l’adresse d’un struct. On peut ensuite récupérer cette donnée à tout moment dans le programme. Ce mécanisme permet ainsi d’éviter l’emploi de variables globales.

void ez_set_data(Ez_window win, void *data)

Mémorise la donnée data dans la fenêtre win

void *ez_get_data(Ez_window win)

Renvoie la donnée associée à la fenêtre win.

Voici un exemple de programme qui affiche un cercle, dont les coordonnées sont placées dans une variable globale md :

 1#include "ez-draw.h"
 2
 3typedef struct {
 4    int x, y, r;
 5} Mes_donnees;
 6
 7Mes_donnees md;  /* 1. Variable globale */
 8
 9
10void win1_on_expose (Ez_event *ev)
11{
12    /* 3. Utilisation */
13    ez_draw_circle (ev->win, md.x-md.r, md.y-md.r, md.x+md.r, md.y+md.r);
14}
15
16
17void win1_on_event (Ez_event *ev)
18{
19   switch (ev->type) {
20        case Expose : win1_on_expose (ev); break;
21    }
22}
23
24
25int main ()
26{
27    if (ez_init() < 0) exit(1);
28
29    /* 2. Initialisation */
30    md.x = 200; md.y = 100; md.r = 50;
31
32    ez_window_create (400, 300, "Demo client-data 1", win1_on_event);
33
34    ez_main_loop ();
35    exit(0);
36}

Voici maintenant le même programme sans variable globale, en mémorisant la donnée dans la fenêtre :

 1#include "ez-draw.h"
 2
 3typedef struct {
 4    int x, y, r;
 5} Mes_donnees;
 6
 7
 8void win1_on_expose (Ez_event *ev)
 9{
10    /* 4. On retrouve les données attachées à la fenêtre */
11    Mes_donnees *md = ez_get_data (ev->win);
12
13    /* 5. Utilisation */
14    ez_draw_circle (ev->win, md->x-md->r, md->y-md->r, md->x+md->r, md->y+md->r);
15}
16
17
18void win1_on_event (Ez_event *ev)
19{
20   switch (ev->type) {
21        case Expose : win1_on_expose (ev); break;
22    }
23}
24
25
26int main ()
27{
28    Ez_window win1;
29    Mes_donnees md;  /* 1. Variable locale à main() */
30
31    if (ez_init() < 0) exit(1);
32
33    /* 2. Initialisation */
34    md.x = 200; md.y = 100; md.r = 50;
35
36    win1 = ez_window_create (400, 300, "Demo client-data 2", win1_on_event);
37
38    /* 3. On mémorise la donnée dans la fenêtre */
39    ez_set_data (win1, &md);
40
41    ez_main_loop ();
42    exit(0);
43}

Comme autre exemple, voir demo-10.c.

2.10. Le type image

EZ-Draw permet d’afficher ou de manipuler des images avec le type suivant :

type Ez_image

Type struct principal pour mémoriser une image.

Ce type est défini dans ez-image.h de la façon suivante :

typedef struct {
    int width, height;
    Ez_uint8 *pixels_rgba;
    int has_alpha;
    int opacity;
} Ez_image;

La largeur de l’image en pixels est width et sa hauteur est height.

Les pixels sont mémorisés dans le tableau pixels_rgba sous la forme R,G,B,A (pour rouge, vert, bleu, alpha, c’est-à-dire transparence) avec une valeur entre 0 et 255 (255 est l’intensité ou l’opacité maximale).

Les valeurs R,G,B,A d’un pixel de coordonnées x,y dans l’image sont mémorisées dans pixels_rgba[(y*width+x)*4 + 0..3].

Le champ has_alpha indique si le canal alpha est utilisé (has_alpha = 1) ou ignoré (has_alpha = 0) lors de l’affichage. Si le canal est ignoré, tous les pixels seront affichés ; s’il est utilisé, seuls les pixels opaques seront affichés.

Les pixels opaques sont les pixels dont le canal alpha est supérieur ou égal au seuil d’opacité, stipulé par le champ opacity ; par défaut le seuil d’opacité est 128.

Attention :

ne modifiez pas les champs width, height, pixels_rgba d’une image, car ils décrivent la mémoire qui a été allouée. En revanche, vous pouvez modifier les champs has_alpha, opacity, ainsi que la valeur des pixels dans pixels_rgba[]. On peut aussi utiliser les fonctions suivantes.

void ez_image_set_alpha(Ez_image *img, int has_alpha)
int ez_image_has_alpha(Ez_image *img)
void ez_image_set_opacity(Ez_image *img, int opacity)
int ez_image_get_opacity(Ez_image *img)

Récupére ou modifie les champs has_alpha et opacity.

Ces fonctions ne font rien si l’image img est NULL.

2.11. Gestion des images

Pour utiliser les fonctions suivantes il faut inclure ez-image.h.

Ez_image *ez_image_create(int w, int h)

Crée une image de largeur w et hauteur h en pixels.

Renvoie l’image créée, ou NULL si erreur.

Ez_image *ez_image_load(const char *filename)

Charge une image depuis le fichier filename. Le fichier doit être au format PNG, JPEG, GIF ou BMP.

La transparence est gérée pour les formats PNG, GIF et BMP : si le fichier contient un canal alpha, le champ has_alpha de l’image est mis à 1.

Renvoie l’image créée, ou NULL si erreur.

Ez_image *ez_image_dup(Ez_image *img)

Crée une copie profonde de l’image img.

Renvoie l’image créée, ou NULL si erreur.

void ez_image_destroy(Ez_image *img)

Détruit une image en mémoire.

Toutes les images créées par les fonctions ez_image_... doivent être libérées avec cette fonction.

void ez_image_paint(Ez_window win, Ez_image *img, int x, int y)

Affiche une image dans la fenêtre win, avec le coin supérieur gauche de l’image aux coordonnées x,y dans la fenêtre. Si img->has_alpha est vrai, applique la transparence, c’est-à-dire n’affiche que les pixels opaques.

void ez_image_paint_sub(Ez_window win, Ez_image *img, int x, int y, int src_x, int src_y, int w, int h)

Affiche une région rectangulaire d’une image dans la fenêtre win.

La région de l’image est délimitée par les coordonnées src_x, src_y (coin supérieur gauche) et src_x+w-1, src_y+h-1 (coin inférieur droit) dans l’image. Si les coordonnées dépassent l’image, seule la région appartenant effectivement à l’image est affichée.

Le coin supérieur gauche de la région est affiché aux coordonnées x,y dans la fenêtre. Si img->has_alpha est vrai, applique la transparence.

void ez_image_print(Ez_image *img, int src_x, int src_y, int w, int h)

Affiche une région rectangulaire d’une image dans le terminal.

La région de l’image img est délimitée par les coordonnées src_x, src_y (coin supérieur gauche) et src_x+w-1, src_y+h-1 (coin inférieur droit) dans img. Si les coordonnées dépassent l’image, seule la région appartenant effectivement à l’image est affichée.

2.12. Opérations sur les images

Cette section présente quelques opérations disponibles en incluant ez-image.h. Ces opérations sont faites sur les couleurs et sur le canal alpha.

void ez_image_fill_rgba(Ez_image *img, Ez_uint8 r, Ez_uint8 g, Ez_uint8 b, Ez_uint8 a)

Remplit une image avec une couleur r,g,b,a.

Les valeurs sont entre 0 et 255.

void ez_image_blend(Ez_image *dst, Ez_image *src, int dst_x, int dst_y)
void ez_image_blend_sub(Ez_image *dst, Ez_image *src, int dst_x, int dst_y, int src_x, int src_y, int w, int h)

Incruste une région de l’image src dans l’image dst.

La région de l’image source src est délimitée par les coordonnées src_x, src_y (coin supérieur gauche) et src_x+w-1, src_y+h-1 (coin inférieur droit). Cette région est incrustée dans l’image destination dst aux coordonnées dst_x, dst_y (coin supérieur gauche) et dst_x+w-1, dst_y+h-1 (coin inférieur droit).

Si les coordonnées dépassent les images src ou dst, seule la région commune est incrustée. Si l’image source n’a pas de canal alpha (c’est-à-dire si src->has_alpha est faux), alors les valeurs de la région de src écrasent celle de dst. Dans le cas contraîre, les régions sont mélangées par transparence (alpha blending) avec les formules de Porter et Duff.

Ez_image *ez_image_extract(Ez_image *img, int src_x, int src_y, int w, int h)

Crée une image contenant une copie d’une région rectangulaire de l’image source img.

La région de l’image est délimitée par les coordonnées src_x, src_y (coin supérieur gauche) et src_x+w-1, src_y+h-1 (coin inférieur droit) dans img. Si les coordonnées dépassent l’image, seule la région appartenant effectivement à l’image est extraite.

Renvoie NULL en cas d’erreur mémoire ou si l’intersection est vide.

Ez_image *ez_image_sym_ver(Ez_image *img)
Ez_image *ez_image_sym_hor(Ez_image *img)

Crée une image de même taille et propriétés que l’image source img, contenant le symétrique de l’image par rapport à l’axe vertical ou horizontal.

Renvoie la nouvelle image, ou NULL si erreur.

Ez_image *ez_image_scale(Ez_image *img, double factor)

Crée une image de taille multipliée par factor pour l’image source img, contenant l’image mise à l’échelle. Le facteur d’échelle factor doit être strictement positif.

Renvoie la nouvelle image, ou NULL si erreur.

Ez_image *ez_image_rotate(Ez_image *img, double theta, int quality)

Effectue une rotation de l’image source img d’angle theta en degrés. Renvoie une nouvelle image dont la taille est ajustée pour contenir le résultat, ou NULL en cas d’erreur.

Dans l’image résultat, le champs has_alpha est mis à 1, et les parties ne provenant pas de l’image source sont transparentes ; le but est qu’elles n’apparaissent pas lors de l’affichage.

Si quality = 1, l’algorithme utilisé lisse le résultat (avec une interpolation bilinéaire) ; si quality = 0, l’algorithme privilégie la rapidité (avec un calcul de plus proche voisin), ce qui permet de gagner environ un facteur 3.

Note :

le résultat étant indépendant du centre de rotation, il n’est pas demandé en paramètre ; on peut toutefois et indépendamment de la rotation elle-même, choisir arbitrairement un centre de rotation et calculer ses nouvelles coordonnées avec la fonction suivante :

void ez_image_rotate_point(Ez_image *img, double theta, int src_x, int src_y, int *dst_x, int *dst_y)

Calcule pour un point de coordonnées src_x,src_y dans l’image source, les nouvelles coordonnées dst_x,dst_y du point correspondant dans l’image résultat.

L’exemple demo-16.c illustre les rotations, sans ou avec transparence. Le centre de rotation (croix rouge) est déplaçable avec les flèches. On peut aussi modifier la qualité.

On obtient ces fenêtres :

demo-16-1 demo-16-2 demo-16-3

2.13. Accélérer l’affichage des images

Nous avons vu dans les sections précédentes le type Ez_image défini dans ez-image.h.

Ce type est commode pour charger des images, les transformer, les afficher. Toutefois, l’affichage d’une image prend quelques millisecondes à quelques dizaines de millisecondes, durée variable selon la taille de l’image et la puissance de la machine. La raison en est qu’à chaque affichage, ez_image_paint() refait toute la conversion depuis le type Ez_image en une image intermédiaire en mémoire, applique la transparence éventuelle, envoie le résultat à la carte graphique qui enfin l’affiche.

On peut afficher la durée des opérations dans le terminal, en définissant une variable d’environnement puis en relançant une démo : sous Unix, taper

export EZ_IMAGE_DEBUG=1

ou sous Windows, taper

set EZ_IMAGE_DEBUG=1

On obtient par exemple sous Unix :

$ ./demo-14
ez_image_load  file "images/paper1.jpg"  in 8.725 ms  w = 640  h = 480  n = 3  has_alpha = 0
ez_image_load  file "images/tux1.png"  in 1.946 ms  w = 210  h = 214  n = 4  has_alpha = 1
ez_xi_create  w = 640  h = 480  depth = 24  bpp = 32
ez_xi_fill_24 2.875 ms
ez_xi_create  w = 210  h = 214  depth = 24  bpp = 32
ez_xi_fill_24 0.132 ms
ez_xmask_create   fill 0.119 ms   bitmap 5.610 ms

Pour supprimer cette variable d’environnement sous Unix, taper

unset EZ_IMAGE_DEBUG

ou sous Windows, taper

set EZ_IMAGE_DEBUG=

Dans une animation, tous ces temps s’additionnent, et lorsqu’il y a beaucoup d’images, l’animation risque d’être saccadée. La solution est simple : convertir l’image de type Ez_image en un pixmap de type Ez_pixmap, puis afficher le pixmap.

typedef struct Ez_pixmap

Un pixmap est une image déjà convertie et stockée dans la carte graphique. Son affichage est donc beaucoup plus rapide, et de plus soulage le processeur de la machine.

Une fois créé, un pixmap est non modifiable.

Cette solution est aussi intéressante pour afficher une image de fond (qui est souvent de taille importante). Dans ce cas, on gagne encore en efficacité en utilisant une image sans canal alpha.

Le type Ez_pixmap est défini comme ceci :

typedef struct {
    int width, height;
    /* autres champs privés */
} Ez_pixmap

Les fonctions suivantes manipulent les pixmaps :

Ez_pixmap *ez_pixmap_create_from_image(Ez_image *img)

Crée un pixmap à partir d’une image img. Le pixmap conserve la transparence de l’image. L’image peut ensuite être libérée s’il n’y en a plus besoin.

Renvoie le nouveau pixmap, ou NULL si erreur.

void ez_pixmap_destroy(Ez_pixmap *pix)

Détruit le pixmap pix.

Les pixmaps doivent être détruits par cette fonction.

void ez_pixmap_paint(Ez_window win, Ez_pixmap *pix, int x, int y)

Affiche le pixmap pix dans la fenêtre win.

Le coin supérieur gauche du pixmap est affiché aux coordonnées x,y dans la fenêtre.

void ez_pixmap_tile(Ez_window win, Ez_pixmap *pix, int x, int y, int w, int h)

Affiche le pixmap pix de manière répétitive dans la fenêtre win.

Le pixmap est affiché à la manière d’un papier peint dans la zone de la fenêtre délimitée par les coordonnées x,y (coin supérieur gauche) et x+w-1,y+h-1 (coin inférieur droit).

L’exemple demo-17.c permet de tester la vitesse d’affichage, mesurée en fps (pour frame per second) dans une animation. Utiliser les touches + et - pour modifier le nombre de balles, et la touche p pour activer l’utilisation des pixmaps.

On obtient cette fenêtre :

demo-17

2.14. Divers

int ez_random(int n)

Renvoie un entier aléatoire entre 0 et n-1.

Remarque : le générateur de nombres aléatoires est initialisé par ez_init().

double ez_get_time()

Renvoie le temps écoulé depuis l”Epoch (le 1er janvier 1970 à 0h) en secondes avec une précision en microsecondes.

Cette fonction est utile pour mesurer la durée d’un calcul : il suffit d’appeler ez_get_time() avant et après le calcul, puis d’afficher la différence :

double t1, t2;
t1 = ez_get_time ();
calcul ();
t2 = ez_get_time ();
printf ("Durée du calcul : %.6f s\n", t2-t1)