Bumping manifests a=b2g-bump
[gecko.git] / gfx / cairo / unicode-printing.patch
blob09b3991ea011eff2de1e073567d705321000a74e
1 diff --git a/gfx/cairo/cairo/src/cairo-win32-printing-surface.c b/gfx/cairo/cairo/src/cairo-win32-printing-surface.c
2 --- a/gfx/cairo/cairo/src/cairo-win32-printing-surface.c
3 +++ b/gfx/cairo/cairo/src/cairo-win32-printing-surface.c
4 @@ -1426,16 +1426,104 @@ _cairo_win32_printing_surface_fill (void
7 fflush(stderr);
9 return status;
12 static cairo_int_status_t
13 +_cairo_win32_printing_surface_emit_win32_glyphs (cairo_win32_surface_t *surface,
14 + cairo_operator_t op,
15 + const cairo_pattern_t *source,
16 + cairo_glyph_t *glyphs,
17 + int num_glyphs,
18 + cairo_scaled_font_t *scaled_font,
19 + cairo_clip_t *clip,
20 + int *remaining_glyphs)
22 + cairo_matrix_t ctm;
23 + cairo_glyph_t *unicode_glyphs;
24 + cairo_scaled_font_subsets_glyph_t subset_glyph;
25 + int i, first;
26 + cairo_bool_t sequence_is_unicode;
27 + cairo_status_t status = CAIRO_STATUS_SUCCESS;
29 + /* Where possible reverse the glyph indices back to unicode
30 + * characters. Strings of glyphs that could not be reversed to
31 + * unicode will be printed with ETO_GLYPH_INDEX.
32 + *
33 + * As _cairo_win32_scaled_font_index_to_ucs4() is a slow
34 + * operation, the font subsetting function
35 + * _cairo_scaled_font_subsets_map_glyph() is used to obtain
36 + * the unicode value because it caches the reverse mapping in
37 + * the subsets.
38 + */
40 + if (surface->has_ctm) {
41 + for (i = 0; i < num_glyphs; i++)
42 + cairo_matrix_transform_point (&surface->ctm, &glyphs[i].x, &glyphs[i].y);
43 + cairo_matrix_multiply (&ctm, &scaled_font->ctm, &surface->ctm);
44 + scaled_font = cairo_scaled_font_create (scaled_font->font_face,
45 + &scaled_font->font_matrix,
46 + &ctm,
47 + &scaled_font->options);
48 + }
50 + unicode_glyphs = _cairo_malloc_ab (num_glyphs, sizeof (cairo_glyph_t));
51 + if (unicode_glyphs == NULL)
52 + return _cairo_error (CAIRO_STATUS_NO_MEMORY);
54 + memcpy (unicode_glyphs, glyphs, num_glyphs * sizeof (cairo_glyph_t));
55 + for (i = 0; i < num_glyphs; i++) {
56 + status = _cairo_scaled_font_subsets_map_glyph (surface->font_subsets,
57 + scaled_font,
58 + glyphs[i].index,
59 + NULL, 0,
60 + &subset_glyph);
61 + if (status)
62 + goto fail;
64 + unicode_glyphs[i].index = subset_glyph.unicode;
65 + }
67 + i = 0;
68 + first = 0;
69 + sequence_is_unicode = unicode_glyphs[0].index <= 0xffff;
70 + while (i < num_glyphs) {
71 + if (i == num_glyphs - 1 ||
72 + ((unicode_glyphs[i + 1].index < 0xffff) != sequence_is_unicode))
73 + {
74 + status = _cairo_win32_surface_show_glyphs_internal (
75 + surface,
76 + op,
77 + source,
78 + sequence_is_unicode ? &unicode_glyphs[first] : &glyphs[first],
79 + i - first + 1,
80 + scaled_font,
81 + clip,
82 + remaining_glyphs,
83 + ! sequence_is_unicode);
84 + first = i + 1;
85 + if (i < num_glyphs - 1)
86 + sequence_is_unicode = unicode_glyphs[i + 1].index <= 0xffff;
87 + }
88 + i++;
89 + }
91 +fail:
92 + if (surface->has_ctm)
93 + cairo_scaled_font_destroy (scaled_font);
95 + free (unicode_glyphs);
97 + return status;
100 +static cairo_int_status_t
101 _cairo_win32_printing_surface_show_glyphs (void *abstract_surface,
102 cairo_operator_t op,
103 const cairo_pattern_t *source,
104 cairo_glyph_t *glyphs,
105 int num_glyphs,
106 cairo_scaled_font_t *scaled_font,
107 cairo_clip_t *clip,
108 int *remaining_glyphs)
109 @@ -1533,77 +1621,24 @@ _cairo_win32_printing_surface_show_glyph
112 #endif
114 #if CAIRO_HAS_WIN32_FONT
115 if (cairo_scaled_font_get_type (scaled_font) == CAIRO_FONT_TYPE_WIN32 &&
116 source->type == CAIRO_PATTERN_TYPE_SOLID)
118 - cairo_matrix_t ctm;
119 - cairo_glyph_t *type1_glyphs = NULL;
120 - cairo_scaled_font_subsets_glyph_t subset_glyph;
122 - /* Calling ExtTextOutW() with ETO_GLYPH_INDEX and a Type 1
123 - * font on a printer DC prints garbled text. The text displays
124 - * correctly on a display DC. When using a printer
125 - * DC, ExtTextOutW() only works with characters and not glyph
126 - * indices.
128 - * For Type 1 fonts the glyph indices are converted back to
129 - * unicode characters before calling _cairo_win32_surface_show_glyphs().
131 - * As _cairo_win32_scaled_font_index_to_ucs4() is a slow
132 - * operation, the font subsetting function
133 - * _cairo_scaled_font_subsets_map_glyph() is used to obtain
134 - * the unicode value because it caches the reverse mapping in
135 - * the subsets.
136 - */
137 - if (_cairo_win32_scaled_font_is_type1 (scaled_font)) {
138 - type1_glyphs = _cairo_malloc_ab (num_glyphs, sizeof (cairo_glyph_t));
139 - if (type1_glyphs == NULL) {
140 - status = _cairo_error (CAIRO_STATUS_NO_MEMORY);
141 - goto FINISH;
143 - memcpy (type1_glyphs, glyphs, num_glyphs * sizeof (cairo_glyph_t));
144 - for (i = 0; i < num_glyphs; i++) {
145 - status = _cairo_scaled_font_subsets_map_glyph (surface->font_subsets,
146 - scaled_font,
147 - type1_glyphs[i].index,
148 - NULL, 0,
149 - &subset_glyph);
150 - if (status)
151 - goto FINISH;
153 - type1_glyphs[i].index = subset_glyph.unicode;
155 - glyphs = type1_glyphs;
158 - if (surface->has_ctm || surface->has_gdi_ctm) {
159 - cairo_matrix_multiply (&ctm, &surface->ctm, &surface->gdi_ctm);
160 - for (i = 0; i < num_glyphs; i++)
161 - cairo_matrix_transform_point (&ctm, &glyphs[i].x, &glyphs[i].y);
162 - cairo_matrix_multiply (&ctm, &scaled_font->ctm, &ctm);
163 - scaled_font = cairo_scaled_font_create (scaled_font->font_face,
164 - &scaled_font->font_matrix,
165 - &ctm,
166 - &scaled_font->options);
168 - status = _cairo_win32_surface_show_glyphs (surface, op,
169 - source, glyphs,
170 - num_glyphs, scaled_font,
171 - clip,
172 - remaining_glyphs);
173 - if (surface->has_ctm || surface->has_gdi_ctm)
174 - cairo_scaled_font_destroy (scaled_font);
176 - if (type1_glyphs != NULL)
177 - free (type1_glyphs);
179 + status = _cairo_win32_printing_surface_emit_win32_glyphs (surface,
180 + op,
181 + source,
182 + glyphs,
183 + num_glyphs,
184 + scaled_font,
185 + clip,
186 + remaining_glyphs);
187 goto FINISH;
189 #endif
191 SaveDC (surface->dc);
192 old_ctm = surface->ctm;
193 old_has_ctm = surface->has_ctm;
194 surface->has_ctm = TRUE;
195 diff --git a/gfx/cairo/cairo/src/cairo-win32-private.h b/gfx/cairo/cairo/src/cairo-win32-private.h
196 --- a/gfx/cairo/cairo/src/cairo-win32-private.h
197 +++ b/gfx/cairo/cairo/src/cairo-win32-private.h
198 @@ -157,16 +157,27 @@ _cairo_win32_surface_get_extents (void
199 uint32_t
200 _cairo_win32_flags_for_dc (HDC dc);
202 cairo_status_t
203 _cairo_win32_surface_set_clip_region (void *abstract_surface,
204 cairo_region_t *region);
206 cairo_int_status_t
207 +_cairo_win32_surface_show_glyphs_internal (void *surface,
208 + cairo_operator_t op,
209 + const cairo_pattern_t *source,
210 + cairo_glyph_t *glyphs,
211 + int num_glyphs,
212 + cairo_scaled_font_t *scaled_font,
213 + cairo_clip_t *clip,
214 + int *remaining_glyphs,
215 + cairo_bool_t glyph_indices);
217 +cairo_int_status_t
218 _cairo_win32_surface_show_glyphs (void *surface,
219 cairo_operator_t op,
220 const cairo_pattern_t *source,
221 cairo_glyph_t *glyphs,
222 int num_glyphs,
223 cairo_scaled_font_t *scaled_font,
224 cairo_clip_t *clip,
225 int *remaining_glyphs);
226 diff --git a/gfx/cairo/cairo/src/cairo-win32-surface.c b/gfx/cairo/cairo/src/cairo-win32-surface.c
227 --- a/gfx/cairo/cairo/src/cairo-win32-surface.c
228 +++ b/gfx/cairo/cairo/src/cairo-win32-surface.c
229 @@ -1607,24 +1607,25 @@ static cairo_status_t
230 _cairo_win32_surface_flush (void *abstract_surface)
232 return _cairo_win32_surface_set_clip_region (abstract_surface, NULL);
235 #define STACK_GLYPH_SIZE 256
237 cairo_int_status_t
238 -_cairo_win32_surface_show_glyphs (void *surface,
239 - cairo_operator_t op,
240 - const cairo_pattern_t *source,
241 - cairo_glyph_t *glyphs,
242 - int num_glyphs,
243 - cairo_scaled_font_t *scaled_font,
244 - cairo_clip_t *clip,
245 - int *remaining_glyphs)
246 +_cairo_win32_surface_show_glyphs_internal (void *surface,
247 + cairo_operator_t op,
248 + const cairo_pattern_t *source,
249 + cairo_glyph_t *glyphs,
250 + int num_glyphs,
251 + cairo_scaled_font_t *scaled_font,
252 + cairo_clip_t *clip,
253 + int *remaining_glyphs,
254 + cairo_bool_t glyph_indexing)
256 #ifdef CAIRO_HAS_WIN32_FONT
257 if (scaled_font->backend->type == CAIRO_FONT_TYPE_DWRITE) {
258 #ifdef CAIRO_HAS_DWRITE_FONT
259 return _cairo_dwrite_show_glyphs_on_surface(surface, op, source, glyphs, num_glyphs, scaled_font, clip);
260 #endif
261 } else {
262 cairo_win32_surface_t *dst = surface;
263 @@ -1737,29 +1738,20 @@ _cairo_win32_surface_show_glyphs (void
264 dxy_buf[j+1] = _cairo_lround (logical_y - next_logical_y);
265 /* note that GDI coordinate system is inverted */
267 logical_x = next_logical_x;
268 logical_y = next_logical_y;
272 - /* Using glyph indices for a Type 1 font does not work on a
273 - * printer DC. The win32 printing surface will convert the the
274 - * glyph indices of Type 1 fonts to the unicode values.
275 - */
276 - if ((dst->flags & CAIRO_WIN32_SURFACE_FOR_PRINTING) &&
277 - _cairo_win32_scaled_font_is_type1 (scaled_font))
279 + if (glyph_indexing)
280 + glyph_index_option = ETO_GLYPH_INDEX;
281 + else
282 glyph_index_option = 0;
284 - else
286 - glyph_index_option = ETO_GLYPH_INDEX;
289 win_result = ExtTextOutW(dst->dc,
290 start_x,
291 start_y,
292 glyph_index_option | ETO_PDY,
293 NULL,
294 glyph_buf,
295 num_glyphs,
296 @@ -1778,16 +1770,37 @@ _cairo_win32_surface_show_glyphs (void
298 #else
299 return CAIRO_INT_STATUS_UNSUPPORTED;
300 #endif
303 #undef STACK_GLYPH_SIZE
305 +cairo_int_status_t
306 +_cairo_win32_surface_show_glyphs (void *surface,
307 + cairo_operator_t op,
308 + const cairo_pattern_t *source,
309 + cairo_glyph_t *glyphs,
310 + int num_glyphs,
311 + cairo_scaled_font_t *scaled_font,
312 + cairo_clip_t *clip,
313 + int *remaining_glyphs)
315 + return _cairo_win32_surface_show_glyphs_internal (surface,
316 + op,
317 + source,
318 + glyphs,
319 + num_glyphs,
320 + scaled_font,
321 + clip,
322 + remaining_glyphs,
323 + TRUE);
326 static cairo_surface_t *
327 cairo_win32_surface_create_internal (HDC hdc, cairo_format_t format)
329 cairo_win32_surface_t *surface;
331 RECT rect;
333 surface = malloc (sizeof (cairo_win32_surface_t));