From 850b4a03e6e5c0478c3c63559abddd8f714b6ac4 Mon Sep 17 00:00:00 2001 From: Andreas Kling Date: Mon, 16 Jan 2023 09:26:01 +0100 Subject: [PATCH] LibGfx: Cache font pixel metrics in ScaledFont Instead of recomputing the pixel metrics over and over, we can just cache them with the font and avoid a bunch of expensive computation. --- Userland/Libraries/LibGfx/Font/ScaledFont.cpp | 34 +++++++++++++------ Userland/Libraries/LibGfx/Font/ScaledFont.h | 13 ++----- 2 files changed, 26 insertions(+), 21 deletions(-) diff --git a/Userland/Libraries/LibGfx/Font/ScaledFont.cpp b/Userland/Libraries/LibGfx/Font/ScaledFont.cpp index 70437e9040..5e4040c235 100644 --- a/Userland/Libraries/LibGfx/Font/ScaledFont.cpp +++ b/Userland/Libraries/LibGfx/Font/ScaledFont.cpp @@ -10,6 +10,28 @@ namespace Gfx { +ScaledFont::ScaledFont(NonnullRefPtr font, float point_width, float point_height, unsigned dpi_x, unsigned dpi_y) + : m_font(move(font)) + , m_point_width(point_width) + , m_point_height(point_height) +{ + float units_per_em = m_font->units_per_em(); + m_x_scale = (point_width * dpi_x) / (POINTS_PER_INCH * units_per_em); + m_y_scale = (point_height * dpi_y) / (POINTS_PER_INCH * units_per_em); + + auto metrics = m_font->metrics(m_x_scale, m_y_scale); + + m_pixel_metrics = Gfx::FontPixelMetrics { + .size = (float)pixel_size(), + .x_height = (float)x_height(), + .advance_of_ascii_zero = (float)glyph_width('0'), + .glyph_spacing = (float)glyph_spacing(), + .ascent = metrics.ascender, + .descent = metrics.descender, + .line_gap = metrics.line_gap, + }; +} + float ScaledFont::width(StringView view) const { return unicode_view_width(Utf8View(view)); } float ScaledFont::width(Utf8View const& view) const { return unicode_view_width(view); } float ScaledFont::width(Utf32View const& view) const { return unicode_view_width(view); } @@ -103,17 +125,7 @@ u8 ScaledFont::glyph_fixed_width() const Gfx::FontPixelMetrics ScaledFont::pixel_metrics() const { - auto metrics = m_font->metrics(m_x_scale, m_y_scale); - - return Gfx::FontPixelMetrics { - .size = (float)pixel_size(), - .x_height = (float)x_height(), - .advance_of_ascii_zero = (float)glyph_width('0'), - .glyph_spacing = (float)glyph_spacing(), - .ascent = metrics.ascender, - .descent = metrics.descender, - .line_gap = metrics.line_gap, - }; + return m_pixel_metrics; } } diff --git a/Userland/Libraries/LibGfx/Font/ScaledFont.h b/Userland/Libraries/LibGfx/Font/ScaledFont.h index 3cc5705e25..3c47cc498e 100644 --- a/Userland/Libraries/LibGfx/Font/ScaledFont.h +++ b/Userland/Libraries/LibGfx/Font/ScaledFont.h @@ -23,17 +23,9 @@ struct GlyphIndexWithSubpixelOffset { bool operator==(GlyphIndexWithSubpixelOffset const&) const = default; }; -class ScaledFont : public Gfx::Font { +class ScaledFont final : public Gfx::Font { public: - ScaledFont(NonnullRefPtr font, float point_width, float point_height, unsigned dpi_x = DEFAULT_DPI, unsigned dpi_y = DEFAULT_DPI) - : m_font(move(font)) - , m_point_width(point_width) - , m_point_height(point_height) - { - float units_per_em = m_font->units_per_em(); - m_x_scale = (point_width * dpi_x) / (POINTS_PER_INCH * units_per_em); - m_y_scale = (point_height * dpi_y) / (POINTS_PER_INCH * units_per_em); - } + ScaledFont(NonnullRefPtr, float point_width, float point_height, unsigned dpi_x = DEFAULT_DPI, unsigned dpi_y = DEFAULT_DPI); u32 glyph_id_for_code_point(u32 code_point) const { return m_font->glyph_id_for_code_point(code_point); } ScaledFontMetrics metrics() const { return m_font->metrics(m_x_scale, m_y_scale); } ScaledGlyphMetrics glyph_metrics(u32 glyph_id) const { return m_font->glyph_metrics(glyph_id, m_x_scale, m_y_scale); } @@ -81,6 +73,7 @@ private: float m_point_width { 0.0f }; float m_point_height { 0.0f }; mutable HashMap> m_cached_glyph_bitmaps; + Gfx::FontPixelMetrics m_pixel_metrics; template float unicode_view_width(T const& view) const;