1 
2 //          Copyright Ahmet Sait Koçak 2020.
3 // Distributed under the Boost Software License, Version 1.0.
4 //    (See accompanying file LICENSE_1_0.txt or copy at
5 //          https://www.boost.org/LICENSE_1_0.txt)
6 
7 module bindbc.hb.bind.buffer;
8 
9 import bindbc.hb.config;
10 
11 import bindbc.hb.bind.common;
12 import bindbc.hb.bind.font;
13 import bindbc.hb.bind.unicode;
14 
15 extern(C) @nogc nothrow:
16 
17 /**
18  * hb_glyph_info_t:
19  * @codepoint: either a Unicode code point (before shaping) or a glyph index
20  *             (after shaping).
21  * @cluster: the index of the character in the original text that corresponds
22  *           to this #hb_glyph_info_t, or whatever the client passes to
23  *           hb_buffer_add(). More than one #hb_glyph_info_t can have the same
24  *           @cluster value, if they resulted from the same character (e.g. one
25  *           to many glyph substitution), and when more than one character gets
26  *           merged in the same glyph (e.g. many to one glyph substitution) the
27  *           #hb_glyph_info_t will have the smallest cluster value of them.
28  *           By default some characters are merged into the same cluster
29  *           (e.g. combining marks have the same cluster as their bases)
30  *           even if they are separate glyphs, hb_buffer_set_cluster_level()
31  *           allow selecting more fine-grained cluster handling.
32  *
33  * The #hb_glyph_info_t is the structure that holds information about the
34  * glyphs and their relation to input text.
35  */
36 struct hb_glyph_info_t
37 {
38     hb_codepoint_t codepoint;
39     /*< private >*/
40     hb_mask_t mask;
41     /*< public >*/
42     uint cluster;
43 
44     /*< private >*/
45     hb_var_int_t var1;
46     hb_var_int_t var2;
47 }
48 
49 /**
50  * hb_glyph_flags_t:
51  * @HB_GLYPH_FLAG_UNSAFE_TO_BREAK: Indicates that if input text is broken at the
52  * 				   beginning of the cluster this glyph is part of,
53  * 				   then both sides need to be re-shaped, as the
54  * 				   result might be different.  On the flip side,
55  * 				   it means that when this flag is not present,
56  * 				   then it's safe to break the glyph-run at the
57  * 				   beginning of this cluster, and the two sides
58  * 				   represent the exact same result one would get
59  * 				   if breaking input text at the beginning of
60  * 				   this cluster and shaping the two sides
61  * 				   separately.  This can be used to optimize
62  * 				   paragraph layout, by avoiding re-shaping
63  * 				   of each line after line-breaking, or limiting
64  * 				   the reshaping to a small piece around the
65  * 				   breaking point only.
66  * @HB_GLYPH_FLAG_DEFINED: All the currently defined flags.
67  *
68  * Since: 1.5.0
69  */
70 enum : uint
71 {
72     /*< flags >*/
73     HB_GLYPH_FLAG_UNSAFE_TO_BREAK = 0x00000001,
74 
75     HB_GLYPH_FLAG_DEFINED = 0x00000001 /* OR of all defined flags */
76 }
77 alias hb_glyph_flags_t = uint;
78 
79 extern (D) hb_glyph_flags_t hb_glyph_info_get_glyph_flags(const(hb_glyph_info_t)* info)
80 {
81     return cast(hb_glyph_flags_t) (cast(uint) info.mask & HB_GLYPH_FLAG_DEFINED);
82 }
83 
84 /**
85  * hb_glyph_position_t:
86  * @x_advance: how much the line advances after drawing this glyph when setting
87  *             text in horizontal direction.
88  * @y_advance: how much the line advances after drawing this glyph when setting
89  *             text in vertical direction.
90  * @x_offset: how much the glyph moves on the X-axis before drawing it, this
91  *            should not affect how much the line advances.
92  * @y_offset: how much the glyph moves on the Y-axis before drawing it, this
93  *            should not affect how much the line advances.
94  *
95  * The #hb_glyph_position_t is the structure that holds the positions of the
96  * glyph in both horizontal and vertical directions. All positions in
97  * #hb_glyph_position_t are relative to the current point.
98  *
99  */
100 struct hb_glyph_position_t
101 {
102     hb_position_t x_advance;
103     hb_position_t y_advance;
104     hb_position_t x_offset;
105     hb_position_t y_offset;
106 
107     /*< private >*/
108     hb_var_int_t var;
109 }
110 
111 /**
112  * hb_segment_properties_t:
113  * @direction: the #hb_direction_t of the buffer, see hb_buffer_set_direction().
114  * @script: the #hb_script_t of the buffer, see hb_buffer_set_script().
115  * @language: the #hb_language_t of the buffer, see hb_buffer_set_language().
116  *
117  * The structure that holds various text properties of an #hb_buffer_t. Can be
118  * set and retrieved using hb_buffer_set_segment_properties() and
119  * hb_buffer_get_segment_properties(), respectively.
120  */
121 struct hb_segment_properties_t
122 {
123     hb_direction_t direction;
124     hb_script_t script;
125     hb_language_t language;
126     /*< private >*/
127     void* reserved1;
128     void* reserved2;
129 }
130 
131 version(BindHB_Static)
132     hb_bool_t hb_segment_properties_equal (
133         const(hb_segment_properties_t)* a,
134         const(hb_segment_properties_t)* b);
135 else
136 {
137     private alias fp_hb_segment_properties_equal = hb_bool_t function (
138         const(hb_segment_properties_t)* a,
139         const(hb_segment_properties_t)* b);
140     __gshared fp_hb_segment_properties_equal hb_segment_properties_equal;
141 }
142 
143 version(BindHB_Static)
144     uint hb_segment_properties_hash (const(hb_segment_properties_t)* p);
145 else
146 {
147     private alias fp_hb_segment_properties_hash = uint function (const(hb_segment_properties_t)* p);
148     __gshared fp_hb_segment_properties_hash hb_segment_properties_hash;
149 }
150 
151 /**
152  * hb_buffer_t:
153  *
154  * The main structure holding the input text and its properties before shaping,
155  * and output glyphs and their information after shaping.
156  */
157 
158 struct hb_buffer_t;
159 
160 version(BindHB_Static)
161     hb_buffer_t* hb_buffer_create ();
162 else
163 {
164     private alias fp_hb_buffer_create = hb_buffer_t* function ();
165     __gshared fp_hb_buffer_create hb_buffer_create;
166 }
167 
168 version(BindHB_Static)
169     hb_buffer_t* hb_buffer_get_empty ();
170 else
171 {
172     private alias fp_hb_buffer_get_empty = hb_buffer_t* function ();
173     __gshared fp_hb_buffer_get_empty hb_buffer_get_empty;
174 }
175 
176 version(BindHB_Static)
177     hb_buffer_t* hb_buffer_reference (hb_buffer_t* buffer);
178 else
179 {
180     private alias fp_hb_buffer_reference = hb_buffer_t* function (hb_buffer_t* buffer);
181     __gshared fp_hb_buffer_reference hb_buffer_reference;
182 }
183 
184 version(BindHB_Static)
185     void hb_buffer_destroy (hb_buffer_t* buffer);
186 else
187 {
188     private alias fp_hb_buffer_destroy = void function (hb_buffer_t* buffer);
189     __gshared fp_hb_buffer_destroy hb_buffer_destroy;
190 }
191 
192 version(BindHB_Static)
193     hb_bool_t hb_buffer_set_user_data (
194         hb_buffer_t* buffer,
195         hb_user_data_key_t* key,
196         void* data,
197         hb_destroy_func_t destroy,
198         hb_bool_t replace);
199 else
200 {
201     private alias fp_hb_buffer_set_user_data = hb_bool_t function (
202         hb_buffer_t* buffer,
203         hb_user_data_key_t* key,
204         void* data,
205         hb_destroy_func_t destroy,
206         hb_bool_t replace);
207     __gshared fp_hb_buffer_set_user_data hb_buffer_set_user_data;
208 }
209 
210 version(BindHB_Static)
211     void* hb_buffer_get_user_data (hb_buffer_t* buffer, hb_user_data_key_t* key);
212 else
213 {
214     private alias fp_hb_buffer_get_user_data = void* function (hb_buffer_t* buffer, hb_user_data_key_t* key);
215     __gshared fp_hb_buffer_get_user_data hb_buffer_get_user_data;
216 }
217 
218 /**
219  * hb_buffer_content_type_t:
220  * @HB_BUFFER_CONTENT_TYPE_INVALID: Initial value for new buffer.
221  * @HB_BUFFER_CONTENT_TYPE_UNICODE: The buffer contains input characters (before shaping).
222  * @HB_BUFFER_CONTENT_TYPE_GLYPHS: The buffer contains output glyphs (after shaping).
223  */
224 enum : int
225 {
226     HB_BUFFER_CONTENT_TYPE_INVALID = 0,
227     HB_BUFFER_CONTENT_TYPE_UNICODE = 1,
228     HB_BUFFER_CONTENT_TYPE_GLYPHS = 2
229 }
230 alias hb_buffer_content_type_t = int;
231 
232 version(BindHB_Static)
233     void hb_buffer_set_content_type (
234         hb_buffer_t* buffer,
235         hb_buffer_content_type_t content_type);
236 else
237 {
238     private alias fp_hb_buffer_set_content_type = void function (
239         hb_buffer_t* buffer,
240         hb_buffer_content_type_t content_type);
241     __gshared fp_hb_buffer_set_content_type hb_buffer_set_content_type;
242 }
243 
244 version(BindHB_Static)
245     hb_buffer_content_type_t hb_buffer_get_content_type (hb_buffer_t* buffer);
246 else
247 {
248     private alias fp_hb_buffer_get_content_type = hb_buffer_content_type_t function (hb_buffer_t* buffer);
249     __gshared fp_hb_buffer_get_content_type hb_buffer_get_content_type;
250 }
251 
252 version(BindHB_Static)
253     void hb_buffer_set_unicode_funcs (
254         hb_buffer_t* buffer,
255         hb_unicode_funcs_t* unicode_funcs);
256 else
257 {
258     private alias fp_hb_buffer_set_unicode_funcs = void function (
259         hb_buffer_t* buffer,
260         hb_unicode_funcs_t* unicode_funcs);
261     __gshared fp_hb_buffer_set_unicode_funcs hb_buffer_set_unicode_funcs;
262 }
263 
264 version(BindHB_Static)
265     hb_unicode_funcs_t* hb_buffer_get_unicode_funcs (hb_buffer_t* buffer);
266 else
267 {
268     private alias fp_hb_buffer_get_unicode_funcs = hb_unicode_funcs_t* function (hb_buffer_t* buffer);
269     __gshared fp_hb_buffer_get_unicode_funcs hb_buffer_get_unicode_funcs;
270 }
271 
272 version(BindHB_Static)
273     void hb_buffer_set_direction (hb_buffer_t* buffer, hb_direction_t direction);
274 else
275 {
276     private alias fp_hb_buffer_set_direction = void function (hb_buffer_t* buffer, hb_direction_t direction);
277     __gshared fp_hb_buffer_set_direction hb_buffer_set_direction;
278 }
279 
280 version(BindHB_Static)
281     hb_direction_t hb_buffer_get_direction (hb_buffer_t* buffer);
282 else
283 {
284     private alias fp_hb_buffer_get_direction = hb_direction_t function (hb_buffer_t* buffer);
285     __gshared fp_hb_buffer_get_direction hb_buffer_get_direction;
286 }
287 
288 version(BindHB_Static)
289     void hb_buffer_set_script (hb_buffer_t* buffer, hb_script_t script);
290 else
291 {
292     private alias fp_hb_buffer_set_script = void function (hb_buffer_t* buffer, hb_script_t script);
293     __gshared fp_hb_buffer_set_script hb_buffer_set_script;
294 }
295 
296 version(BindHB_Static)
297     hb_script_t hb_buffer_get_script (hb_buffer_t* buffer);
298 else
299 {
300     private alias fp_hb_buffer_get_script = hb_script_t function (hb_buffer_t* buffer);
301     __gshared fp_hb_buffer_get_script hb_buffer_get_script;
302 }
303 
304 version(BindHB_Static)
305     void hb_buffer_set_language (hb_buffer_t* buffer, hb_language_t language);
306 else
307 {
308     private alias fp_hb_buffer_set_language = void function (hb_buffer_t* buffer, hb_language_t language);
309     __gshared fp_hb_buffer_set_language hb_buffer_set_language;
310 }
311 
312 version(BindHB_Static)
313     hb_language_t hb_buffer_get_language (hb_buffer_t* buffer);
314 else
315 {
316     private alias fp_hb_buffer_get_language = hb_language_t function (hb_buffer_t* buffer);
317     __gshared fp_hb_buffer_get_language hb_buffer_get_language;
318 }
319 
320 version(BindHB_Static)
321     void hb_buffer_set_segment_properties (
322         hb_buffer_t* buffer,
323         const(hb_segment_properties_t)* props);
324 else
325 {
326     private alias fp_hb_buffer_set_segment_properties = void function (
327         hb_buffer_t* buffer,
328         const(hb_segment_properties_t)* props);
329     __gshared fp_hb_buffer_set_segment_properties hb_buffer_set_segment_properties;
330 }
331 
332 version(BindHB_Static)
333     void hb_buffer_get_segment_properties (
334         hb_buffer_t* buffer,
335         hb_segment_properties_t* props);
336 else
337 {
338     private alias fp_hb_buffer_get_segment_properties = void function (
339         hb_buffer_t* buffer,
340         hb_segment_properties_t* props);
341     __gshared fp_hb_buffer_get_segment_properties hb_buffer_get_segment_properties;
342 }
343 
344 version(BindHB_Static)
345     void hb_buffer_guess_segment_properties (hb_buffer_t* buffer);
346 else
347 {
348     private alias fp_hb_buffer_guess_segment_properties = void function (hb_buffer_t* buffer);
349     __gshared fp_hb_buffer_guess_segment_properties hb_buffer_guess_segment_properties;
350 }
351 
352 /**
353  * hb_buffer_flags_t:
354  * @HB_BUFFER_FLAG_DEFAULT: the default buffer flag.
355  * @HB_BUFFER_FLAG_BOT: flag indicating that special handling of the beginning
356  *                      of text paragraph can be applied to this buffer. Should usually
357  *                      be set, unless you are passing to the buffer only part
358  *                      of the text without the full context.
359  * @HB_BUFFER_FLAG_EOT: flag indicating that special handling of the end of text
360  *                      paragraph can be applied to this buffer, similar to
361  *                      @HB_BUFFER_FLAG_BOT.
362  * @HB_BUFFER_FLAG_PRESERVE_DEFAULT_IGNORABLES:
363  *                      flag indication that character with Default_Ignorable
364  *                      Unicode property should use the corresponding glyph
365  *                      from the font, instead of hiding them (done by
366  *                      replacing them with the space glyph and zeroing the
367  *                      advance width.)  This flag takes precedence over
368  *                      @HB_BUFFER_FLAG_REMOVE_DEFAULT_IGNORABLES.
369  * @HB_BUFFER_FLAG_REMOVE_DEFAULT_IGNORABLES:
370  *                      flag indication that character with Default_Ignorable
371  *                      Unicode property should be removed from glyph string
372  *                      instead of hiding them (done by replacing them with the
373  *                      space glyph and zeroing the advance width.)
374  *                      @HB_BUFFER_FLAG_PRESERVE_DEFAULT_IGNORABLES takes
375  *                      precedence over this flag. Since: 1.8.0
376  * @HB_BUFFER_FLAG_DO_NOT_INSERT_DOTTED_CIRCLE:
377  *                      flag indicating that a dotted circle should
378  *                      not be inserted in the rendering of incorrect
379  *                      character sequences (such at <0905 093E>). Since: 2.4
380  *
381  * Since: 0.9.20
382  */
383 enum : uint
384 {
385     /*< flags >*/
386     HB_BUFFER_FLAG_DEFAULT = 0x00000000u,
387     HB_BUFFER_FLAG_BOT = 0x00000001u, /* Beginning-of-text */
388     HB_BUFFER_FLAG_EOT = 0x00000002u, /* End-of-text */
389     HB_BUFFER_FLAG_PRESERVE_DEFAULT_IGNORABLES = 0x00000004u,
390     HB_BUFFER_FLAG_REMOVE_DEFAULT_IGNORABLES = 0x00000008u,
391     HB_BUFFER_FLAG_DO_NOT_INSERT_DOTTED_CIRCLE = 0x00000010u
392 }
393 alias hb_buffer_flags_t = uint;
394 
395 version(BindHB_Static)
396     void hb_buffer_set_flags (hb_buffer_t* buffer, hb_buffer_flags_t flags);
397 else
398 {
399     private alias fp_hb_buffer_set_flags = void function (hb_buffer_t* buffer, hb_buffer_flags_t flags);
400     __gshared fp_hb_buffer_set_flags hb_buffer_set_flags;
401 }
402 
403 version(BindHB_Static)
404     hb_buffer_flags_t hb_buffer_get_flags (hb_buffer_t* buffer);
405 else
406 {
407     private alias fp_hb_buffer_get_flags = hb_buffer_flags_t function (hb_buffer_t* buffer);
408     __gshared fp_hb_buffer_get_flags hb_buffer_get_flags;
409 }
410 
411 /**
412  * hb_buffer_cluster_level_t:
413  * @HB_BUFFER_CLUSTER_LEVEL_MONOTONE_GRAPHEMES: Return cluster values grouped by graphemes into
414  *   monotone order.
415  * @HB_BUFFER_CLUSTER_LEVEL_MONOTONE_CHARACTERS: Return cluster values grouped into monotone order.
416  * @HB_BUFFER_CLUSTER_LEVEL_CHARACTERS: Don't group cluster values.
417  * @HB_BUFFER_CLUSTER_LEVEL_DEFAULT: Default cluster level,
418  *   equal to @HB_BUFFER_CLUSTER_LEVEL_MONOTONE_GRAPHEMES.
419  *
420  * Since: 0.9.42
421  */
422 enum : int
423 {
424     HB_BUFFER_CLUSTER_LEVEL_MONOTONE_GRAPHEMES = 0,
425     HB_BUFFER_CLUSTER_LEVEL_MONOTONE_CHARACTERS = 1,
426     HB_BUFFER_CLUSTER_LEVEL_CHARACTERS = 2,
427     HB_BUFFER_CLUSTER_LEVEL_DEFAULT = HB_BUFFER_CLUSTER_LEVEL_MONOTONE_GRAPHEMES
428 }
429 alias hb_buffer_cluster_level_t = int;
430 
431 version(BindHB_Static)
432     void hb_buffer_set_cluster_level (
433         hb_buffer_t* buffer,
434         hb_buffer_cluster_level_t cluster_level);
435 else
436 {
437     private alias fp_hb_buffer_set_cluster_level = void function (
438         hb_buffer_t* buffer,
439         hb_buffer_cluster_level_t cluster_level);
440     __gshared fp_hb_buffer_set_cluster_level hb_buffer_set_cluster_level;
441 }
442 
443 version(BindHB_Static)
444     hb_buffer_cluster_level_t hb_buffer_get_cluster_level (hb_buffer_t* buffer);
445 else
446 {
447     private alias fp_hb_buffer_get_cluster_level = hb_buffer_cluster_level_t function (hb_buffer_t* buffer);
448     __gshared fp_hb_buffer_get_cluster_level hb_buffer_get_cluster_level;
449 }
450 
451 /**
452  * HB_BUFFER_REPLACEMENT_CODEPOINT_DEFAULT:
453  *
454  * The default code point for replacing invalid characters in a given encoding.
455  * Set to U+FFFD REPLACEMENT CHARACTER.
456  *
457  * Since: 0.9.31
458  */
459 enum HB_BUFFER_REPLACEMENT_CODEPOINT_DEFAULT = 0xFFFDu;
460 
461 version(BindHB_Static)
462     void hb_buffer_set_replacement_codepoint (
463         hb_buffer_t* buffer,
464         hb_codepoint_t replacement);
465 else
466 {
467     private alias fp_hb_buffer_set_replacement_codepoint = void function (
468         hb_buffer_t* buffer,
469         hb_codepoint_t replacement);
470     __gshared fp_hb_buffer_set_replacement_codepoint hb_buffer_set_replacement_codepoint;
471 }
472 
473 version(BindHB_Static)
474     hb_codepoint_t hb_buffer_get_replacement_codepoint (hb_buffer_t* buffer);
475 else
476 {
477     private alias fp_hb_buffer_get_replacement_codepoint = hb_codepoint_t function (hb_buffer_t* buffer);
478     __gshared fp_hb_buffer_get_replacement_codepoint hb_buffer_get_replacement_codepoint;
479 }
480 
481 static if (hbSupport >= HBSupport.v2_6_3)
482 {
483 	version(BindHB_Static)
484 		void hb_buffer_set_invisible_glyph (
485 			hb_buffer_t* buffer,
486 			hb_codepoint_t invisible);
487 	else
488 	{
489 		private alias fp_hb_buffer_set_invisible_glyph = void function (
490 			hb_buffer_t* buffer,
491 			hb_codepoint_t invisible);
492 		__gshared fp_hb_buffer_set_invisible_glyph hb_buffer_set_invisible_glyph;
493 	}
494 	
495 	version(BindHB_Static)
496 		hb_codepoint_t hb_buffer_get_invisible_glyph (hb_buffer_t* buffer);
497 	else
498 	{
499 		private alias fp_hb_buffer_get_invisible_glyph = hb_codepoint_t function (hb_buffer_t* buffer);
500 		__gshared fp_hb_buffer_get_invisible_glyph hb_buffer_get_invisible_glyph;
501 	}
502 }
503 
504 version(BindHB_Static)
505     void hb_buffer_reset (hb_buffer_t* buffer);
506 else
507 {
508     private alias fp_hb_buffer_reset = void function (hb_buffer_t* buffer);
509     __gshared fp_hb_buffer_reset hb_buffer_reset;
510 }
511 
512 version(BindHB_Static)
513     void hb_buffer_clear_contents (hb_buffer_t* buffer);
514 else
515 {
516     private alias fp_hb_buffer_clear_contents = void function (hb_buffer_t* buffer);
517     __gshared fp_hb_buffer_clear_contents hb_buffer_clear_contents;
518 }
519 
520 version(BindHB_Static)
521     hb_bool_t hb_buffer_pre_allocate (hb_buffer_t* buffer, uint size);
522 else
523 {
524     private alias fp_hb_buffer_pre_allocate = hb_bool_t function (hb_buffer_t* buffer, uint size);
525     __gshared fp_hb_buffer_pre_allocate hb_buffer_pre_allocate;
526 }
527 
528 version(BindHB_Static)
529     hb_bool_t hb_buffer_allocation_successful (hb_buffer_t* buffer);
530 else
531 {
532     private alias fp_hb_buffer_allocation_successful = hb_bool_t function (hb_buffer_t* buffer);
533     __gshared fp_hb_buffer_allocation_successful hb_buffer_allocation_successful;
534 }
535 
536 version(BindHB_Static)
537     void hb_buffer_reverse (hb_buffer_t* buffer);
538 else
539 {
540     private alias fp_hb_buffer_reverse = void function (hb_buffer_t* buffer);
541     __gshared fp_hb_buffer_reverse hb_buffer_reverse;
542 }
543 
544 version(BindHB_Static)
545     void hb_buffer_reverse_range (hb_buffer_t* buffer, uint start, uint end);
546 else
547 {
548     private alias fp_hb_buffer_reverse_range = void function (hb_buffer_t* buffer, uint start, uint end);
549     __gshared fp_hb_buffer_reverse_range hb_buffer_reverse_range;
550 }
551 
552 version(BindHB_Static)
553     void hb_buffer_reverse_clusters (hb_buffer_t* buffer);
554 else
555 {
556     private alias fp_hb_buffer_reverse_clusters = void function (hb_buffer_t* buffer);
557     __gshared fp_hb_buffer_reverse_clusters hb_buffer_reverse_clusters;
558 }
559 
560 /* Filling the buffer in */
561 
562 version(BindHB_Static)
563     void hb_buffer_add (
564         hb_buffer_t* buffer,
565         hb_codepoint_t codepoint,
566         uint cluster);
567 else
568 {
569     private alias fp_hb_buffer_add = void function (
570         hb_buffer_t* buffer,
571         hb_codepoint_t codepoint,
572         uint cluster);
573     __gshared fp_hb_buffer_add hb_buffer_add;
574 }
575 
576 version(BindHB_Static)
577     void hb_buffer_add_utf8 (
578         hb_buffer_t* buffer,
579         const(char)* text,
580         int text_length,
581         uint item_offset,
582         int item_length);
583 else
584 {
585     private alias fp_hb_buffer_add_utf8 = void function (
586         hb_buffer_t* buffer,
587         const(char)* text,
588         int text_length,
589         uint item_offset,
590         int item_length);
591     __gshared fp_hb_buffer_add_utf8 hb_buffer_add_utf8;
592 }
593 
594 version(BindHB_Static)
595     void hb_buffer_add_utf16 (
596         hb_buffer_t* buffer,
597         const(ushort)* text,
598         int text_length,
599         uint item_offset,
600         int item_length);
601 else
602 {
603     private alias fp_hb_buffer_add_utf16 = void function (
604         hb_buffer_t* buffer,
605         const(wchar)* text,
606         int text_length,
607         uint item_offset,
608         int item_length);
609     __gshared fp_hb_buffer_add_utf16 hb_buffer_add_utf16;
610 }
611 
612 version(BindHB_Static)
613     void hb_buffer_add_utf32 (
614         hb_buffer_t* buffer,
615         const(uint)* text,
616         int text_length,
617         uint item_offset,
618         int item_length);
619 else
620 {
621     private alias fp_hb_buffer_add_utf32 = void function (
622         hb_buffer_t* buffer,
623         const(dchar)* text,
624         int text_length,
625         uint item_offset,
626         int item_length);
627     __gshared fp_hb_buffer_add_utf32 hb_buffer_add_utf32;
628 }
629 
630 version(BindHB_Static)
631     void hb_buffer_add_latin1 (
632         hb_buffer_t* buffer,
633         const(ubyte)* text,
634         int text_length,
635         uint item_offset,
636         int item_length);
637 else
638 {
639     private alias fp_hb_buffer_add_latin1 = void function (
640         hb_buffer_t* buffer,
641         const(ubyte)* text,
642         int text_length,
643         uint item_offset,
644         int item_length);
645     __gshared fp_hb_buffer_add_latin1 hb_buffer_add_latin1;
646 }
647 
648 version(BindHB_Static)
649     void hb_buffer_add_codepoints (
650         hb_buffer_t* buffer,
651         const(hb_codepoint_t)* text,
652         int text_length,
653         uint item_offset,
654         int item_length);
655 else
656 {
657     private alias fp_hb_buffer_add_codepoints = void function (
658         hb_buffer_t* buffer,
659         const(hb_codepoint_t)* text,
660         int text_length,
661         uint item_offset,
662         int item_length);
663     __gshared fp_hb_buffer_add_codepoints hb_buffer_add_codepoints;
664 }
665 
666 version(BindHB_Static)
667     void hb_buffer_append (
668         hb_buffer_t* buffer,
669         hb_buffer_t* source,
670         uint start,
671         uint end);
672 else
673 {
674     private alias fp_hb_buffer_append = void function (
675         hb_buffer_t* buffer,
676         hb_buffer_t* source,
677         uint start,
678         uint end);
679     __gshared fp_hb_buffer_append hb_buffer_append;
680 }
681 
682 version(BindHB_Static)
683     hb_bool_t hb_buffer_set_length (hb_buffer_t* buffer, uint length);
684 else
685 {
686     private alias fp_hb_buffer_set_length = hb_bool_t function (hb_buffer_t* buffer, uint length);
687     __gshared fp_hb_buffer_set_length hb_buffer_set_length;
688 }
689 
690 version(BindHB_Static)
691     uint hb_buffer_get_length (hb_buffer_t* buffer);
692 else
693 {
694     private alias fp_hb_buffer_get_length = uint function (hb_buffer_t* buffer);
695     __gshared fp_hb_buffer_get_length hb_buffer_get_length;
696 }
697 
698 /* Getting glyphs out of the buffer */
699 
700 version(BindHB_Static)
701     hb_glyph_info_t* hb_buffer_get_glyph_infos (hb_buffer_t* buffer, uint* length);
702 else
703 {
704     private alias fp_hb_buffer_get_glyph_infos = hb_glyph_info_t* function (hb_buffer_t* buffer, uint* length);
705     __gshared fp_hb_buffer_get_glyph_infos hb_buffer_get_glyph_infos;
706 }
707 
708 version(BindHB_Static)
709     hb_glyph_position_t* hb_buffer_get_glyph_positions (
710         hb_buffer_t* buffer,
711         uint* length);
712 else
713 {
714     private alias fp_hb_buffer_get_glyph_positions = hb_glyph_position_t* function (
715         hb_buffer_t* buffer,
716         uint* length);
717     __gshared fp_hb_buffer_get_glyph_positions hb_buffer_get_glyph_positions;
718 }
719 
720 version(BindHB_Static)
721     void hb_buffer_normalize_glyphs (hb_buffer_t* buffer);
722 else
723 {
724     private alias fp_hb_buffer_normalize_glyphs = void function (hb_buffer_t* buffer);
725     __gshared fp_hb_buffer_normalize_glyphs hb_buffer_normalize_glyphs;
726 }
727 
728 /*
729  * Serialize
730  */
731 
732 /**
733  * hb_buffer_serialize_flags_t:
734  * @HB_BUFFER_SERIALIZE_FLAG_DEFAULT: serialize glyph names, clusters and positions.
735  * @HB_BUFFER_SERIALIZE_FLAG_NO_CLUSTERS: do not serialize glyph cluster.
736  * @HB_BUFFER_SERIALIZE_FLAG_NO_POSITIONS: do not serialize glyph position information.
737  * @HB_BUFFER_SERIALIZE_FLAG_NO_GLYPH_NAMES: do no serialize glyph name.
738  * @HB_BUFFER_SERIALIZE_FLAG_GLYPH_EXTENTS: serialize glyph extents.
739  * @HB_BUFFER_SERIALIZE_FLAG_GLYPH_FLAGS: serialize glyph flags. Since: 1.5.0
740  * @HB_BUFFER_SERIALIZE_FLAG_NO_ADVANCES: do not serialize glyph advances,
741  *  glyph offsets will reflect absolute glyph positions. Since: 1.8.0
742  *
743  * Flags that control what glyph information are serialized in hb_buffer_serialize_glyphs().
744  *
745  * Since: 0.9.20
746  */
747 enum : uint
748 {
749     /*< flags >*/
750     HB_BUFFER_SERIALIZE_FLAG_DEFAULT = 0x00000000u,
751     HB_BUFFER_SERIALIZE_FLAG_NO_CLUSTERS = 0x00000001u,
752     HB_BUFFER_SERIALIZE_FLAG_NO_POSITIONS = 0x00000002u,
753     HB_BUFFER_SERIALIZE_FLAG_NO_GLYPH_NAMES = 0x00000004u,
754     HB_BUFFER_SERIALIZE_FLAG_GLYPH_EXTENTS = 0x00000008u,
755     HB_BUFFER_SERIALIZE_FLAG_GLYPH_FLAGS = 0x00000010u,
756     HB_BUFFER_SERIALIZE_FLAG_NO_ADVANCES = 0x00000020u
757 }
758 alias hb_buffer_serialize_flags_t = uint;
759 
760 /**
761  * hb_buffer_serialize_format_t:
762  * @HB_BUFFER_SERIALIZE_FORMAT_TEXT: a human-readable, plain text format.
763  * @HB_BUFFER_SERIALIZE_FORMAT_JSON: a machine-readable JSON format.
764  * @HB_BUFFER_SERIALIZE_FORMAT_INVALID: invalid format.
765  *
766  * The buffer serialization and de-serialization format used in
767  * hb_buffer_serialize_glyphs() and hb_buffer_deserialize_glyphs().
768  *
769  * Since: 0.9.2
770  */
771 enum : hb_tag_t
772 {
773     HB_BUFFER_SERIALIZE_FORMAT_TEXT = HB_TAG('T', 'E', 'X', 'T'),
774     HB_BUFFER_SERIALIZE_FORMAT_JSON = HB_TAG('J', 'S', 'O', 'N'),
775     HB_BUFFER_SERIALIZE_FORMAT_INVALID = HB_TAG_NONE
776 }
777 alias hb_buffer_serialize_format_t = hb_tag_t;
778 
779 version(BindHB_Static)
780     hb_buffer_serialize_format_t hb_buffer_serialize_format_from_string (
781         const(char)* str,
782         int len);
783 else
784 {
785     private alias fp_hb_buffer_serialize_format_from_string = hb_buffer_serialize_format_t function (
786         const(char)* str,
787         int len);
788     __gshared fp_hb_buffer_serialize_format_from_string hb_buffer_serialize_format_from_string;
789 }
790 
791 version(BindHB_Static)
792     const(char)* hb_buffer_serialize_format_to_string (
793         hb_buffer_serialize_format_t format);
794 else
795 {
796     private alias fp_hb_buffer_serialize_format_to_string = const(char)* function (
797         hb_buffer_serialize_format_t format);
798     __gshared fp_hb_buffer_serialize_format_to_string hb_buffer_serialize_format_to_string;
799 }
800 
801 version(BindHB_Static)
802     const(char*)* hb_buffer_serialize_list_formats ();
803 else
804 {
805     private alias fp_hb_buffer_serialize_list_formats = const(char*)* function ();
806     __gshared fp_hb_buffer_serialize_list_formats hb_buffer_serialize_list_formats;
807 }
808 
809 version(BindHB_Static)
810     uint hb_buffer_serialize_glyphs (
811         hb_buffer_t* buffer,
812         uint start,
813         uint end,
814         char* buf,
815         uint buf_size,
816         uint* buf_consumed,
817         hb_font_t* font,
818         hb_buffer_serialize_format_t format,
819         hb_buffer_serialize_flags_t flags);
820 else
821 {
822     private alias fp_hb_buffer_serialize_glyphs = uint function (
823         hb_buffer_t* buffer,
824         uint start,
825         uint end,
826         char* buf,
827         uint buf_size,
828         uint* buf_consumed,
829         hb_font_t* font,
830         hb_buffer_serialize_format_t format,
831         hb_buffer_serialize_flags_t flags);
832     __gshared fp_hb_buffer_serialize_glyphs hb_buffer_serialize_glyphs;
833 }
834 
835 version(BindHB_Static)
836     hb_bool_t hb_buffer_deserialize_glyphs (
837         hb_buffer_t* buffer,
838         const(char)* buf,
839         int buf_len,
840         const(char*)* end_ptr,
841         hb_font_t* font,
842         hb_buffer_serialize_format_t format);
843 else
844 {
845     private alias fp_hb_buffer_deserialize_glyphs = hb_bool_t function (
846         hb_buffer_t* buffer,
847         const(char)* buf,
848         int buf_len,
849         const(char*)* end_ptr,
850         hb_font_t* font,
851         hb_buffer_serialize_format_t format);
852     __gshared fp_hb_buffer_deserialize_glyphs hb_buffer_deserialize_glyphs;
853 }
854 
855 /*
856  * Compare buffers
857  */
858 
859 enum : uint
860 {
861     /*< flags >*/
862     HB_BUFFER_DIFF_FLAG_EQUAL = 0x0000,
863 
864     /* Buffers with different content_type cannot be meaningfully compared
865      * in any further detail. */
866     HB_BUFFER_DIFF_FLAG_CONTENT_TYPE_MISMATCH = 0x0001,
867 
868     /* For buffers with differing length, the per-glyph comparison is not
869      * attempted, though we do still scan reference for dottedcircle / .notdef
870      * glyphs. */
871     HB_BUFFER_DIFF_FLAG_LENGTH_MISMATCH = 0x0002,
872 
873     /* We want to know if dottedcircle / .notdef glyphs are present in the
874      * reference, as we may not care so much about other differences in this
875      * case. */
876     HB_BUFFER_DIFF_FLAG_NOTDEF_PRESENT = 0x0004,
877     HB_BUFFER_DIFF_FLAG_DOTTED_CIRCLE_PRESENT = 0x0008,
878 
879     /* If the buffers have the same length, we compare them glyph-by-glyph
880      * and report which aspect(s) of the glyph info/position are different. */
881     HB_BUFFER_DIFF_FLAG_CODEPOINT_MISMATCH = 0x0010,
882     HB_BUFFER_DIFF_FLAG_CLUSTER_MISMATCH = 0x0020,
883     HB_BUFFER_DIFF_FLAG_GLYPH_FLAGS_MISMATCH = 0x0040,
884     HB_BUFFER_DIFF_FLAG_POSITION_MISMATCH = 0x0080
885 }
886 alias hb_buffer_diff_flags_t = uint;
887 
888 /* Compare the contents of two buffers, report types of differences. */
889 version(BindHB_Static)
890     hb_buffer_diff_flags_t hb_buffer_diff (
891         hb_buffer_t* buffer,
892         hb_buffer_t* reference,
893         hb_codepoint_t dottedcircle_glyph,
894         uint position_fuzz);
895 else
896 {
897     private alias fp_hb_buffer_diff = hb_buffer_diff_flags_t function (
898         hb_buffer_t* buffer,
899         hb_buffer_t* reference,
900         hb_codepoint_t dottedcircle_glyph,
901         uint position_fuzz);
902     __gshared fp_hb_buffer_diff hb_buffer_diff;
903 }
904 
905 /*
906  * Debugging.
907  */
908 
909 alias hb_buffer_message_func_t = int function (
910     hb_buffer_t* buffer,
911     hb_font_t* font,
912     const(char)* message,
913     void* user_data);
914 
915 version(BindHB_Static)
916     void hb_buffer_set_message_func (
917         hb_buffer_t* buffer,
918         hb_buffer_message_func_t func,
919         void* user_data,
920         hb_destroy_func_t destroy);
921 else
922 {
923     private alias fp_hb_buffer_set_message_func = void function (
924         hb_buffer_t* buffer,
925         hb_buffer_message_func_t func,
926         void* user_data,
927         hb_destroy_func_t destroy);
928     __gshared fp_hb_buffer_set_message_func hb_buffer_set_message_func;
929 }