[PATCH 2/4] dwrite: Use correct glyph origins during rendering.

Nikolay Sivov nsivov at codeweavers.com
Mon Feb 22 12:29:36 CST 2021


Signed-off-by: Nikolay Sivov <nsivov at codeweavers.com>
---
 dlls/dwrite/dwrite_private.h |  2 ++
 dlls/dwrite/font.c           | 57 ++++--------------------------------
 dlls/dwrite/freetype.c       | 36 +++++++++++++----------
 dlls/dwrite/main.c           |  2 +-
 4 files changed, 29 insertions(+), 68 deletions(-)

diff --git a/dlls/dwrite/dwrite_private.h b/dlls/dwrite/dwrite_private.h
index 830c71f0abf..13bef3ad36b 100644
--- a/dlls/dwrite/dwrite_private.h
+++ b/dlls/dwrite/dwrite_private.h
@@ -347,6 +347,8 @@ extern HRESULT create_inmemory_fileloader(IDWriteInMemoryFontFileLoader **loader
 extern HRESULT create_font_resource(IDWriteFactory7 *factory, IDWriteFontFile *file, UINT32 face_index,
         IDWriteFontResource **resource) DECLSPEC_HIDDEN;
 extern HRESULT create_fontset_builder(IDWriteFactory7 *factory, IDWriteFontSetBuilder2 **ret) DECLSPEC_HIDDEN;
+extern HRESULT compute_glyph_origins(DWRITE_GLYPH_RUN const *run, DWRITE_MEASURING_MODE measuring_mode,
+        D2D1_POINT_2F baseline_origin, DWRITE_MATRIX const *transform, D2D1_POINT_2F *origins) DECLSPEC_HIDDEN;
 
 struct dwrite_fontface;
 
diff --git a/dlls/dwrite/font.c b/dlls/dwrite/font.c
index e22e4abf271..ac8f5c0a7bb 100644
--- a/dlls/dwrite/font.c
+++ b/dlls/dwrite/font.c
@@ -5918,10 +5918,7 @@ float fontface_get_scaled_design_advance(struct dwrite_fontface *fontface, DWRIT
 HRESULT create_glyphrunanalysis(const struct glyphrunanalysis_desc *desc, IDWriteGlyphRunAnalysis **ret)
 {
     struct dwrite_glyphrunanalysis *analysis;
-    struct dwrite_fontface *fontface;
-    D2D_POINT_2F origin;
-    FLOAT rtl_factor;
-    UINT32 i;
+    unsigned int i;
 
     *ret = NULL;
 
@@ -5977,57 +5974,13 @@ HRESULT create_glyphrunanalysis(const struct glyphrunanalysis_desc *desc, IDWrit
     }
 
     analysis->run.glyphIndices = analysis->glyphs;
-
-    rtl_factor = desc->run->bidiLevel & 1 ? -1.0f : 1.0f;
-
     memcpy(analysis->glyphs, desc->run->glyphIndices, desc->run->glyphCount*sizeof(*desc->run->glyphIndices));
 
-    fontface = unsafe_impl_from_IDWriteFontFace(desc->run->fontFace);
-
-    origin.x = desc->origin.x;
-    origin.y = desc->origin.y;
-    for (i = 0; i < desc->run->glyphCount; ++i)
+    compute_glyph_origins(desc->run, desc->measuring_mode, desc->origin, desc->transform, analysis->origins);
+    if (analysis->flags & RUNANALYSIS_USE_TRANSFORM)
     {
-        float advance;
-
-        /* Use nominal advances if not provided by caller. */
-        if (desc->run->glyphAdvances)
-            advance = rtl_factor * desc->run->glyphAdvances[i];
-        else
-            advance = rtl_factor * fontface_get_scaled_design_advance(fontface, desc->measuring_mode,
-                    desc->run->fontEmSize, 1.0f, desc->transform, desc->run->glyphIndices[i], desc->run->isSideways);
-
-        analysis->origins[i] = origin;
-        if (desc->run->bidiLevel & 1)
-        {
-            if (desc->run->isSideways)
-                analysis->origins[i].y += advance;
-            else
-                analysis->origins[i].x += advance;
-        }
-
-        /* Offsets are optional, appled to pre-transformed origin. */
-        if (desc->run->glyphOffsets) {
-            FLOAT advanceoffset = rtl_factor * desc->run->glyphOffsets[i].advanceOffset;
-            FLOAT ascenderoffset = -desc->run->glyphOffsets[i].ascenderOffset;
-
-            if (desc->run->isSideways) {
-                analysis->origins[i].x += ascenderoffset;
-                analysis->origins[i].y += advanceoffset;
-            }
-            else {
-                analysis->origins[i].x += advanceoffset;
-                analysis->origins[i].y += ascenderoffset;
-            }
-        }
-
-        if (analysis->flags & RUNANALYSIS_USE_TRANSFORM)
-            transform_point(analysis->origins + i, &analysis->m);
-
-        if (desc->run->isSideways)
-            origin.y += advance;
-        else
-            origin.x += advance;
+        for (i = 0; i < desc->run->glyphCount; ++i)
+            transform_point(&analysis->origins[i], &analysis->m);
     }
 
     *ret = &analysis->IDWriteGlyphRunAnalysis_iface;
diff --git a/dlls/dwrite/freetype.c b/dlls/dwrite/freetype.c
index 91e44d82f2b..32fa4cc97c3 100644
--- a/dlls/dwrite/freetype.c
+++ b/dlls/dwrite/freetype.c
@@ -488,8 +488,8 @@ HRESULT freetype_get_glyphrun_outline(IDWriteFontFace5 *fontface, float emSize,
     scaler.y_res = 0;
 
     EnterCriticalSection(&freetype_cs);
-    if (pFTC_Manager_LookupSize(cache_manager, &scaler, &size) == 0) {
-        float rtl_factor = is_rtl ? -1.0f : 1.0f;
+    if (pFTC_Manager_LookupSize(cache_manager, &scaler, &size) == 0)
+    {
         D2D1_POINT_2F origin;
         unsigned int i;
 
@@ -501,7 +501,6 @@ HRESULT freetype_get_glyphrun_outline(IDWriteFontFace5 *fontface, float emSize,
                 FLOAT ft_advance = size->face->glyph->metrics.horiAdvance >> 6;
                 FT_Outline *outline = &size->face->glyph->outline;
                 D2D1_POINT_2F glyph_origin;
-                float advance;
                 FT_Matrix m;
 
                 if (simulations & DWRITE_FONT_SIMULATIONS_BOLD)
@@ -514,25 +513,32 @@ HRESULT freetype_get_glyphrun_outline(IDWriteFontFace5 *fontface, float emSize,
 
                 pFT_Outline_Transform(outline, &m);
 
-                if (advances)
-                    advance = rtl_factor * advances[i];
-                else
-                    advance = rtl_factor * ft_advance;
-
                 glyph_origin = origin;
+
                 if (is_rtl)
-                    glyph_origin.x += advance;
+                {
+                    glyph_origin.x -= ft_advance;
 
-                /* glyph offsets act as current glyph adjustment */
-                if (offsets)
+                    if (offsets)
+                    {
+                        glyph_origin.x -= offsets[i].advanceOffset;
+                        glyph_origin.y -= offsets[i].ascenderOffset;
+                    }
+
+                    origin.x -= advances ? advances[i] : ft_advance;
+                }
+                else
                 {
-                    glyph_origin.x += rtl_factor * offsets[i].advanceOffset;
-                    glyph_origin.y -= offsets[i].ascenderOffset;
+                    if (offsets)
+                    {
+                        glyph_origin.x += offsets[i].advanceOffset;
+                        glyph_origin.y -= offsets[i].ascenderOffset;
+                    }
+
+                    origin.x += advances ? advances[i] : ft_advance;
                 }
 
                 decompose_outline(outline, glyph_origin, sink);
-
-                origin.x += advance;
             }
         }
     }
diff --git a/dlls/dwrite/main.c b/dlls/dwrite/main.c
index 3b0505231bf..560661983d0 100644
--- a/dlls/dwrite/main.c
+++ b/dlls/dwrite/main.c
@@ -1550,7 +1550,7 @@ static HRESULT WINAPI dwritefactory4_TranslateColorGlyphRun(IDWriteFactory7 *ifa
     return E_NOTIMPL;
 }
 
-static HRESULT compute_glyph_origins(DWRITE_GLYPH_RUN const *run, DWRITE_MEASURING_MODE measuring_mode,
+HRESULT compute_glyph_origins(DWRITE_GLYPH_RUN const *run, DWRITE_MEASURING_MODE measuring_mode,
     D2D1_POINT_2F baseline_origin, DWRITE_MATRIX const *transform, D2D1_POINT_2F *origins)
 {
     struct dwrite_fontface *font_obj;
-- 
2.30.0




More information about the wine-devel mailing list