Imported Upstream version 1.8.1
[platform/upstream/harfbuzz.git] / src / hb-ot-shape-complex-khmer-private.hh
1 /*
2  * Copyright © 2018  Google, Inc.
3  *
4  *  This is part of HarfBuzz, a text shaping 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  * Google Author(s): Behdad Esfahbod
25  */
26
27 #ifndef HB_OT_SHAPE_COMPLEX_KHMER_PRIVATE_HH
28 #define HB_OT_SHAPE_COMPLEX_KHMER_PRIVATE_HH
29
30 #include "hb-private.hh"
31
32 #include "hb-ot-shape-complex-indic-private.hh"
33
34
35 /* buffer var allocations */
36 #define khmer_category() indic_category() /* khmer_category_t */
37 #define khmer_position() indic_position() /* khmer_position_t */
38
39
40 typedef indic_category_t khmer_category_t;
41 typedef indic_position_t khmer_position_t;
42
43
44 static inline khmer_position_t
45 matra_position_khmer (khmer_position_t side)
46 {
47   switch ((int) side)
48   {
49     case POS_PRE_C:
50       return POS_PRE_M;
51
52     case POS_POST_C:
53     case POS_ABOVE_C:
54     case POS_BELOW_C:
55       return POS_AFTER_POST;
56
57     default:
58       return side;
59   };
60 }
61
62 static inline bool
63 is_consonant_or_vowel (const hb_glyph_info_t &info)
64 {
65   return is_one_of (info, CONSONANT_FLAGS | FLAG (OT_V));
66 }
67
68 static inline bool
69 is_coeng (const hb_glyph_info_t &info)
70 {
71   return is_one_of (info, FLAG (OT_Coeng));
72 }
73
74 static inline void
75 set_khmer_properties (hb_glyph_info_t &info)
76 {
77   hb_codepoint_t u = info.codepoint;
78   unsigned int type = hb_indic_get_categories (u);
79   khmer_category_t cat = (khmer_category_t) (type & 0x7Fu);
80   khmer_position_t pos = (khmer_position_t) (type >> 8);
81
82
83   /*
84    * Re-assign category
85    */
86
87   if (unlikely (u == 0x17C6u)) cat = OT_N; /* Khmer Bindu doesn't like to be repositioned. */
88   else if (unlikely (hb_in_range<hb_codepoint_t> (u, 0x17CDu, 0x17D1u) ||
89                      u == 0x17CBu || u == 0x17D3u || u == 0x17DDu)) /* Khmer Various signs */
90   {
91     /* These can occur mid-syllable (eg. before matras), even though Unicode marks them as Syllable_Modifier.
92      * https://github.com/roozbehp/unicode-data/issues/5 */
93     cat = OT_M;
94     pos = POS_ABOVE_C;
95   }
96   else if (unlikely (hb_in_range<hb_codepoint_t> (u, 0x2010u, 0x2011u))) cat = OT_PLACEHOLDER;
97   else if (unlikely (u == 0x25CCu)) cat = OT_DOTTEDCIRCLE;
98
99
100   /*
101    * Re-assign position.
102    */
103
104   if ((FLAG_UNSAFE (cat) & CONSONANT_FLAGS))
105   {
106     pos = POS_BASE_C;
107     if (u == 0x179Au)
108       cat = OT_Ra;
109   }
110   else if (cat == OT_M)
111   {
112     pos = matra_position_khmer (pos);
113   }
114   else if ((FLAG_UNSAFE (cat) & (FLAG (OT_SM) | FLAG (OT_A) | FLAG (OT_Symbol))))
115   {
116     pos = POS_SMVD;
117   }
118
119   info.khmer_category() = cat;
120   info.khmer_position() = pos;
121 }
122
123
124 #endif /* HB_OT_SHAPE_COMPLEX_KHMER_PRIVATE_HH */