| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright © 2011,2012 Google, Inc. | 2 * Copyright © 2011,2012 Google, Inc. |
| 3 * | 3 * |
| 4 * This is part of HarfBuzz, a text shaping library. | 4 * This is part of HarfBuzz, a text shaping library. |
| 5 * | 5 * |
| 6 * Permission is hereby granted, without written agreement and without | 6 * Permission is hereby granted, without written agreement and without |
| 7 * license or royalty fees, to use, copy, modify, and distribute this | 7 * license or royalty fees, to use, copy, modify, and distribute this |
| 8 * software and its documentation for any purpose, provided that the | 8 * software and its documentation for any purpose, provided that the |
| 9 * above copyright notice and the following two paragraphs appear in | 9 * above copyright notice and the following two paragraphs appear in |
| 10 * all copies of this software. | 10 * all copies of this software. |
| (...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 84 hb_codepoint_t a, | 84 hb_codepoint_t a, |
| 85 hb_codepoint_t b, | 85 hb_codepoint_t b, |
| 86 hb_codepoint_t *ab) | 86 hb_codepoint_t *ab) |
| 87 { | 87 { |
| 88 return (bool) c->unicode->compose (a, b, ab); | 88 return (bool) c->unicode->compose (a, b, ab); |
| 89 } | 89 } |
| 90 | 90 |
| 91 static inline void | 91 static inline void |
| 92 set_glyph (hb_glyph_info_t &info, hb_font_t *font) | 92 set_glyph (hb_glyph_info_t &info, hb_font_t *font) |
| 93 { | 93 { |
| 94 font->get_glyph (info.codepoint, 0, &info.glyph_index()); | 94 font->get_nominal_glyph (info.codepoint, &info.glyph_index()); |
| 95 } | 95 } |
| 96 | 96 |
| 97 static inline void | 97 static inline void |
| 98 output_char (hb_buffer_t *buffer, hb_codepoint_t unichar, hb_codepoint_t glyph) | 98 output_char (hb_buffer_t *buffer, hb_codepoint_t unichar, hb_codepoint_t glyph) |
| 99 { | 99 { |
| 100 buffer->cur().glyph_index() = glyph; | 100 buffer->cur().glyph_index() = glyph; |
| 101 buffer->output_glyph (unichar); /* This is very confusing indeed. */ | 101 buffer->output_glyph (unichar); /* This is very confusing indeed. */ |
| 102 _hb_glyph_info_set_unicode_props (&buffer->prev(), buffer); | 102 _hb_glyph_info_set_unicode_props (&buffer->prev(), buffer); |
| 103 } | 103 } |
| 104 | 104 |
| (...skipping 12 matching lines...) Expand all Loading... |
| 117 | 117 |
| 118 /* Returns 0 if didn't decompose, number of resulting characters otherwise. */ | 118 /* Returns 0 if didn't decompose, number of resulting characters otherwise. */ |
| 119 static inline unsigned int | 119 static inline unsigned int |
| 120 decompose (const hb_ot_shape_normalize_context_t *c, bool shortest, hb_codepoint
_t ab) | 120 decompose (const hb_ot_shape_normalize_context_t *c, bool shortest, hb_codepoint
_t ab) |
| 121 { | 121 { |
| 122 hb_codepoint_t a, b, a_glyph, b_glyph; | 122 hb_codepoint_t a, b, a_glyph, b_glyph; |
| 123 hb_buffer_t * const buffer = c->buffer; | 123 hb_buffer_t * const buffer = c->buffer; |
| 124 hb_font_t * const font = c->font; | 124 hb_font_t * const font = c->font; |
| 125 | 125 |
| 126 if (!c->decompose (c, ab, &a, &b) || | 126 if (!c->decompose (c, ab, &a, &b) || |
| 127 (b && !font->get_glyph (b, 0, &b_glyph))) | 127 (b && !font->get_nominal_glyph (b, &b_glyph))) |
| 128 return 0; | 128 return 0; |
| 129 | 129 |
| 130 bool has_a = (bool) font->get_glyph (a, 0, &a_glyph); | 130 bool has_a = (bool) font->get_nominal_glyph (a, &a_glyph); |
| 131 if (shortest && has_a) { | 131 if (shortest && has_a) { |
| 132 /* Output a and b */ | 132 /* Output a and b */ |
| 133 output_char (buffer, a, a_glyph); | 133 output_char (buffer, a, a_glyph); |
| 134 if (likely (b)) { | 134 if (likely (b)) { |
| 135 output_char (buffer, b, b_glyph); | 135 output_char (buffer, b, b_glyph); |
| 136 return 2; | 136 return 2; |
| 137 } | 137 } |
| 138 return 1; | 138 return 1; |
| 139 } | 139 } |
| 140 | 140 |
| (...skipping 18 matching lines...) Expand all Loading... |
| 159 return 0; | 159 return 0; |
| 160 } | 160 } |
| 161 | 161 |
| 162 static inline void | 162 static inline void |
| 163 decompose_current_character (const hb_ot_shape_normalize_context_t *c, bool shor
test) | 163 decompose_current_character (const hb_ot_shape_normalize_context_t *c, bool shor
test) |
| 164 { | 164 { |
| 165 hb_buffer_t * const buffer = c->buffer; | 165 hb_buffer_t * const buffer = c->buffer; |
| 166 hb_codepoint_t u = buffer->cur().codepoint; | 166 hb_codepoint_t u = buffer->cur().codepoint; |
| 167 hb_codepoint_t glyph; | 167 hb_codepoint_t glyph; |
| 168 | 168 |
| 169 if (shortest && c->font->get_glyph (u, 0, &glyph)) | 169 if (shortest && c->font->get_nominal_glyph (u, &glyph)) |
| 170 { | 170 { |
| 171 next_char (buffer, glyph); | 171 next_char (buffer, glyph); |
| 172 return; | 172 return; |
| 173 } | 173 } |
| 174 | 174 |
| 175 if (decompose (c, shortest, u)) | 175 if (decompose (c, shortest, u)) |
| 176 { | 176 { |
| 177 skip_char (buffer); | 177 skip_char (buffer); |
| 178 return; | 178 return; |
| 179 } | 179 } |
| 180 | 180 |
| 181 if (!shortest && c->font->get_glyph (u, 0, &glyph)) | 181 if (!shortest && c->font->get_nominal_glyph (u, &glyph)) |
| 182 { | 182 { |
| 183 next_char (buffer, glyph); | 183 next_char (buffer, glyph); |
| 184 return; | 184 return; |
| 185 } | 185 } |
| 186 | 186 |
| 187 if (_hb_glyph_info_is_unicode_space (&buffer->cur())) | 187 if (_hb_glyph_info_is_unicode_space (&buffer->cur())) |
| 188 { | 188 { |
| 189 hb_codepoint_t space_glyph; | 189 hb_codepoint_t space_glyph; |
| 190 hb_unicode_funcs_t::space_t space_type = buffer->unicode->space_fallback_typ
e (u); | 190 hb_unicode_funcs_t::space_t space_type = buffer->unicode->space_fallback_typ
e (u); |
| 191 if (space_type != hb_unicode_funcs_t::NOT_SPACE && c->font->get_glyph (0x002
0u, 0, &space_glyph)) | 191 if (space_type != hb_unicode_funcs_t::NOT_SPACE && c->font->get_nominal_glyp
h (0x0020u, &space_glyph)) |
| 192 { | 192 { |
| 193 _hb_glyph_info_set_unicode_space_fallback_type (&buffer->cur(), space_type
); | 193 _hb_glyph_info_set_unicode_space_fallback_type (&buffer->cur(), space_type
); |
| 194 next_char (buffer, space_glyph); | 194 next_char (buffer, space_glyph); |
| 195 buffer->scratch_flags |= HB_BUFFER_SCRATCH_FLAG_HAS_SPACE_FALLBACK; | 195 buffer->scratch_flags |= HB_BUFFER_SCRATCH_FLAG_HAS_SPACE_FALLBACK; |
| 196 return; | 196 return; |
| 197 } | 197 } |
| 198 } | 198 } |
| 199 | 199 |
| 200 if (u == 0x2011u) | 200 if (u == 0x2011u) |
| 201 { | 201 { |
| 202 /* U+2011 is the only sensible character that is a no-break version of anoth
er character | 202 /* U+2011 is the only sensible character that is a no-break version of anoth
er character |
| 203 * and not a space. The space ones are handled already. Handle this lone o
ne. */ | 203 * and not a space. The space ones are handled already. Handle this lone o
ne. */ |
| 204 hb_codepoint_t other_glyph; | 204 hb_codepoint_t other_glyph; |
| 205 if (c->font->get_glyph (0x2010u, 0, &other_glyph)) | 205 if (c->font->get_nominal_glyph (0x2010u, &other_glyph)) |
| 206 { | 206 { |
| 207 next_char (buffer, other_glyph); | 207 next_char (buffer, other_glyph); |
| 208 return; | 208 return; |
| 209 } | 209 } |
| 210 } | 210 } |
| 211 | 211 |
| 212 next_char (buffer, glyph); /* glyph is initialized in earlier branches. */ | 212 next_char (buffer, glyph); /* glyph is initialized in earlier branches. */ |
| 213 } | 213 } |
| 214 | 214 |
| 215 static inline void | 215 static inline void |
| 216 handle_variation_selector_cluster (const hb_ot_shape_normalize_context_t *c, uns
igned int end, bool short_circuit) | 216 handle_variation_selector_cluster (const hb_ot_shape_normalize_context_t *c, uns
igned int end, bool short_circuit) |
| 217 { | 217 { |
| 218 /* TODO Currently if there's a variation-selector we give-up, it's just too ha
rd. */ | 218 /* TODO Currently if there's a variation-selector we give-up, it's just too ha
rd. */ |
| 219 hb_buffer_t * const buffer = c->buffer; | 219 hb_buffer_t * const buffer = c->buffer; |
| 220 hb_font_t * const font = c->font; | 220 hb_font_t * const font = c->font; |
| 221 for (; buffer->idx < end - 1 && !buffer->in_error;) { | 221 for (; buffer->idx < end - 1 && !buffer->in_error;) { |
| 222 if (unlikely (buffer->unicode->is_variation_selector (buffer->cur(+1).codepo
int))) { | 222 if (unlikely (buffer->unicode->is_variation_selector (buffer->cur(+1).codepo
int))) { |
| 223 /* The next two lines are some ugly lines... But work. */ | 223 /* The next two lines are some ugly lines... But work. */ |
| 224 if (font->get_glyph (buffer->cur().codepoint, buffer->cur(+1).codepoint, &
buffer->cur().glyph_index())) | 224 if (font->get_variation_glyph (buffer->cur().codepoint, buffer->cur(+1).co
depoint, &buffer->cur().glyph_index())) |
| 225 { | 225 { |
| 226 buffer->replace_glyphs (2, 1, &buffer->cur().codepoint); | 226 buffer->replace_glyphs (2, 1, &buffer->cur().codepoint); |
| 227 } | 227 } |
| 228 else | 228 else |
| 229 { | 229 { |
| 230 /* Just pass on the two characters separately, let GSUB do its magic. */ | 230 /* Just pass on the two characters separately, let GSUB do its magic. */ |
| 231 set_glyph (buffer->cur(), font); | 231 set_glyph (buffer->cur(), font); |
| 232 buffer->next_glyph (); | 232 buffer->next_glyph (); |
| 233 set_glyph (buffer->cur(), font); | 233 set_glyph (buffer->cur(), font); |
| 234 buffer->next_glyph (); | 234 buffer->next_glyph (); |
| (...skipping 146 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 381 /* If there's anything between the starter and this char, they should ha
ve CCC | 381 /* If there's anything between the starter and this char, they should ha
ve CCC |
| 382 * smaller than this character's. */ | 382 * smaller than this character's. */ |
| 383 (starter == buffer->out_len - 1 || | 383 (starter == buffer->out_len - 1 || |
| 384 _hb_glyph_info_get_modified_combining_class (&buffer->prev()) < _hb_gly
ph_info_get_modified_combining_class (&buffer->cur())) && | 384 _hb_glyph_info_get_modified_combining_class (&buffer->prev()) < _hb_gly
ph_info_get_modified_combining_class (&buffer->cur())) && |
| 385 /* And compose. */ | 385 /* And compose. */ |
| 386 c.compose (&c, | 386 c.compose (&c, |
| 387 buffer->out_info[starter].codepoint, | 387 buffer->out_info[starter].codepoint, |
| 388 buffer->cur().codepoint, | 388 buffer->cur().codepoint, |
| 389 &composed) && | 389 &composed) && |
| 390 /* And the font has glyph for the composite. */ | 390 /* And the font has glyph for the composite. */ |
| 391 » font->get_glyph (composed, 0, &glyph)) | 391 » font->get_nominal_glyph (composed, &glyph)) |
| 392 { | 392 { |
| 393 /* Composes. */ | 393 /* Composes. */ |
| 394 buffer->next_glyph (); /* Copy to out-buffer. */ | 394 buffer->next_glyph (); /* Copy to out-buffer. */ |
| 395 if (unlikely (buffer->in_error)) | 395 if (unlikely (buffer->in_error)) |
| 396 return; | 396 return; |
| 397 buffer->merge_out_clusters (starter, buffer->out_len); | 397 buffer->merge_out_clusters (starter, buffer->out_len); |
| 398 buffer->out_len--; /* Remove the second composable. */ | 398 buffer->out_len--; /* Remove the second composable. */ |
| 399 /* Modify starter and carry on. */ | 399 /* Modify starter and carry on. */ |
| 400 buffer->out_info[starter].codepoint = composed; | 400 buffer->out_info[starter].codepoint = composed; |
| 401 buffer->out_info[starter].glyph_index() = glyph; | 401 buffer->out_info[starter].glyph_index() = glyph; |
| 402 _hb_glyph_info_set_unicode_props (&buffer->out_info[starter], buffer); | 402 _hb_glyph_info_set_unicode_props (&buffer->out_info[starter], buffer); |
| 403 | 403 |
| 404 continue; | 404 continue; |
| 405 } | 405 } |
| 406 | 406 |
| 407 /* Blocked, or doesn't compose. */ | 407 /* Blocked, or doesn't compose. */ |
| 408 buffer->next_glyph (); | 408 buffer->next_glyph (); |
| 409 | 409 |
| 410 if (_hb_glyph_info_get_modified_combining_class (&buffer->prev()) == 0) | 410 if (_hb_glyph_info_get_modified_combining_class (&buffer->prev()) == 0) |
| 411 starter = buffer->out_len - 1; | 411 starter = buffer->out_len - 1; |
| 412 } | 412 } |
| 413 buffer->swap_buffers (); | 413 buffer->swap_buffers (); |
| 414 | 414 |
| 415 } | 415 } |
| OLD | NEW |