Programmation GTK2 en Pascal/GtkLabel

Programmation GTK2 en Pascal

Présentation modifier

Le contrôle GtkLabel va nous permettre d'afficher du texte à l'intérieur de nos fenêtres.

Hiérarchie modifier

Hiérarchie
GObject
  └─GtkObject
      └─GtkWidget
          └─GtkMisc
              └─GtkLabel

Utilisation de base modifier

Création d'un label modifier

Après avoir déclarer un objet pLabel de type PGtkWidget, il faut utiliser la fonction :

function gtk_label_new(str : Pchar) : PGtkWidget;

Le paramètre str n'est autre que le texte qui sera affiché par le GtkLabel.

Modification du label modifier

Il peut arriver qu'au cours d'un programme, l'on veuille modifier le texte qui est affiché. La fonction à utiliser est la suivante :

procedure gtk_label_set_label(_label : PGtkLabel; str : Pgchar);

Le premier paramètre _label correspond au contrôle dont on veut modifier le texte, et le paramètre str est le nouveau texte qui sera affiché.

Récupération du label modifier

Pour récupérer le texte qui est affiché par un label, la fonction est :

function gtk_label_get_label(_label : PGtkLabel) : Pgchar;

Attention la valeur de retour est une variable constante, il ne faut donc pas essayer de la modifier.

Alignement du texte modifier

Maintenant, nous allons voir comment aligner notre texte lorsque celui-ci comporte plusieurs lignes. Comme d'habitude, GTK+ nous fourni une fonction très simple d'utilisation :

procedure gtk_label_set_justify(_label : PGtkLabel; jtype : TGtkJustification);

Le paramètre jtype correspond à l'alignement du texte et peut prendre une de ces valeurs :

  • GTK_JUSTIFY_LEFT pour aligner le texte à gauche (par défaut) ;
  • GTK_JUSTIFY_RIGHT pour aligner le texte à droite ;
  • GTK_JUSTIFY_CENTER pour centrer le texte ;
  • GTK_JUSTIFY_FILL pour justifier le texte.

Au contraire, pour obtenir l'alignement du texte, la fonction est :

function gtk_label_get_justify(_label : PGtkLabel) : TGtkJustification;

Programme exemple modifier

Nous allons, comme programme exemple, utiliser le classique « Hello Word! », traduit ici en « Bonjour tout le monde ! ».

Voilà le fichier gtk011.pas :

program gtk011;

uses glib2, gtk2;

var
  pFenetre    : PGtkWidget;
  pLabel      : PGtkWidget;
begin
  gtk_init(@argc, @argv);
  pFenetre := gtk_window_new(GTK_WINDOW_TOPLEVEL);
  gtk_window_set_position(GTK_WINDOW(pFenetre), GTK_WIN_POS_CENTER);
  gtk_window_set_default_size(GTK_WINDOW(pFenetre), 320, 200);
  gtk_window_set_title(GTK_WINDOW(pFenetre), 'Gtk011 : GtkLabel');
  gtk_signal_connect(pGTKOBJECT(pFenetre), 'destroy', GTK_SIGNAL_FUNC(@gtk_main_quit), NULL);

  // Création du GtkLabel et ajout dans la fenêtre
  pLabel := gtk_label_new('Bonjour tout le monde !');
  gtk_container_add(GTK_CONTAINER(pFenetre), pLabel);

  gtk_widget_show_all(pFenetre);
  gtk_main;
end.

Voilà ce que donne l'exécution du programme gtk011 :

 

Les caractères accentués modifier

Vous avez peut-être déjà essayé d'afficher du texte contenant des caractères tel que « é, è, à, ... » en n'ayant pas utilisé un éditeur de textes unicode (utf-8), et lors de l'exécution, votre texte ne s'affiche pas complètement. Nous allons maintenant voir le pourquoi du comment.

Application test modifier

Pour vous montrer tout cela, nous allons reprendre l'exemple précédent en remplaçant « Bonjour tout le monde » par « Texte à afficher », et cela ne marche pas ! En effet vous obtenez cela :

 

Et en plus sur la console, vous avez le message d'erreur suivant :

** (gtk012:3449): WARNING **: Invalid UTF8 string passed to pango_layout_set_text()

Comment ça marche ? modifier

Pour afficher du texte, Gtk utilise la librairie Pango qui s'occupe du rendu et de l'affichage du texte. Le but de Pango est de permettre l'internationalisation des applications, et pour cela Pango utilise l'encodage utf-8. Ce charset est codé de 1 à 4 octets permettant d'afficher 4 milliards caractères, afin d'afficher des caractères accentués et bien plus (ex : pour le grec, le chinois, etc.).

Puisque Pango sait faire tout cela, pourquoi le test n'a-t-il pas fonctionné ? Et bien, tout simplement parce que votre système d'exploitation n'utilise pas ce charset. Lorsque vous souhaitez afficher « Texte à afficher », Pango va avant tout vérifier l'encodage d'un caractère et si l'un de ces caractères n'est pas correct, Pango va arrêter son processus de rendu et envoyer un message d'erreur.

Le moyen le plus simple pour voir les effets d'une erreur d'encodage est de changer celui de votre navigateur. Modifiez les options de votre navigateur afin d'utiliser l'encodage iso-8859-1. Cette page web utilisant le charset unicode (utf-8), les caractères accentués deviendront des signes cabalistiques.

Solution modifier

Une seule chose s'impose à nous : il faut convertir notre chaîne de caractère en utf-8.

Pour cela, soit utiliser la première solution qu'on a utilisé des le début de ce cours qui est d'utiliser un éditeur de texte permettant la frappe et la sauvegarde de caractères codés en utf-8.

Soit utiliser une fonction de Glib qui est :

function g_locale_to_utf8(opsysstring : Pgchar; len : gssize; bytes_read : Pgsize; 
  bytes_written : Pgsize; error : PPGError) : Pgchar;

La valeur de retour est le pointeur sur la chaîne de caractère fraîchement convertie. Si une erreur est survenue lors de la conversion, g_locale_to_utf8 renvoie NULL. Il faudra tout de même libérer le mémoire allouée par cette fonction lorsque la variable ne sera plus utile.

Le premier paramètre opsysstring est la chaîne de caractère à convertir et le second paramètre len correspond à la longueur de la chaîne. Ce paramètre sera en général égal à -1 (on laisse la bibliothèque calculer la longueur toute seule).

Les trois derniers paramètres sont utiles en cas d'erreur lors de la conversion. Tout d'abord bytes_read est le nombre d'octet qui ont été lus dans le texte à convertir, et bytes_writen le nombre d'octet qui ont été écris dans la nouvelle chaîne de caractères. Le dernier paramètre error, donne plus de précision en cas d'erreur. Voici la liste des messages d'erreur possibles :

  • G_CONVERT_ERROR_NO_CONVERSION ;
  • G_CONVERT_ERROR_ILLEGAL_SEQUENCE ;
  • G_CONVERT_ERROR_FAILED ;
  • G_CONVERT_ERROR_PARTIAL_INPUT ;
  • G_CONVERT_ERROR_BAD_URI ;
  • G_CONVERT_ERROR_NOT_ABSOLUTE_PATH.

Attention cette fonction alloue de la mémoire. Lorsque vous n'avez plus besoin de la valeur de retour de cette fonction, il faut libérer la mémoire à l'aide de la fonction g_free.

Programme exemple modifier

Pour notre exemple, nous n'allons pas utiliser les trois derniers paramètres. En cas d'erreur, il n'y aura donc aucun moyen d'avoir plus de précision sur l'erreur survenue.

Voilà le fichier gtk013.pas (sauvegardé en codage ISO-8859-15) :

program gtk013;

uses glib2, gtk2;

var
  pFenetre    : PGtkWidget;
  pLabel      : PGtkWidget;
  Utf8        : PGChar;
begin
  gtk_init(@argc, @argv);
  pFenetre := gtk_window_new(GTK_WINDOW_TOPLEVEL);
  gtk_window_set_position(GTK_WINDOW(pFenetre), GTK_WIN_POS_CENTER);
  gtk_window_set_default_size(GTK_WINDOW(pFenetre), 320, 200);
  gtk_window_set_title(GTK_WINDOW(pFenetre), 'Gtk013 : GtkLabel (ISO-8859-15)');
  gtk_signal_connect(pGTKOBJECT(pFenetre), 'destroy', GTK_SIGNAL_FUNC(@gtk_main_quit), NULL);

  // Création du GtkLabel et ajout dans la fenêtre
  Utf8 := g_locale_to_utf8('Texte à afficher', -1, NULL, NULL, NULL);
  pLabel := gtk_label_new(Utf8);
  g_free(Utf8);
  gtk_container_add(GTK_CONTAINER(pFenetre), pLabel);

  gtk_widget_show_all(pFenetre);
  gtk_main;
end.

Voilà ce que donne l'exécution du programme gtk013 :

 

Formatage du texte modifier

Nous allons maintenant voir comment modifier l'apparence de notre texte (police, couleur, etc.).

Pour notre application test, nous allons afficher une ligne en Courier gras taille 10, une ligne en Times New Roman italique bleu taille 12, et une ligne en Verdana souligné taille 16. Et tout cela centré (bien sûr).

Définition du format modifier

Une fois encore, nous allons utiliser les propriétés de Pango (même si nous n'allons pas utiliser les fonctions de Pango directement).

Pour définir le format du texte, il suffit d'insérer des balises à l'intérieur même de notre texte. Pango s'occupe ensuite de rechercher les balises puis de formater le texte à notre convenance.

Les balises rapides modifier

Les balises rapides servent à mettre le texte en gras, italique ou autre de manière très simple. Voici l'intégralité de ces balises :

  • <b> : Met le texte en gras
  • <big> : Augmente légèrement la taille du texte
  • <i> : Met le texte en italique
  • <s> : Barre le texte
  • <sub> : Met le texte en indice
  • <sup> : Met le texte en exposant
  • <small> : Diminue légèrement la taille du texte
  • <tt> : Met le texte en télétype
  • <u> : Souligne le texte

Pour utiliser ces balises, il suffit d'encadrer le texte à modifier des balises de formatage. Par exemple, pour mettre le texte en gras, il faudra entrer : 'Normal vs <b>Gras</b>'.

Mais cela ne suffit pas, il faut aussi dire que le texte utilise les balises Pango, ce qui est possible avec la fonction suivante :

procedure gtk_label_set_use_markup(_label : PGtkLabel; setting : gboolean);

Il faut mettre le paramètre setting à TRUE, et le texte sera alors formaté en conséquence.

Un autre moyen de spécifier l'utilisation des balises, est d'utiliser cette fonction :

procedure gtk_label_set_markup(_label : PGtkLabel; str : Pgchar);

Cette fonction dit à Pango qu'il faut utiliser les balises, mais elle modifie aussi le label en affichant la chaîne de caractères str (deuxième paramètre).

La balise <span> modifier

Ici nous allons étudier la balise <span> en détail. Avec celle-ci, nous allons pouvoir changer la police de caractères, la couleur du texte et bien d'autres choses. Cette balise s'utilise comme les précédentes si ce n'est qu'elle accepte des paramètres. Le tableau ci-dessous présente tous les paramètres et les effets sur le texte.

  • font_family : Pour définir la police à utiliser. Si la valeur donnée à ce paramètre est incorrecte, la police par défaut (Sans Serif) sera utilisée. Exemple : <span font_family="Courier New">Courier New</span>.
  • face : Identique à font_family. Exemple : <span face="Times New Roman">Times New Roman</span>.
  • size : Pour définir la taille du texte (par défaut 10). Exemple : <span size="12">Taille 12</span>
  • style : Pour définir le style du texte. Trois valeurs possibles : normal, oblique, italic. Exemple : <span style="oblique">Oblique</span>.
  • font_desc : Permet de combiner les paramètres précédents en un seul. Exemple : <span font_desc="Courier New italic 12">Courier New italic 12</span>.
  • weight : Permet de définir l'épaisseur des lettres. Les valeurs peuvent être ultralight, light, normal, bold, utrabold, heavy ou encore une valeur numérique. (Vous remarquerez qu'il n'y a que peu ou pas de différence). Exemple : <span weight="bold">Bold</span>.
  • variant : Pour définir si l'on veut du texte normal (normal) ou en petite majuscule (smallcaps). Exemple : <span variant="smallcaps"> Smallcaps </span>. Afin de pourvoir l'utiliser, il faut avoir la police : nom smallcaps
  • stretch : Permet d'étirer le texte. La valeur de ce paramètre peut être : ultracondensed, extracondensed, condensed, semicondensed, normal, semiexpanded, expanded, extraexpanded, ultraexpanded. Afin de pourvoir l'utiliser, il faut avoir la police : nom condensed (ou autre).
  • foreground : Pour définir la couleur du texte. Il faut donner la valeur hexadécimale de la palette RVB. Exemple : <span foreground="#FF0000"> Couleur Texte </span>.
  • background : Pour définir la couleur du fond. Il faut donner la valeur hexadécimale de la palette RVB. Exemple : <span background="#FF0000"> Couleur Texte </span>.
  • underline : Pour souligner le texte. Exemple : <span underline="double">Double</span>.
  • rise : Pour déplacer le texte verticalement.
  • strikethrough : Pour barrer le texte. Exemple : <span strikethrough="true">Striketrough = "true"</span>
  • lang : Pour indiquer la langue du texte.

Tous ces paramètres peuvent être mis à l'intérieur d'une seule et même balise <span>.

Programme exemple modifier

Voilà le fichier gtk014.pas (sauvegardé en codage ISO-8859-15) :

program gtk014;

uses glib2, gtk2;

var
  pFenetre    : PGtkWidget;
  pLabel      : PGtkWidget;
  Utf8        : PGChar;
begin
  gtk_init(@argc, @argv);
  pFenetre := gtk_window_new(GTK_WINDOW_TOPLEVEL);
  gtk_window_set_position(GTK_WINDOW(pFenetre), GTK_WIN_POS_CENTER);
  gtk_window_set_default_size(GTK_WINDOW(pFenetre), 320, 200);
  gtk_window_set_title(GTK_WINDOW(pFenetre), 'Gtk014 : Formatage texte');
  gtk_signal_connect(pGTKOBJECT(pFenetre), 'destroy', GTK_SIGNAL_FUNC(@gtk_main_quit), NULL);

  // Création du GtkLabel et ajout dans la fenêtre
  pLabel := gtk_label_new(NULL);
  Utf8 := g_locale_to_utf8('<span face="Courier New"><b>Courier New 10 Gras</b></span>'#13#10 +
    '<span font_desc="Times New Roman italic 12" foreground="#0000FF">' +
    'Times New Roman 12 Italique</span>'#13#10 +
    '<span face="Sans" size="16"><u>Sans 16 Souligné</u></span>', -1, NULL, NULL, NULL);
  gtk_label_set_markup(GTK_LABEL(pLabel), Utf8);
  g_free(Utf8);
  gtk_container_add(GTK_CONTAINER(pFenetre), pLabel);

  gtk_widget_show_all(pFenetre);
  gtk_main;
end.

Voilà ce que donne l'exécution du programme gtk014 :

 

Note : On a beau jouer sur les différentes valeurs du paramètre size et même de face de la troisième ligne, celle-ci s'affiche en très petit. En cours de recherche...

Visuels : GtkLabel ~ GtkImage ~ GtkStatusBar ~ GtkProgressBar ~ GtkDrawingArea