1 /*
2  * Copyright (C) 2015 The Qt Company Ltd
3  *
4  * This is part of HarfBuzz, an OpenType Layout engine library.
5  *
6  * Permission is hereby granted, without written agreement and without
7  * license or royalty fees, to use, copy, modify, and distribute this
8  * software and its documentation for any purpose, provided that the
9  * above copyright notice and the following two paragraphs appear in
10  * all copies of this software.
11  *
12  * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
13  * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
14  * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
15  * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
16  * DAMAGE.
17  *
18  * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
19  * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
20  * FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS
21  * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
22  * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
23  */
24 
25 #ifndef HARFBUZZ_SHAPER_H
26 #define HARFBUZZ_SHAPER_H
27 
28 #include "harfbuzz-global.h"
29 #include "harfbuzz-gdef.h"
30 #include "harfbuzz-gpos.h"
31 #include "harfbuzz-gsub.h"
32 #include "harfbuzz-external.h"
33 #include "harfbuzz-stream-private.h"
34 
35 HB_BEGIN_HEADER
36 
37 /*
38    using anything else than signed or unsigned for bitfields in C is non standard,
39    but accepted by almost all compilers. And it gives a significant reduction in
40    memory consumption as HB_CharAttributes and HB_GlyphAttributes will not have
41    a 4 byte alignment
42 */
43 #ifdef  __xlC__
44 typedef unsigned hb_bitfield;
45 #else
46 typedef hb_uint8 hb_bitfield;
47 #endif
48 
49 typedef enum {
50         HB_Script_Common,
51         HB_Script_Greek,
52         HB_Script_Cyrillic,
53         HB_Script_Armenian,
54         HB_Script_Hebrew,
55         HB_Script_Arabic,
56         HB_Script_Syriac,
57         HB_Script_Thaana,
58         HB_Script_Devanagari,
59         HB_Script_Bengali,
60         HB_Script_Gurmukhi,
61         HB_Script_Gujarati,
62         HB_Script_Oriya,
63         HB_Script_Tamil,
64         HB_Script_Telugu,
65         HB_Script_Kannada,
66         HB_Script_Malayalam,
67         HB_Script_Sinhala,
68         HB_Script_Thai,
69         HB_Script_Lao,
70         HB_Script_Tibetan,
71         HB_Script_Myanmar,
72         HB_Script_Georgian,
73         HB_Script_Hangul,
74         HB_Script_Ogham,
75         HB_Script_Runic,
76         HB_Script_Khmer,
77         HB_Script_Nko,
78         HB_Script_Inherited,
79         HB_ScriptCount = HB_Script_Inherited
80         /*
81         HB_Script_Latin = Common,
82         HB_Script_Ethiopic = Common,
83         HB_Script_Cherokee = Common,
84         HB_Script_CanadianAboriginal = Common,
85         HB_Script_Mongolian = Common,
86         HB_Script_Hiragana = Common,
87         HB_Script_Katakana = Common,
88         HB_Script_Bopomofo = Common,
89         HB_Script_Han = Common,
90         HB_Script_Yi = Common,
91         HB_Script_OldItalic = Common,
92         HB_Script_Gothic = Common,
93         HB_Script_Deseret = Common,
94         HB_Script_Tagalog = Common,
95         HB_Script_Hanunoo = Common,
96         HB_Script_Buhid = Common,
97         HB_Script_Tagbanwa = Common,
98         HB_Script_Limbu = Common,
99         HB_Script_TaiLe = Common,
100         HB_Script_LinearB = Common,
101         HB_Script_Ugaritic = Common,
102         HB_Script_Shavian = Common,
103         HB_Script_Osmanya = Common,
104         HB_Script_Cypriot = Common,
105         HB_Script_Braille = Common,
106         HB_Script_Buginese = Common,
107         HB_Script_Coptic = Common,
108         HB_Script_NewTaiLue = Common,
109         HB_Script_Glagolitic = Common,
110         HB_Script_Tifinagh = Common,
111         HB_Script_SylotiNagri = Common,
112         HB_Script_OldPersian = Common,
113         HB_Script_Kharoshthi = Common,
114         HB_Script_Balinese = Common,
115         HB_Script_Cuneiform = Common,
116         HB_Script_Phoenician = Common,
117         HB_Script_PhagsPa = Common,
118         */
119 } HB_Script;
120 
121 typedef struct
122 {
123     hb_uint32 pos;
124     hb_uint32 length;
125     HB_Script script;
126     hb_uint8 bidiLevel;
127 } HB_ScriptItem;
128 
129 
130 typedef struct {
131     hb_bitfield graphemeBoundary : 1;     /* Valid cursor position (for left/right arrow) */
132     hb_bitfield wordBreak        : 1;
133     hb_bitfield sentenceBoundary : 1;
134     hb_bitfield lineBreak        : 1;
135     hb_bitfield whiteSpace       : 1;     /* A unicode whitespace character */
136     hb_bitfield wordStart        : 1;
137     hb_bitfield wordEnd          : 1;
138     hb_bitfield mandatoryBreak   : 1;
139 } HB_CharAttributes;
140 
141 void HB_GetTailoredCharAttributes(const HB_UChar16 *string, hb_uint32 stringLength,
142                                   const HB_ScriptItem *items, hb_uint32 numItems,
143                                   HB_CharAttributes *attributes);
144 
145 
146 typedef enum {
147     HB_LeftToRight = 0,
148     HB_RightToLeft = 1
149 } HB_StringToGlyphsFlags;
150 
151 typedef enum {
152     HB_ShaperFlag_Default = 0,
153     HB_ShaperFlag_NoKerning = 1,
154     HB_ShaperFlag_UseDesignMetrics = 2
155 } HB_ShaperFlag;
156 
157 /*
158    highest value means highest priority for justification. Justification is done by first inserting kashidas
159    starting with the highest priority positions, then stretching spaces, afterwards extending inter char
160    spacing, and last spacing between arabic words.
161    NoJustification is for example set for arabic where no Kashida can be inserted or for diacritics.
162 */
163 typedef enum {
164     HB_NoJustification= 0,   /* Justification can't be applied after this glyph */
165     HB_Arabic_Space   = 1,   /* This glyph represents a space inside arabic text */
166     HB_Character      = 2,   /* Inter-character justification point follows this glyph */
167     HB_Space          = 4,   /* This glyph represents a blank outside an Arabic run */
168     HB_Arabic_Normal  = 7,   /* Normal Middle-Of-Word glyph that connects to the right (begin) */
169     HB_Arabic_Waw     = 8,   /* Next character is final form of Waw/Ain/Qaf/Fa */
170     HB_Arabic_BaRa    = 9,   /* Next two chars are Ba + Ra/Ya/AlefMaksura */
171     HB_Arabic_Alef    = 10,  /* Next character is final form of Alef/Tah/Lam/Kaf/Gaf */
172     HB_Arabic_HaaDal  = 11,  /* Next character is final form of Haa/Dal/Taa Marbutah */
173     HB_Arabic_Seen    = 12,  /* Initial or Medial form Of Seen/Sad */
174     HB_Arabic_Kashida = 13   /* Kashida(U+640) in middle of word */
175 } HB_JustificationClass;
176 
177 /* This structure is binary compatible with Uniscribe's SCRIPT_VISATTR. Would be nice to keep
178  * it like that. If this is a problem please tell Trolltech :)
179  */
180 typedef struct {
181     hb_bitfield justification   :4;  /* Justification class */
182     hb_bitfield clusterStart    :1;  /* First glyph of representation of cluster */
183     hb_bitfield mark            :1;  /* needs to be positioned around base char */
184     hb_bitfield zeroWidth       :1;  /* ZWJ, ZWNJ etc, with no width */
185     hb_bitfield dontPrint       :1;
186     hb_bitfield combiningClass  :8;
187 } HB_GlyphAttributes;
188 
189 typedef HB_Error (*HB_GetFontTableFunc)(void *font, HB_Tag tag, HB_Byte *buffer, HB_UInt *length);
190 
191 typedef struct HB_FaceRec_ {
192     HB_Bool isSymbolFont;
193 
194     HB_GDEF gdef;
195     HB_GSUB gsub;
196     HB_GPOS gpos;
197     HB_Bool supported_scripts[HB_ScriptCount];
198     HB_Buffer buffer;
199     HB_Script current_script;
200     int current_flags; /* HB_ShaperFlags */
201     HB_Bool has_opentype_kerning;
202     HB_Bool glyphs_substituted;
203     HB_GlyphAttributes *tmpAttributes;
204     unsigned int *tmpLogClusters;
205     int length;
206     int orig_nglyphs;
207     void *font_for_init;
208     HB_GetFontTableFunc get_font_table_func;
209 } HB_FaceRec;
210 
211 
212 
213 HB_Face HB_NewFace(void *font, HB_GetFontTableFunc tableFunc);
214 HB_Face HB_AllocFace(void *font, HB_GetFontTableFunc tableFunc);
215 HB_Face HB_LoadFace(HB_Face face);
216 void HB_FreeFace(HB_Face face);
217 
218 typedef struct {
219     HB_Fixed x, y;
220     HB_Fixed width, height;
221     HB_Fixed xOffset, yOffset;
222 } HB_GlyphMetrics;
223 
224 typedef enum {
225     HB_FontAscent
226 } HB_FontMetric;
227 
228 typedef struct {
229     HB_Bool  (*convertStringToGlyphIndices)(HB_Font font, const HB_UChar16 *string, hb_uint32 length, HB_Glyph *glyphs, hb_uint32 *numGlyphs, HB_Bool rightToLeft);
230     void     (*getGlyphAdvances)(HB_Font font, const HB_Glyph *glyphs, hb_uint32 numGlyphs, HB_Fixed *advances, int flags /*HB_ShaperFlag*/);
231     HB_Bool  (*canRender)(HB_Font font, const HB_UChar16 *string, hb_uint32 length);
232     /* implementation needs to make sure to load a scaled glyph, so /no/ FT_LOAD_NO_SCALE */
233     HB_Error (*getPointInOutline)(HB_Font font, HB_Glyph glyph, int flags /*HB_ShaperFlag*/, hb_uint32 point, HB_Fixed *xpos, HB_Fixed *ypos, hb_uint32 *nPoints);
234     void     (*getGlyphMetrics)(HB_Font font, HB_Glyph glyph, HB_GlyphMetrics *metrics);
235     HB_Fixed (*getFontMetric)(HB_Font font, HB_FontMetric metric);
236 } HB_FontClass;
237 
238 typedef struct HB_Font_ {
239     const HB_FontClass *klass;
240 
241     /* Metrics */
242     HB_UShort x_ppem, y_ppem;
243     HB_16Dot16 x_scale, y_scale;
244 
245     void *userData;
246 } HB_FontRec;
247 
248 typedef struct HB_ShaperItem_ HB_ShaperItem;
249 
250 struct HB_ShaperItem_ {
251     const HB_UChar16 *string;               /* input: the Unicode UTF16 text to be shaped */
252     hb_uint32 stringLength;                 /* input: the length of the input in 16-bit words */
253     HB_ScriptItem item;                     /* input: the current run to be shaped: a run of text all in the same script that is a substring of <string> */
254     HB_Font font;                           /* input: the font: scale, units and function pointers supplying glyph indices and metrics */
255     HB_Face face;                           /* input: the shaper state; current script, access to the OpenType tables , etc. */
256     int shaperFlags;                        /* input (unused) should be set to 0; intended to support flags defined in HB_ShaperFlag */
257     HB_Bool glyphIndicesPresent;            /* input: true if the <glyphs> array contains glyph indices ready to be shaped */
258     hb_uint32 initialGlyphCount;            /* input: if glyphIndicesPresent is true, the number of glyph indices in the <glyphs> array */
259 
260     hb_uint32 num_glyphs;                   /* input: capacity of output arrays <glyphs>, <attributes>, <advances>, <offsets>, and <log_clusters>; */
261                                             /* output: required capacity (may be larger than actual capacity) */
262 
263     HB_Glyph *glyphs;                       /* output: <num_glyphs> indices of shaped glyphs */
264     HB_GlyphAttributes *attributes;         /* output: <num_glyphs> glyph attributes */
265     HB_Fixed *advances;                     /* output: <num_glyphs> advances */
266     HB_FixedPoint *offsets;                 /* output: <num_glyphs> offsets */
267     unsigned short *log_clusters;           /* output: for each output glyph, the index in the input of the start of its logical cluster */
268 
269     /* internal */
270     HB_Bool kerning_applied;                /* output: true if kerning was applied by the shaper */
271 };
272 
273 HB_Bool HB_ShapeItem(HB_ShaperItem *item);
274 
275 HB_END_HEADER
276 
277 #endif
278