1/* == Start of generated functions == */
2/*
3 * The following functions are generated by running:
4 *
5 * ./gen-vowel-constraints.py use Scripts.txt
6 *
7 * on files with these headers:
8 *
9 * # Copied from https://docs.microsoft.com/en-us/typography/script-development/use
10 * # On October 23, 2018; with documentd dated 02/07/2018.
11 *
12 * # Scripts-11.0.0.txt
13 * # Date: 2018-02-21, 05:34:31 GMT
14 */
15
16#include "hb-ot-shape-complex-vowel-constraints.hh"
17
18static void
19_output_dotted_circle (hb_buffer_t *buffer)
20{
21 hb_glyph_info_t &dottedcircle = buffer->output_glyph (0x25CCu);
22 _hb_glyph_info_reset_continuation (&dottedcircle);
23}
24
25static void
26_output_with_dotted_circle (hb_buffer_t *buffer)
27{
28 _output_dotted_circle (buffer);
29 buffer->next_glyph ();
30}
31
32void
33_hb_preprocess_text_vowel_constraints (const hb_ot_shape_plan_t *plan HB_UNUSED,
34 hb_buffer_t *buffer,
35 hb_font_t *font HB_UNUSED)
36{
37 /* UGLY UGLY UGLY business of adding dotted-circle in the middle of
38 * vowel-sequences that look like another vowel. Data for each script
39 * collected from the USE script development spec.
40 *
41 * https://github.com/harfbuzz/harfbuzz/issues/1019
42 */
43 bool processed = false;
44 buffer->clear_output ();
45 unsigned int count = buffer->len;
46 switch ((unsigned) buffer->props.script)
47 {
48 case HB_SCRIPT_DEVANAGARI:
49 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
50 {
51 bool matched = false;
52 switch (buffer->cur ().codepoint)
53 {
54 case 0x0905u:
55 switch (buffer->cur (1).codepoint)
56 {
57 case 0x093Au: case 0x093Bu: case 0x093Eu: case 0x0945u:
58 case 0x0946u: case 0x0949u: case 0x094Au: case 0x094Bu:
59 case 0x094Cu: case 0x094Fu: case 0x0956u: case 0x0957u:
60 matched = true;
61 break;
62 }
63 break;
64 case 0x0906u:
65 switch (buffer->cur (1).codepoint)
66 {
67 case 0x093Au: case 0x0945u: case 0x0946u: case 0x0947u:
68 case 0x0948u:
69 matched = true;
70 break;
71 }
72 break;
73 case 0x0909u:
74 matched = 0x0941u == buffer->cur (1).codepoint;
75 break;
76 case 0x090Fu:
77 switch (buffer->cur (1).codepoint)
78 {
79 case 0x0945u: case 0x0946u: case 0x0947u:
80 matched = true;
81 break;
82 }
83 break;
84 case 0x0930u:
85 if (0x094Du == buffer->cur (1).codepoint &&
86 buffer->idx + 2 < count &&
87 0x0907u == buffer->cur (2).codepoint)
88 {
89 buffer->next_glyph ();
90 buffer->next_glyph ();
91 _output_dotted_circle (buffer);
92 }
93 break;
94 }
95 buffer->next_glyph ();
96 if (matched) _output_with_dotted_circle (buffer);
97 }
98 processed = true;
99 break;
100
101 case HB_SCRIPT_BENGALI:
102 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
103 {
104 bool matched = false;
105 switch (buffer->cur ().codepoint)
106 {
107 case 0x0985u:
108 matched = 0x09BEu == buffer->cur (1).codepoint;
109 break;
110 case 0x098Bu:
111 matched = 0x09C3u == buffer->cur (1).codepoint;
112 break;
113 case 0x098Cu:
114 matched = 0x09E2u == buffer->cur (1).codepoint;
115 break;
116 }
117 buffer->next_glyph ();
118 if (matched) _output_with_dotted_circle (buffer);
119 }
120 processed = true;
121 break;
122
123 case HB_SCRIPT_GURMUKHI:
124 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
125 {
126 bool matched = false;
127 switch (buffer->cur ().codepoint)
128 {
129 case 0x0A05u:
130 switch (buffer->cur (1).codepoint)
131 {
132 case 0x0A3Eu: case 0x0A48u: case 0x0A4Cu:
133 matched = true;
134 break;
135 }
136 break;
137 case 0x0A72u:
138 switch (buffer->cur (1).codepoint)
139 {
140 case 0x0A3Fu: case 0x0A40u: case 0x0A47u:
141 matched = true;
142 break;
143 }
144 break;
145 case 0x0A73u:
146 switch (buffer->cur (1).codepoint)
147 {
148 case 0x0A41u: case 0x0A42u: case 0x0A4Bu:
149 matched = true;
150 break;
151 }
152 break;
153 }
154 buffer->next_glyph ();
155 if (matched) _output_with_dotted_circle (buffer);
156 }
157 processed = true;
158 break;
159
160 case HB_SCRIPT_GUJARATI:
161 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
162 {
163 bool matched = false;
164 switch (buffer->cur ().codepoint)
165 {
166 case 0x0A85u:
167 switch (buffer->cur (1).codepoint)
168 {
169 case 0x0ABEu: case 0x0AC5u: case 0x0AC7u: case 0x0AC8u:
170 case 0x0AC9u: case 0x0ACBu: case 0x0ACCu:
171 matched = true;
172 break;
173 }
174 break;
175 case 0x0AC5u:
176 matched = 0x0ABEu == buffer->cur (1).codepoint;
177 break;
178 }
179 buffer->next_glyph ();
180 if (matched) _output_with_dotted_circle (buffer);
181 }
182 processed = true;
183 break;
184
185 case HB_SCRIPT_ORIYA:
186 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
187 {
188 bool matched = false;
189 switch (buffer->cur ().codepoint)
190 {
191 case 0x0B05u:
192 matched = 0x0B3Eu == buffer->cur (1).codepoint;
193 break;
194 case 0x0B0Fu: case 0x0B13u:
195 matched = 0x0B57u == buffer->cur (1).codepoint;
196 break;
197 }
198 buffer->next_glyph ();
199 if (matched) _output_with_dotted_circle (buffer);
200 }
201 processed = true;
202 break;
203
204 case HB_SCRIPT_TELUGU:
205 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
206 {
207 bool matched = false;
208 switch (buffer->cur ().codepoint)
209 {
210 case 0x0C12u:
211 switch (buffer->cur (1).codepoint)
212 {
213 case 0x0C4Cu: case 0x0C55u:
214 matched = true;
215 break;
216 }
217 break;
218 case 0x0C3Fu: case 0x0C46u: case 0x0C4Au:
219 matched = 0x0C55u == buffer->cur (1).codepoint;
220 break;
221 }
222 buffer->next_glyph ();
223 if (matched) _output_with_dotted_circle (buffer);
224 }
225 processed = true;
226 break;
227
228 case HB_SCRIPT_KANNADA:
229 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
230 {
231 bool matched = false;
232 switch (buffer->cur ().codepoint)
233 {
234 case 0x0C89u: case 0x0C8Bu:
235 matched = 0x0CBEu == buffer->cur (1).codepoint;
236 break;
237 case 0x0C92u:
238 matched = 0x0CCCu == buffer->cur (1).codepoint;
239 break;
240 }
241 buffer->next_glyph ();
242 if (matched) _output_with_dotted_circle (buffer);
243 }
244 processed = true;
245 break;
246
247 case HB_SCRIPT_MALAYALAM:
248 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
249 {
250 bool matched = false;
251 switch (buffer->cur ().codepoint)
252 {
253 case 0x0D07u: case 0x0D09u:
254 matched = 0x0D57u == buffer->cur (1).codepoint;
255 break;
256 case 0x0D0Eu:
257 matched = 0x0D46u == buffer->cur (1).codepoint;
258 break;
259 case 0x0D12u:
260 switch (buffer->cur (1).codepoint)
261 {
262 case 0x0D3Eu: case 0x0D57u:
263 matched = true;
264 break;
265 }
266 break;
267 }
268 buffer->next_glyph ();
269 if (matched) _output_with_dotted_circle (buffer);
270 }
271 processed = true;
272 break;
273
274 case HB_SCRIPT_SINHALA:
275 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
276 {
277 bool matched = false;
278 switch (buffer->cur ().codepoint)
279 {
280 case 0x0D85u:
281 switch (buffer->cur (1).codepoint)
282 {
283 case 0x0DCFu: case 0x0DD0u: case 0x0DD1u:
284 matched = true;
285 break;
286 }
287 break;
288 case 0x0D8Bu: case 0x0D8Fu: case 0x0D94u:
289 matched = 0x0DDFu == buffer->cur (1).codepoint;
290 break;
291 case 0x0D8Du:
292 matched = 0x0DD8u == buffer->cur (1).codepoint;
293 break;
294 case 0x0D91u:
295 switch (buffer->cur (1).codepoint)
296 {
297 case 0x0DCAu: case 0x0DD9u: case 0x0DDAu: case 0x0DDCu:
298 case 0x0DDDu:
299 matched = true;
300 break;
301 }
302 break;
303 }
304 buffer->next_glyph ();
305 if (matched) _output_with_dotted_circle (buffer);
306 }
307 processed = true;
308 break;
309
310 case HB_SCRIPT_BRAHMI:
311 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
312 {
313 bool matched = false;
314 switch (buffer->cur ().codepoint)
315 {
316 case 0x11005u:
317 matched = 0x11038u == buffer->cur (1).codepoint;
318 break;
319 case 0x1100Bu:
320 matched = 0x1103Eu == buffer->cur (1).codepoint;
321 break;
322 case 0x1100Fu:
323 matched = 0x11042u == buffer->cur (1).codepoint;
324 break;
325 }
326 buffer->next_glyph ();
327 if (matched) _output_with_dotted_circle (buffer);
328 }
329 processed = true;
330 break;
331
332 case HB_SCRIPT_KHUDAWADI:
333 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
334 {
335 bool matched = false;
336 switch (buffer->cur ().codepoint)
337 {
338 case 0x112B0u:
339 switch (buffer->cur (1).codepoint)
340 {
341 case 0x112E0u: case 0x112E5u: case 0x112E6u: case 0x112E7u:
342 case 0x112E8u:
343 matched = true;
344 break;
345 }
346 break;
347 }
348 buffer->next_glyph ();
349 if (matched) _output_with_dotted_circle (buffer);
350 }
351 processed = true;
352 break;
353
354 case HB_SCRIPT_TIRHUTA:
355 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
356 {
357 bool matched = false;
358 switch (buffer->cur ().codepoint)
359 {
360 case 0x11481u:
361 matched = 0x114B0u == buffer->cur (1).codepoint;
362 break;
363 case 0x1148Bu: case 0x1148Du:
364 matched = 0x114BAu == buffer->cur (1).codepoint;
365 break;
366 case 0x114AAu:
367 switch (buffer->cur (1).codepoint)
368 {
369 case 0x114B5u: case 0x114B6u:
370 matched = true;
371 break;
372 }
373 break;
374 }
375 buffer->next_glyph ();
376 if (matched) _output_with_dotted_circle (buffer);
377 }
378 processed = true;
379 break;
380
381 case HB_SCRIPT_MODI:
382 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
383 {
384 bool matched = false;
385 switch (buffer->cur ().codepoint)
386 {
387 case 0x11600u: case 0x11601u:
388 switch (buffer->cur (1).codepoint)
389 {
390 case 0x11639u: case 0x1163Au:
391 matched = true;
392 break;
393 }
394 break;
395 }
396 buffer->next_glyph ();
397 if (matched) _output_with_dotted_circle (buffer);
398 }
399 processed = true;
400 break;
401
402 case HB_SCRIPT_TAKRI:
403 for (buffer->idx = 0; buffer->idx + 1 < count && buffer->successful;)
404 {
405 bool matched = false;
406 switch (buffer->cur ().codepoint)
407 {
408 case 0x11680u:
409 switch (buffer->cur (1).codepoint)
410 {
411 case 0x116ADu: case 0x116B4u: case 0x116B5u:
412 matched = true;
413 break;
414 }
415 break;
416 case 0x11686u:
417 matched = 0x116B2u == buffer->cur (1).codepoint;
418 break;
419 }
420 buffer->next_glyph ();
421 if (matched) _output_with_dotted_circle (buffer);
422 }
423 processed = true;
424 break;
425
426 default:
427 break;
428 }
429 if (processed)
430 {
431 if (buffer->idx < count)
432 buffer->next_glyph ();
433 buffer->swap_buffers ();
434 }
435}
436
437/* == End of generated functions == */
438