summaryrefslogtreecommitdiff
path: root/external/harfbuzz/0001-graphite-Fix-shaping-with-varying-font-size.patch
blob: f9e6afc1a37bb1bd1ffb1e18317e100f8da01849 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
From 82f7be388090f19333876877366907fec09f0312 Mon Sep 17 00:00:00 2001
From: Khaled Hosny <khaledhosny@eglug.org>
Date: Sun, 30 Oct 2016 20:16:41 +0200
Subject: [PATCH] [graphite] Fix shaping with varying font size

See https://bugs.documentfoundation.org/show_bug.cgi?id=103403#c7
---
 src/hb-graphite2.cc | 40 ++++++++++++++++++++++++++++------------
 1 file changed, 28 insertions(+), 12 deletions(-)

diff --git a/src/hb-graphite2.cc b/src/hb-graphite2.cc
index c32318d..138a5ae 100644
--- src/hb-graphite2.cc
+++ src/hb-graphite2.cc
@@ -27,7 +27,6 @@
  */
 
 #define HB_SHAPER graphite2
-#define hb_graphite2_shaper_font_data_t gr_font
 #include "hb-shaper-impl-private.hh"
 
 #include "hb-graphite2.h"
@@ -55,6 +54,12 @@ struct hb_graphite2_shaper_face_data_t {
   hb_graphite2_tablelist_t *tlist;
 };
 
+struct hb_graphite2_shaper_font_data_t {
+  gr_font   *grfont;
+  int        xscale;
+  int        yscale;
+};
+
 static const void *hb_graphite2_get_table (const void *data, unsigned int tag, size_t *len)
 {
   hb_graphite2_shaper_face_data_t *face_data = (hb_graphite2_shaper_face_data_t *) data;
@@ -166,13 +171,20 @@ _hb_graphite2_shaper_font_data_create (hb_font_t *font)
   hb_face_t *face = font->face;
   hb_graphite2_shaper_face_data_t *face_data = HB_SHAPER_DATA_GET (face);
 
-  return gr_make_font_with_advance_fn (font->x_scale, font, &hb_graphite2_get_advance, face_data->grface);
+  hb_graphite2_shaper_font_data_t *data = (hb_graphite2_shaper_font_data_t *) calloc (1, sizeof (hb_graphite2_shaper_font_data_t));
+  data->grfont = gr_make_font_with_advance_fn (font->x_scale, font, &hb_graphite2_get_advance, face_data->grface);
+  data->xscale = font->x_scale;
+  data->yscale = font->y_scale;
+
+  return data;
 }
 
 void
 _hb_graphite2_shaper_font_data_destroy (hb_graphite2_shaper_font_data_t *data)
 {
-  gr_font_destroy (data);
+  gr_font_destroy (data->grfont);
+
+  free (data);
 }
 
 /*
@@ -182,7 +194,7 @@ gr_font *
 hb_graphite2_font_get_gr_font (hb_font_t *font)
 {
   if (unlikely (!hb_graphite2_shaper_font_data_ensure (font))) return NULL;
-  return HB_SHAPER_DATA_GET (font);
+  return HB_SHAPER_DATA_GET (font)->grfont;
 }
 
 
@@ -228,7 +240,7 @@ _hb_graphite2_shape (hb_shape_plan_t    *shape_plan,
 {
   hb_face_t *face = font->face;
   gr_face *grface = HB_SHAPER_DATA_GET (face)->grface;
-  gr_font *grfont = HB_SHAPER_DATA_GET (font);
+  gr_font *grfont = HB_SHAPER_DATA_GET (font)->grfont;
 
   const char *lang = hb_language_to_string (hb_buffer_get_language (buffer));
   const char *lang_end = lang ? strchr (lang, '-') : NULL;
@@ -371,7 +383,11 @@ _hb_graphite2_shape (hb_shape_plan_t    *shape_plan,
   }
   buffer->len = glyph_count;
 
-  float yscale = font->y_scale / font->x_scale;
+  hb_graphite2_shaper_font_data_t* font_data = HB_SHAPER_DATA_GET (font);
+
+  float xscale = (float) font->x_scale / (float) font_data->xscale;
+  float yscale = (float) font->y_scale / (float) font_data->yscale;
+  yscale *= yscale / xscale;
   /* Positioning. */
   if (!HB_DIRECTION_IS_BACKWARD(buffer->props.direction))
   {
@@ -381,10 +397,10 @@ _hb_graphite2_shape (hb_shape_plan_t    *shape_plan,
     curradvx = 0;
     for (is = gr_seg_first_slot (seg); is; pPos++, ++info, is = gr_slot_next_in_segment (is))
     {
-      pPos->x_offset = gr_slot_origin_X (is) - curradvx;
+      pPos->x_offset = gr_slot_origin_X (is) * xscale - curradvx;
       pPos->y_offset = gr_slot_origin_Y (is) * yscale - curradvy;
       if (info->cluster != currclus) {
-        pPos->x_advance = info->var1.i32;
+        pPos->x_advance = info->var1.i32 * xscale;
         curradvx += pPos->x_advance;
         currclus = info->cluster;
       } else
@@ -399,20 +415,20 @@ _hb_graphite2_shape (hb_shape_plan_t    *shape_plan,
     int currclus = -1;
     const hb_glyph_info_t *info = buffer->info;
     hb_glyph_position_t *pPos = hb_buffer_get_glyph_positions (buffer, NULL);
-    curradvx = gr_seg_advance_X(seg);
+    curradvx = gr_seg_advance_X(seg) * xscale;
     for (is = gr_seg_first_slot (seg); is; pPos++, info++, is = gr_slot_next_in_segment (is))
     {
       if (info->cluster != currclus)
       {
-        pPos->x_advance = info->var1.i32;
-        if (currclus != -1) curradvx -= info[-1].var1.i32;
+        pPos->x_advance = info->var1.i32 * xscale;
+        if (currclus != -1) curradvx -= info[-1].var1.i32 * xscale;
         currclus = info->cluster;
       } else
       pPos->x_advance = 0.;
 
       pPos->y_advance = gr_slot_advance_Y (is, grface, grfont) * yscale;
       curradvy -= pPos->y_advance;
-      pPos->x_offset = gr_slot_origin_X (is) - curradvx + pPos->x_advance;
+      pPos->x_offset = gr_slot_origin_X (is) * xscale - curradvx + pPos->x_advance;
       pPos->y_offset = gr_slot_origin_Y (is) * yscale - curradvy;
     }
     hb_buffer_reverse_clusters (buffer);
-- 
2.10.1