diff options
author | Chris Wilson <chris@chris-wilson.co.uk> | 2007-02-23 11:23:55 +0000 |
---|---|---|
committer | Chris Wilson <cpwilson@src.gnome.org> | 2007-02-23 11:23:55 +0000 |
commit | 7e2654510c7fe848162021a698ddba2b90cf7d59 (patch) | |
tree | 9fb71782d78a56018f25753278c5e9cffb113286 | |
parent | 4074098e6fc909d6ae0dfe027303ac9887a10809 (diff) | |
download | vte-7e2654510c7fe848162021a698ddba2b90cf7d59.tar.gz |
Cache the font metrics on the vte_xft_font, avoids having to remeasure
2007-02-23 Chris Wilson <chris@chris-wilson.co.uk>
Cache the font metrics on the vte_xft_font, avoids having to remeasure
when opening a new terminal.
* src/vtexft.c: (_vte_xft_font_open), (_vte_xft_set_text_font):
svn path=/trunk/; revision=1727
-rw-r--r-- | ChangeLog | 7 | ||||
-rw-r--r-- | src/vtexft.c | 173 |
2 files changed, 102 insertions, 78 deletions
@@ -1,5 +1,12 @@ 2007-02-23 Chris Wilson <chris@chris-wilson.co.uk> + Cache the font metrics on the vte_xft_font, avoids having to remeasure + when opening a new terminal. + + * src/vtexft.c: (_vte_xft_font_open), (_vte_xft_set_text_font): + +2007-02-23 Chris Wilson <chris@chris-wilson.co.uk> + Share XftFonts between terminal backends and preserve faces from the previous draw - helps prevents font cache thrashing inside libXft. diff --git a/src/vtexft.c b/src/vtexft.c index fa4b6c29..a5782406 100644 --- a/src/vtexft.c +++ b/src/vtexft.c @@ -49,6 +49,9 @@ struct _vte_xft_font { VteTree *fontmap; VteTree *widths; guint last_pattern; + + gint width, height, ascent; + gboolean have_metrics; }; struct _vte_xft_data { @@ -143,6 +146,7 @@ _vte_xft_font_open (GtkWidget *widget, const PangoFontDescription *fontdesc, font->display = GDK_DISPLAY_XDISPLAY (gtk_widget_get_display (widget)); font->patterns = patterns; font->last_pattern = 0; + font->have_metrics = FALSE; if (font_cache == NULL) { font_cache = g_hash_table_new ( @@ -586,15 +590,8 @@ _vte_xft_set_text_font (struct _vte_draw *draw, const PangoFontDescription *fontdesc, VteTerminalAntiAlias antialias) { - struct _vte_xft_font *ft; - XftFont *font, *prev_font; - XGlyphInfo extents; struct _vte_xft_data *data; - gunichar wide_chars[] = {VTE_DRAW_DOUBLE_WIDE_CHARACTERS}; - guint i; - gint n, width, height, min = G_MAXINT, max = G_MININT; - FcChar32 c; - GPtrArray *locked_fonts; + struct _vte_xft_font *ft; data = (struct _vte_xft_data*) draw->impl_data; @@ -610,86 +607,106 @@ _vte_xft_set_text_font (struct _vte_draw *draw, return; } - gdk_error_trap_push (); data->locked_fonts[0] = ptr_array_zeroed_new (data->font->patterns->len); data->locked_fonts[1] = ptr_array_zeroed_new (data->font->patterns->len); - locked_fonts = data->locked_fonts [data->cur_locked_fonts&1]; - - draw->width = 1; - draw->height = 1; - draw->ascent = 1; - - n = width = height = 0; - /* Estimate a typical cell width by looking at single-width - * characters. */ - for (i = 0; i < sizeof (VTE_DRAW_SINGLE_WIDE_CHARACTERS) - 1; i++) { - c = VTE_DRAW_SINGLE_WIDE_CHARACTERS[i]; - font = _vte_xft_font_for_char (data->font, c, locked_fonts); - if (font != NULL) { - memset (&extents, 0, sizeof (extents)); - _vte_xft_text_extents (data->font, font, c, &extents); - n++; - width += extents.xOff; - if (extents.xOff < min) { - min = extents.xOff; - } - if (extents.xOff > max) { - max = extents.xOff; - } - if (extents.height > height) { - height = extents.height; + + if (data->font->have_metrics) { + draw->width = data->font->width; + draw->height = data->font->height; + draw->ascent = data->font->ascent; + } else { + XftFont *font, *prev_font; + XGlyphInfo extents; + gunichar wide_chars[] = {VTE_DRAW_DOUBLE_WIDE_CHARACTERS}; + guint i; + gint n, width, height, min = G_MAXINT, max = G_MININT; + FcChar32 c; + GPtrArray *locked_fonts; + + draw->width = 1; + draw->height = 1; + draw->ascent = 1; + + locked_fonts = data->locked_fonts [data->cur_locked_fonts&1]; + + gdk_error_trap_push (); + n = width = height = 0; + /* Estimate a typical cell width by looking at single-width + * characters. */ + for (i = 0; i < sizeof (VTE_DRAW_SINGLE_WIDE_CHARACTERS) - 1; i++) { + c = VTE_DRAW_SINGLE_WIDE_CHARACTERS[i]; + font = _vte_xft_font_for_char (data->font, c, locked_fonts); + if (font != NULL) { + memset (&extents, 0, sizeof (extents)); + _vte_xft_text_extents (data->font, font, c, &extents); + n++; + width += extents.xOff; + if (extents.xOff < min) { + min = extents.xOff; + } + if (extents.xOff > max) { + max = extents.xOff; + } + if (extents.height > height) { + height = extents.height; + } } } - } - if (n > 0) { - draw->width = howmany (width, n); - draw->height = (font != NULL) ? - font->ascent + font->descent : height; - draw->ascent = (font != NULL) ? - font->ascent : height; - } - /* Estimate a typical cell width by looking at double-width - * characters, and if it's the same as the single width, assume the - * single-width stuff is broken. */ - n = width = 0; - prev_font = NULL; - for (i = 0; i < G_N_ELEMENTS (wide_chars); i++) { - c = wide_chars[i]; - font = _vte_xft_font_for_char (data->font, c, locked_fonts); - if (font != NULL) { - if (n && prev_font != font) {/* font change */ - width = howmany (width, n); - if (width >= draw->width -1 && - width <= draw->width + 1){ - /* add 1 to round up when dividing by 2 */ - draw->width = (draw->width + 1) / 2; - break; + if (n > 0) { + draw->width = howmany (width, n); + draw->height = (font != NULL) ? + font->ascent + font->descent : height; + draw->ascent = (font != NULL) ? + font->ascent : height; + } + /* Estimate a typical cell width by looking at double-width + * characters, and if it's the same as the single width, assume the + * single-width stuff is broken. */ + n = width = 0; + prev_font = NULL; + for (i = 0; i < G_N_ELEMENTS (wide_chars); i++) { + c = wide_chars[i]; + font = _vte_xft_font_for_char (data->font, c, locked_fonts); + if (font != NULL) { + if (n && prev_font != font) {/* font change */ + width = howmany (width, n); + if (width >= draw->width -1 && + width <= draw->width + 1){ + /* add 1 to round up when dividing by 2 */ + draw->width = (draw->width + 1) / 2; + break; + } + n = width = 0; } - n = width = 0; + memset (&extents, 0, sizeof (extents)); + _vte_xft_text_extents (data->font, font, c, &extents); + n++; + width += extents.xOff; + prev_font = font; } - memset (&extents, 0, sizeof (extents)); - _vte_xft_text_extents (data->font, font, c, &extents); - n++; - width += extents.xOff; - prev_font = font; } - } - if (n > 0) { - width = howmany (width, n); - if (width >= draw->width -1 && - width <= draw->width + 1){ - /* add 1 to round up when dividing by 2 */ - draw->width = (draw->width + 1) / 2; + if (n > 0) { + width = howmany (width, n); + if (width >= draw->width -1 && + width <= draw->width + 1){ + /* add 1 to round up when dividing by 2 */ + draw->width = (draw->width + 1) / 2; + } } - } - gdk_error_trap_pop (); + gdk_error_trap_pop (); - _vte_debug_print (VTE_DEBUG_MISC, - "VteXft font metrics = %dx%d (%d)," - " width range [%d, %d].\n", - draw->width, draw->height, draw->ascent, - min, max); + data->font->width = draw->width; + data->font->height = draw->height; + data->font->ascent = draw->ascent; + data->font->have_metrics = TRUE; + + _vte_debug_print (VTE_DEBUG_MISC, + "VteXft font metrics = %dx%d (%d)," + " width range [%d, %d].\n", + draw->width, draw->height, draw->ascent, + min, max); + } } static int |