[gtksourceview] gutterrenderertext: cache common widths
- From: Christian Hergert <chergert src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gtksourceview] gutterrenderertext: cache common widths
- Date: Tue, 22 Jun 2021 18:58:55 +0000 (UTC)
commit d6c7228a0f31549f341e9bf59b8538288dbf3915
Author: Christian Hergert <chergert redhat com>
Date: Tue Jun 22 11:58:41 2021 -0700
gutterrenderertext: cache common widths
Generally, this widget is used as the base for line drawing. Additionally,
it is generally used in a monospace fashion.
Until we have a reason to consider alternatives, we should aggressively
cache the widths and re-use them to avoid calculating layout sizes on
every line number.
This caches them by common sizes (1..5) so that we only do that once per
snapshot per width.
gtksourceview/gtksourcegutterrenderertext.c | 68 ++++++++++++++++++++++++-----
1 file changed, 56 insertions(+), 12 deletions(-)
---
diff --git a/gtksourceview/gtksourcegutterrenderertext.c b/gtksourceview/gtksourcegutterrenderertext.c
index 14c8d8f9..eff0e402 100644
--- a/gtksourceview/gtksourcegutterrenderertext.c
+++ b/gtksourceview/gtksourcegutterrenderertext.c
@@ -31,12 +31,19 @@
* #GtkSourceGutter.
*/
+typedef struct
+{
+ int width;
+ int height;
+} Size;
+
typedef struct
{
gchar *text;
PangoLayout *cached_layout;
GdkRGBA cached_color;
gsize text_len;
+ Size cached_sizes[5];
guint is_markup : 1;
} GtkSourceGutterRendererTextPrivate;
@@ -50,6 +57,45 @@ enum
N_PROPS
};
+static void
+gtk_source_gutter_renderer_text_clear_cached_sizes (GtkSourceGutterRendererText *text)
+{
+ GtkSourceGutterRendererTextPrivate *priv = gtk_source_gutter_renderer_text_get_instance_private
(text);
+
+ for (guint i = 0; i < G_N_ELEMENTS (priv->cached_sizes); i++)
+ {
+ priv->cached_sizes[i].width = -1;
+ priv->cached_sizes[i].height = -1;
+ }
+}
+
+static inline void
+gtk_source_gutter_renderer_text_get_size (GtkSourceGutterRendererTextPrivate *priv,
+ PangoLayout *layout,
+ int text_len,
+ int *width,
+ int *height)
+{
+ g_assert (text_len > 0);
+
+ if G_UNLIKELY (text_len > G_N_ELEMENTS (priv->cached_sizes) ||
+ priv->cached_sizes[text_len-1].width == -1)
+ {
+ pango_layout_get_pixel_size (layout, width, height);
+
+ if (text_len <= G_N_ELEMENTS (priv->cached_sizes))
+ {
+ priv->cached_sizes[text_len-1].width = *width;
+ priv->cached_sizes[text_len-1].height = *height;
+ }
+ }
+ else
+ {
+ *width = priv->cached_sizes[text_len-1].width;
+ *height = priv->cached_sizes[text_len-1].height;
+ }
+}
+
static void
gtk_source_gutter_renderer_text_begin (GtkSourceGutterRenderer *renderer,
GtkSourceGutterLines *lines)
@@ -62,6 +108,8 @@ gtk_source_gutter_renderer_text_begin (GtkSourceGutterRenderer *renderer,
g_clear_object (&priv->cached_layout);
priv->cached_layout = gtk_widget_create_pango_layout (GTK_WIDGET (renderer), NULL);
+
+ gtk_source_gutter_renderer_text_clear_cached_sizes (text);
}
static void
@@ -73,10 +121,10 @@ gtk_source_gutter_renderer_text_snapshot_line (GtkSourceGutterRenderer *renderer
GtkSourceGutterRendererText *text = GTK_SOURCE_GUTTER_RENDERER_TEXT (renderer);
GtkSourceGutterRendererTextPrivate *priv = gtk_source_gutter_renderer_text_get_instance_private
(text);
PangoLayout *layout;
- gfloat x;
- gfloat y;
- gint width;
- gint height;
+ float x;
+ float y;
+ int width;
+ int height;
if (priv->text == NULL || priv->text_len == 0)
{
@@ -98,14 +146,8 @@ gtk_source_gutter_renderer_text_snapshot_line (GtkSourceGutterRenderer *renderer
priv->text_len);
}
- pango_layout_get_pixel_size (layout, &width, &height);
-
- gtk_source_gutter_renderer_align_cell (renderer,
- line,
- width,
- height,
- &x,
- &y);
+ gtk_source_gutter_renderer_text_get_size (priv, layout, priv->text_len, &width, &height);
+ gtk_source_gutter_renderer_align_cell (renderer, line, width, height, &x, &y);
gtk_snapshot_render_layout (snapshot,
gtk_widget_get_style_context (GTK_WIDGET (text)),
@@ -388,6 +430,8 @@ gtk_source_gutter_renderer_text_init (GtkSourceGutterRendererText *self)
GtkSourceGutterRendererTextPrivate *priv = gtk_source_gutter_renderer_text_get_instance_private
(self);
priv->is_markup = TRUE;
+
+ gtk_source_gutter_renderer_text_clear_cached_sizes (self);
}
/**
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]