Fonts: 5 ways to change the gtk+-2.0 text label font



Hello,
To change the default text label font in gtk+-2.0 you can:

0. Use gtk_widget_modify_font().
1. pango_layout_set_font_description().
2. ".rc" file.
3. gtk_label_set_attributes().
4. Pango markup language and gtk_label_set_markup().

There's a little demo in attach.

Olexiy

/*
        A little demo how to change the default font of label in 5 ways.
        Be aware: a couple of bugs can be found here.

Olexiy Avramchenko
*/

#include <gtk/gtk.h>


/*
        gtk_widget_modify_font
        This's the simpliest way to change the label's font :)
*/
static void font_set_way0(GtkEntry *entry, gpointer data)
{
GtkLabel                *label;
PangoFontDescription    *pfd;

        g_return_if_fail(GTK_IS_ENTRY(entry));
        g_return_if_fail(GTK_IS_LABEL(data));

        label = GTK_LABEL(data);

        /* creating PangoFontDescription from string, specified in entry */
        pfd = pango_font_description_from_string(gtk_entry_get_text(entry));
        /* setting label's font */
        gtk_widget_modify_font(GTK_WIDGET(label), pfd);
        /* freeing PangoFontDescription, cause it has been copied by prev. call */
        pango_font_description_free(pfd);
}

/*
        pango_layout_set_font_description
        Chaning the label's font with one more step.
*/
static void font_set_way1(GtkEntry *entry, gpointer data)
{
GtkLabel                *label;
PangoFontDescription    *pfd;

        g_return_if_fail(GTK_IS_ENTRY(entry));
        g_return_if_fail(GTK_IS_LABEL(data));

        label = GTK_LABEL(data);

        /* creating PangoFontDescription from string, specified in entry */
        pfd = pango_font_description_from_string(gtk_entry_get_text(entry));
        /* setting PangoFontDescription to label's layout */
        pango_layout_set_font_description(gtk_label_get_layout(label), pfd);
        /* asking label to resize/redraw itself, without this you'll not see the changes */
        gtk_widget_queue_resize(GTK_WIDGET(label));
        /* freeing PangoFontDescription, cause it has been copied by prev. call */
        pango_font_description_free(pfd);
}

/*
        Changing the font of label's text symbols 12..<end of text>.
        More complicated, but more powerfull way. Doesn't work if
        label is using underline or markup.
*/
static void font_set_way3(GtkEntry *entry, gpointer data)
{
GtkLabel                *label;
PangoAttrList           *pal;
PangoAttribute          *pa;
PangoAttrFontDesc       *pafd;
PangoFontDescription    *pfd;


        g_return_if_fail(GTK_IS_ENTRY(entry));
        g_return_if_fail(GTK_IS_LABEL(data));

        label = GTK_LABEL(data);

        /* creating PangoFontDescription from string, specified in entry */
        pfd = pango_font_description_from_string(gtk_entry_get_text(entry));

        /* creating empty PangoAttrList */
        pal = pango_attr_list_new();

        /* creating new PangoAttribute for font description */
        pafd = (PangoAttrFontDesc*)pa = pango_attr_font_desc_new(pfd);
        /* we want to apply this font only to chars from 12 to end of text */
        pa->start_index = 12;
        pa->end_index = g_utf8_strlen(gtk_label_get_text(label), -1); /* dont't forget the text is in utf8 */

        /* inserting attribute we created into the list */
        pango_attr_list_insert(pal, pa);

        /* setting label's attributes list */
        gtk_label_set_attributes(label, pal);

        /* list was referenced by label, so drop our reference */
        pango_attr_list_unref(pal);

        /* we dont need this, case it was already copied */
        pango_font_description_free(pfd);
}


/*
        Setting up widgets: setup_way[01234]
*/
static void setup_way0(GtkBox *box)
{
char      *font;
GtkWidget *hbox;
GtkWidget *entry;
GtkWidget *label;

        hbox = gtk_hbox_new(FALSE, 4);
        gtk_box_pack_start(box, hbox, TRUE,TRUE, 0);

        label = gtk_label_new("Font name");
        gtk_box_pack_start(GTK_BOX(hbox), label, FALSE,FALSE, 0);

        entry = gtk_entry_new();
        gtk_entry_set_width_chars(GTK_ENTRY(entry), 10);
        gtk_box_pack_start(GTK_BOX(hbox), entry, FALSE,FALSE, 0);

        label = gtk_label_new(" 0. The font of this label is changing via gtk_widget_modify_font ");
        gtk_box_pack_start(GTK_BOX(hbox), label, TRUE,TRUE, 0);

        font = pango_font_description_to_string(
                pango_context_get_font_description(
                        gtk_widget_get_pango_context(label)
                )
        );
        gtk_entry_set_text(GTK_ENTRY(entry), font);
        g_free(font);
        g_signal_connect(G_OBJECT(entry), "activate", G_CALLBACK(font_set_way0), (gpointer)label);
}

static void setup_way1(GtkBox *box)
{
char      *font;
GtkWidget *hbox;
GtkWidget *entry;
GtkWidget *label;

        hbox = gtk_hbox_new(FALSE, 4);
        gtk_box_pack_start(box, hbox, TRUE,TRUE, 0);

        label = gtk_label_new("Font name");
        gtk_box_pack_start(GTK_BOX(hbox), label, FALSE,FALSE, 0);

        entry = gtk_entry_new();
        gtk_entry_set_width_chars(GTK_ENTRY(entry), 10);
        gtk_box_pack_start(GTK_BOX(hbox), entry, FALSE,FALSE, 0);

        label = gtk_label_new(" 1. The font of this label is changing via pango_layout_set_font_description 
");
        gtk_box_pack_start(GTK_BOX(hbox), label, TRUE,TRUE, 0);

        font = pango_font_description_to_string(
                pango_context_get_font_description(
                        gtk_widget_get_pango_context(label)
                )
        );
        gtk_entry_set_text(GTK_ENTRY(entry), font);
        g_free(font);
        g_signal_connect(G_OBJECT(entry), "activate", G_CALLBACK(font_set_way1), (gpointer)label);
}

static void setup_way2(GtkBox *box)
{
GtkWidget *label;

        label = gtk_label_new(" 2. The font of this label set via .rc file ");

        /* in .rc file there's a font definition for widgets with this name */
        gtk_widget_set_name(label, "the_name_of_the_label");

        gtk_box_pack_start(box, label, TRUE,TRUE, 0);
}

static void setup_way3(GtkBox *box)
{
char      *font;
GtkWidget *hbox;
GtkWidget *entry;
GtkWidget *label;

        hbox = gtk_hbox_new(FALSE, 4);
        gtk_box_pack_start(box, hbox, TRUE,TRUE, 0);

        label = gtk_label_new("Font name");
        gtk_box_pack_start(GTK_BOX(hbox), label, FALSE,FALSE, 0);

        entry = gtk_entry_new();
        gtk_entry_set_width_chars(GTK_ENTRY(entry), 10);
        gtk_box_pack_start(GTK_BOX(hbox), entry, FALSE,FALSE, 0);

        label = gtk_label_new(" 3. The font of part of this label is changing via gtk_label_set_attributes ");
        gtk_box_pack_start(GTK_BOX(hbox), label, TRUE,TRUE, 0);

        font = pango_font_description_to_string(
                pango_context_get_font_description(
                        gtk_widget_get_pango_context(label)
                )
        );
        gtk_entry_set_text(GTK_ENTRY(entry), font);
        g_free(font);
        g_signal_connect(G_OBJECT(entry), "activate", G_CALLBACK(font_set_way3), (gpointer)label);
}

static void setup_way4(GtkBox *box)
{
GtkWidget *label;

        label = gtk_label_new(NULL);
        gtk_label_set_markup(GTK_LABEL(label), "<span font_desc=\"sans 10\">4. This label using</span><span 
foreground=\"red\" font_desc=\"fixed 14\"> Pango markup</span> ");
        gtk_widget_set_name(label, "the_name_of_the_label");
        gtk_box_pack_start(box, label, TRUE,TRUE, 0);
}


int main(int argc, char **argv)
{
GtkWidget *window;
GtkWidget *vbox;
GtkWidget *label;
GtkWidget *button;
GtkWidget *sep;

        gtk_init(&argc, &argv);

        /* process rc file, contains the font description */
        gtk_rc_parse("fonts.rc");

        window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
        gtk_container_set_border_width(GTK_CONTAINER(window), 8);
        g_signal_connect(G_OBJECT(window), "delete_event", G_CALLBACK(gtk_main_quit), NULL);

        vbox = gtk_vbox_new(FALSE, 2);
        gtk_container_add(GTK_CONTAINER(window), vbox);

        label = gtk_label_new("Type font description in entry and press <Enter>");
        gtk_box_pack_start(GTK_BOX(vbox), label, TRUE,TRUE, 4);

        sep = gtk_hseparator_new();
        gtk_box_pack_start(GTK_BOX(vbox), sep, TRUE,TRUE, 4);

        setup_way0(GTK_BOX(vbox));
        setup_way1(GTK_BOX(vbox));
        setup_way2(GTK_BOX(vbox));
        setup_way3(GTK_BOX(vbox));
        setup_way4(GTK_BOX(vbox));

        sep = gtk_hseparator_new();
        gtk_box_pack_start(GTK_BOX(vbox), sep, TRUE,TRUE, 4);

        button = gtk_button_new_with_label(" QuIt ");
        gtk_box_pack_start(GTK_BOX(vbox), button, TRUE,TRUE, 0);
        g_signal_connect(G_OBJECT(button), "clicked", G_CALLBACK(gtk_main_quit), NULL);

        gtk_widget_show_all(window);
        
        gtk_main();

        return 0;
}
style "label-style" {
        font_name = "fixed 14"
}

widget "*.the_name_of_the_label" style "label-style"
fonts: fonts.c
        gcc -Wall `pkg-config gtk+-2.0 --cflags --libs` $< -o $@
        strip -s fonts


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]