diff options
author | Phil Jones <philj56@gmail.com> | 2022-06-10 00:24:54 +0100 |
---|---|---|
committer | Phil Jones <philj56@gmail.com> | 2022-06-10 00:24:54 +0100 |
commit | 72d98fd99f350d2592c63ee6e1ac28cd38fbcb93 (patch) | |
tree | 106873ab06b2dff56563e2b77a24d437b7db6ff1 /src/entry_backend | |
parent | 34037743f70c6c5e2b8f916d992e70d42ca07b9b (diff) |
Avoid an unnecessary copy of the image buffer.
By pointing Cairo at the mmap-ed file used to create wl_shm buffers, we
can eliminate a memcpy() on every draw, providing a decent speedup
(especially for large window sizes).
This comes at the expense of having to keep track of two Cairo contexts,
one for each of our two buffers used for double buffering. Additionally,
a single memcpy() is still required for initialisation of the second
buffer, so the startup latency isn't affected much.
Diffstat (limited to 'src/entry_backend')
-rw-r--r-- | src/entry_backend/harfbuzz.c | 35 | ||||
-rw-r--r-- | src/entry_backend/harfbuzz.h | 2 | ||||
-rw-r--r-- | src/entry_backend/pango.c | 10 | ||||
-rw-r--r-- | src/entry_backend/pango.h | 2 |
4 files changed, 30 insertions, 19 deletions
diff --git a/src/entry_backend/harfbuzz.c b/src/entry_backend/harfbuzz.c index d1f54e9..779cbd8 100644 --- a/src/entry_backend/harfbuzz.c +++ b/src/entry_backend/harfbuzz.c @@ -1,4 +1,3 @@ -#include <assert.h> #include <cairo/cairo.h> #include <glib.h> #include <harfbuzz/hb-ft.h> @@ -12,6 +11,12 @@ #include "../nelem.h" #include "../xmalloc.h" +/* + * Cairo / FreeType use 72 Pts per inch, but Pango uses 96 DPI, so we have to + * rescale for consistency. + */ +#define PT_TO_DPI (96.0 / 72.0) + static void setup_hb_buffer(hb_buffer_t *buffer) { hb_buffer_set_direction(buffer, HB_DIRECTION_LTR); @@ -69,17 +74,22 @@ static uint32_t render_hb_buffer(cairo_t *cr, hb_buffer_t *buffer, uint32_t scal return width; } -void entry_backend_init(struct entry *entry, uint32_t width, uint32_t height, uint32_t scale) +void entry_backend_init(struct entry *entry, uint32_t *width, uint32_t *height, uint32_t scale) { - cairo_t *cr = entry->cairo.cr; + cairo_t *cr = entry->cairo[0].cr; /* Setup FreeType. */ log_debug("Creating FreeType library.\n"); - assert(!FT_Init_FreeType(&entry->backend.ft_library)); + FT_Init_FreeType(&entry->backend.ft_library); log_debug("Loading FreeType font.\n"); - assert(!FT_New_Face(entry->backend.ft_library, "font.ttf", 0, &entry->backend.ft_face)); - assert(!FT_Set_Char_Size(entry->backend.ft_face, entry->font_size * 64, entry->font_size * 64, 0, 0)); + FT_New_Face(entry->backend.ft_library, "font.ttf", 0, &entry->backend.ft_face); + FT_Set_Char_Size( + entry->backend.ft_face, + entry->font_size * 64 * scale * PT_TO_DPI, + entry->font_size * 64 * scale * PT_TO_DPI, + 0, + 0); log_debug("Creating Cairo font.\n"); entry->backend.cairo_face = cairo_ft_font_face_create_for_ft_face(entry->backend.ft_face, 0); @@ -87,10 +97,11 @@ void entry_backend_init(struct entry *entry, uint32_t width, uint32_t height, ui struct color color = entry->foreground_color; cairo_set_source_rgba(cr, color.r, color.g, color.b, color.a); cairo_set_font_face(cr, entry->backend.cairo_face); - cairo_set_font_size(cr, entry->font_size * (96.0 / 72.0)); + cairo_set_font_size(cr, entry->font_size * PT_TO_DPI); - cairo_font_extents_t font_extents; - cairo_font_extents(cr, &font_extents); + /* We also need to set up the font for our other Cairo context. */ + cairo_set_font_face(entry->cairo[1].cr, entry->backend.cairo_face); + cairo_set_font_size(entry->cairo[1].cr, entry->font_size * PT_TO_DPI); log_debug("Creating Harfbuzz font.\n"); entry->backend.hb_font = hb_ft_font_create_referenced(entry->backend.ft_face); @@ -106,8 +117,8 @@ void entry_backend_init(struct entry *entry, uint32_t width, uint32_t height, ui /* Move and clip so we don't draw over the prompt */ uint32_t prompt_width = render_hb_buffer(cr, entry->backend.hb_buffer, scale); cairo_translate(cr, prompt_width, 0); - width -= prompt_width; - cairo_rectangle(cr, 0, 0, width, height); + *width -= prompt_width; + cairo_rectangle(cr, 0, 0, *width, *height); cairo_clip(cr); } @@ -121,7 +132,7 @@ void entry_backend_destroy(struct entry *entry) void entry_backend_update(struct entry *entry) { - cairo_t *cr = entry->cairo.cr; + cairo_t *cr = entry->cairo[entry->index].cr; hb_buffer_clear_contents(entry->backend.hb_buffer); setup_hb_buffer(entry->backend.hb_buffer); diff --git a/src/entry_backend/harfbuzz.h b/src/entry_backend/harfbuzz.h index 0b07538..52116a8 100644 --- a/src/entry_backend/harfbuzz.h +++ b/src/entry_backend/harfbuzz.h @@ -19,7 +19,7 @@ struct entry_backend { hb_buffer_t *hb_buffer; }; -void entry_backend_init(struct entry *entry, uint32_t width, uint32_t height, uint32_t scale); +void entry_backend_init(struct entry *entry, uint32_t *width, uint32_t *height, uint32_t scale); void entry_backend_destroy(struct entry *entry); void entry_backend_update(struct entry *entry); diff --git a/src/entry_backend/pango.c b/src/entry_backend/pango.c index 569a706..4d43ce3 100644 --- a/src/entry_backend/pango.c +++ b/src/entry_backend/pango.c @@ -7,9 +7,9 @@ #include "../log.h" #include "../nelem.h" -void entry_backend_init(struct entry *entry, uint32_t width, uint32_t height, uint32_t scale) +void entry_backend_init(struct entry *entry, uint32_t *width, uint32_t *height, uint32_t scale) { - cairo_t *cr = entry->cairo.cr; + cairo_t *cr = entry->cairo[0].cr; /* Setup Pango. */ log_debug("Creating Pango context.\n"); @@ -41,8 +41,8 @@ void entry_backend_init(struct entry *entry, uint32_t width, uint32_t height, ui /* Move and clip so we don't draw over the prompt */ cairo_translate(cr, prompt_width, 0); - width -= prompt_width; - cairo_rectangle(cr, 0, 0, width, height); + *width -= prompt_width; + cairo_rectangle(cr, 0, 0, *width, *height); cairo_clip(cr); log_debug("Creating Pango layout.\n"); @@ -70,7 +70,7 @@ void entry_backend_destroy(struct entry *entry) void entry_backend_update(struct entry *entry) { - cairo_t *cr = entry->cairo.cr; + cairo_t *cr = entry->cairo[entry->index].cr; pango_layout_set_text(entry->backend.entry_layout, entry->input_mb, -1); pango_cairo_update_layout(cr, entry->backend.entry_layout); diff --git a/src/entry_backend/pango.h b/src/entry_backend/pango.h index 08572ae..ef58be3 100644 --- a/src/entry_backend/pango.h +++ b/src/entry_backend/pango.h @@ -12,7 +12,7 @@ struct entry_backend { PangoLayout *result_layouts[5]; }; -void entry_backend_init(struct entry *entry, uint32_t width, uint32_t height, uint32_t scale); +void entry_backend_init(struct entry *entry, uint32_t *width, uint32_t *height, uint32_t scale); void entry_backend_destroy(struct entry *entry); void entry_backend_update(struct entry *entry); |