Merge branch 'tizen' into devel/new_mesh
[platform/core/uifw/dali-adaptor.git] / text / dali / devel-api / text-abstraction / script.cpp
1 /*
2  * Copyright (c) 2015 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 // FILE HEADER
19 #include <dali/devel-api/text-abstraction/script.h>
20
21 namespace Dali
22 {
23
24 namespace TextAbstraction
25 {
26
27 namespace
28 {
29 const unsigned int WHITE_SPACE_THRESHOLD  = 0x21; ///< All characters below 0x21 are considered white spaces.
30 const unsigned int CHAR_FL   = 0x000A; ///< NL Line feed, new line.
31 const unsigned int CHAR_VT   = 0x000B; ///< Vertical tab.
32 const unsigned int CHAR_FF   = 0x000C; ///< NP Form feed, new page.
33 const unsigned int CHAR_NEL  = 0x0085; ///< Next line.
34 const unsigned int CHAR_LS   = 0x2028; ///< Line separator.
35 const unsigned int CHAR_PS   = 0x2029; ///< Paragraph separator
36
37 const unsigned int CHAR_ZWS  = 0x200B; ///< Zero width space.
38 const unsigned int CHAR_ZWNJ = 0x200C; ///< Zero width non joiner.
39 const unsigned int CHAR_ZWJ  = 0x200D; ///< Zero width joiner.
40 const unsigned int CHAR_LTRM = 0x200E; ///< Left to Right Mark.
41 const unsigned int CHAR_RTLM = 0x200F; ///< Right to Left Mark.
42 const unsigned int CHAR_TS   = 0x2009; ///< Thin Space.
43 } // namespace
44
45 bool IsRightToLeftScript( Script script )
46 {
47   return ( ( ARABIC == script ) ||
48            ( HEBREW == script ) );
49 }
50
51 Script GetCharacterScript( Character character )
52 {
53   // Latin script:
54   // 0x0000 - 0x007f C0 Controls and Basic Latin
55   // 0x0080 - 0x00ff C1 Controls and Latin-1 Supplement
56   // 0x0100 - 0x017f Latin Extended-A
57   // 0x0180 - 0x024f Latin Extended-B
58   // 0x0250 - 0x02af IPA Extensions
59   // 0x02b0 - 0x02ff Spacing Modifier Letters
60   // 0x1d00 - 0x1d7f Phonetic Extensions
61   // 0x1d80 - 0x1dbf Phonetic Extensions Supplement
62   // 0x1e00 - 0x1eff Latin Extended Additional
63   // 0x2070 - 0x209f Superscripts and Subscripts
64   // 0x2100 - 0x214f Letterlike symbols
65   // 0x2150 - 0x218f Number Forms
66   // 0x2c60 - 0x2c7f Latin Extended-C
67   // 0xa720 - 0xa7ff Latin Extended-D
68   // 0xab30 - 0xab6f Latin Extended-E
69   // 0xfb00 - 0xfb06 Latin Alphabetic Presentation Forms
70   // 0xff00 - 0xffef Halfwidth and Fullwidth Forms
71
72   // Brahmic scripts:
73   // 0x0900 - 0x097f Devanagari
74   // 0x0980 - 0x09ff Bengali
75   // 0x0a00 - 0x0a7f Gurmukhi
76   // 0x0a80 - 0x0aff Gujarati
77   // 0x0b00 - 0x0b7f Oriya
78   // 0x0b80 - 0x0bff Tamil
79   // 0x0c00 - 0x0c7f Telugu
80   // 0x0c80 - 0x0cff Kannada
81   // 0x0d00 - 0x0d7f Malayalam
82
83   // Sinhala script.
84   // 0x0d80 - 0x0dff Sinhala
85
86   // Arabic script.
87   // 0x0600 - 0x06ff Arabic
88   // 0x0750 - 0x077f Arabic Supplement
89   // 0x08A0 - 0x08ff Arabic Extended-A
90   // 0xfb50 - 0xfdff Arabic Presentation Forms-A
91   // 0xfe70 - 0xfeff Arabic Presentation Forms-B
92   // 0x1ee00 - 0x1eeff Arabic Mathematical Alphabetic Symbols
93
94   // CJK (Chinese, Japanese and Korean) and Vietnamese script.
95   // 0x2e80 - 0x2eff CJK Radicals Supplement
96   // 0x2f00 - 0x2fdf Kangxi Radicals
97   // 0x3000 - 0x303f CJK Symbols and Punctuation
98   // 0x3200 - 0x32ff Enclosed CJK Letters and Months
99   // 0x3400 - 0x4dbf CJK Unified Ideographs Extension A
100   // 0x4e00 - 0x62ff CJK Unified Ideographs
101   // 0x6300 - 0x77ff CJK Unified Ideographs
102   // 0x7800 - 0x8cff CJK Unified Ideographs
103   // 0x8d00 - 0x9fff CJK Unified Ideographs
104   // 0x20000 - 0x215ff CJK Unified Ideographs Extension B
105   // 0x21600 - 0x230ff CJK Unified Ideographs Extension B
106   // 0x23100 - 0x245ff CJK Unified Ideographs Extension B
107   // 0x24600 - 0x260ff CJK Unified Ideographs Extension B
108   // 0x26100 - 0x275ff CJK Unified Ideographs Extension B
109   // 0x27600 - 0x290ff CJK Unified Ideographs Extension B
110   // 0x29100 - 0x2a6df CJK Unified Ideographs Extension B
111   // 0x2a700 - 0x2b73f CJK Unified Ideographs Extension C
112   // 0x2b740 - 0x2b81f CJK Unified Ideographs Extension D
113
114   // Japanese scripts.
115   // 0x3040 - 0x309f Hiragana
116   // 0x30a0 - 0x30ff Katakana
117
118   // Hangul script
119   // 0x1100 - 0x11ff Hangul jamo
120   // 0x3130 - 0x318f Hangul Compatibility Jamo
121   // 0xa960 - 0xa97f Hangul Jamo Extended-A
122   // 0xac00 - 0xd7af Hangul Syllables
123   // 0xd7b0 - 0xd7ff Hangul Jamo Extended-B
124
125   // Khmer script
126   // 0x1780 - 0x17ff Khmer
127   // 0x19e0 - 0x19ff Khmer Symbols
128
129   // Lao script
130   // 0x0e80 - 0x0eff Lao
131
132   // Thai script
133   // 0x0e00 - 0x0e7f Thai
134
135   // Burmese script
136   // 0x1000 - 0x109f Myanmar
137
138   // Hebrew script
139   // 0x0591 - 0x05f4 Hebrew
140   // 0xfb1d - 0xfb4f Hebrew subset of Alphabetic Presentation Forms
141
142   // Cyrillic script
143   // 0x0400 - 0x04ff Cyrillic
144   // 0x0500 - 0x052f Cyrillic suplement
145   // 0x2de0 - 0x2dff Cyrillic Extended-A
146   // 0xa640 - 0xa69f Cyrillic Extended-B
147
148   // Georgian script
149   // 0x10a0 - 0x10ff Georgian
150   // 0x2d00 - 0x2d2f Georgian suplement
151
152   // Greek script
153   // 0x0370 - 0x03ff Greek & Coptic
154   // 0x1f00 - 0x1fff Greek Extended
155
156   // Armenian script
157   // 0x0530 - 0x058f Armenian
158   // 0xfb13 - 0xfb17 Armenian subset of Alphabetic prefentation forms
159
160   // The Emoji which map to standardized Unicode characters
161   // 1. Emoticons ( 1F601 - 1F64F )
162   // 2. Dingbats ( 2702 - 27B0 )
163   // 3. Transport and map symbols ( 1F680 - 1F6C0 )
164   // 4. Enclosed characters ( 24C2 - 1F251 )
165   // 5. Uncategorized :-S
166   // 6. Additional Emoticons ( 1F600 - 1F636 )
167   // 6b. Additional transport and map symbols ( 1F681 - 1F6C5 )
168   // 6c. Other additional symbols ( 1F30D - 1F567 )
169
170   if( character <= 0x0cff )
171   {
172     if( character <= 0x09ff )
173     {
174       if( character <= 0x077f )
175       {
176         if( character == 0x00A9 )
177         {
178           return EMOJI; // 5. Uncategorized: copyright sign
179         }
180         if( character == 0x00AE )
181         {
182           return EMOJI; // 5. Uncategorized: registered sign
183         }
184         if( character <= 0x02ff )
185         {
186           return LATIN;
187         }
188         if( ( 0x0370 <= character ) && ( character <= 0x03ff ) )
189         {
190           return GREEK;
191         }
192         if( ( 0x0400 <= character ) && ( character <= 0x04ff ) )
193         {
194           return CYRILLIC;
195         }
196         if( ( 0x0500 <= character ) && ( character <= 0x052f ) )
197         {
198           return CYRILLIC;
199         }
200         if( ( 0x0530 <= character ) && ( character <= 0x058f ) )
201         {
202           return ARMENIAN;
203         }
204         if( ( 0x0591 <= character ) && ( character <= 0x05f4 ) )
205         {
206           return HEBREW;
207         }
208         if( ( 0x0600 <= character ) && ( character <= 0x06ff ) )
209         {
210           return ARABIC;
211         }
212         if( ( 0x0750 <= character ) && ( character <= 0x077f ) )
213         {
214           return ARABIC;
215         }
216       }
217       else // > 0x077f
218       {
219         if( ( 0x08A0 <= character ) && ( character <= 0x08ff ) )
220         {
221           return ARABIC;
222         }
223         if( ( 0x0900 <= character ) && ( character <= 0x097f ) )
224         {
225           return DEVANAGARI;
226         }
227         if( ( 0x0980 <= character ) && ( character <= 0x09ff ) )
228         {
229           return BENGALI;
230         }
231       }
232     }
233     else // > 0x09ff
234     {
235       if( character <= 0x0b7f )
236       {
237         if( ( 0x0a00 <= character ) && ( character <= 0x0a7f ) )
238         {
239           return GURMUKHI;
240         }
241         if( ( 0x0a80 <= character ) && ( character <= 0x0aff ) )
242         {
243           return GUJARATI;
244         }
245         if( ( 0x0b00 <= character ) && ( character <= 0x0b7f ) )
246         {
247           return ORIYA;
248         }
249       }
250       else // > 0x0b7f
251       {
252         if( ( 0x0b80 <= character ) && ( character <= 0x0bff ) )
253         {
254           return TAMIL;
255         }
256         if( ( 0x0c00 <= character ) && ( character <= 0x0c7f ) )
257         {
258           return TELUGU;
259         }
260         if( ( 0x0c80 <= character ) && ( character <= 0x0cff ) )
261         {
262           return KANNADA;
263         }
264       }
265     }
266   }
267   else // > 0x0cff
268   {
269     if( character <= 0x2c7f )
270     {
271       if( character <= 0x1eff )
272       {
273         if( ( 0x0d00 <= character ) && ( character <= 0x0d7f ) )
274         {
275           return MALAYALAM;
276         }
277         if( ( 0x0d80 <= character ) && ( character <= 0x0dff ) )
278         {
279           return SINHALA;
280         }
281         if( ( 0x0e00 <= character ) && ( character <= 0x0e7f ) )
282         {
283           return THAI;
284         }
285         if( ( 0x0e80 <= character ) && ( character <= 0x0eff ) )
286         {
287           return LAO;
288         }
289         if( ( 0x1000 <= character ) && ( character <= 0x109f ) )
290         {
291           return BURMESE;
292         }
293         if( ( 0x10a0 <= character ) && ( character <= 0x10ff ) )
294         {
295           return GEORGIAN;
296         }
297         if( ( 0x1100 <= character ) && ( character <= 0x11ff ) )
298         {
299           return HANGUL;
300         }
301         if( ( 0x1780 <= character ) && ( character <= 0x17ff ) )
302         {
303           return KHMER;
304         }
305         if( ( 0x19e0 <= character ) && ( character <= 0x19ff ) )
306         {
307           return KHMER;
308         }
309         if( ( 0x1d00 <= character ) && ( character <= 0x1eff ) )
310         {
311           return LATIN;
312         }
313       }
314       else // > 0x1eff
315       {
316         if( ( 0x1f00 <= character ) && ( character <= 0x1fff ) )
317         {
318           return GREEK;
319         }
320         if( character == 0x203c )
321         {
322           return EMOJI; // 5. Uncategorized: double exclamation mark
323         }
324         if( character == 0x2049 )
325         {
326           return EMOJI; // 5. Uncategorized: exclamation question mark
327         }
328         if( ( 0x2070 <= character ) && ( character <= 0x209f ) )
329         {
330           return LATIN;
331         }
332         if( character == 0x20e3 )
333         {
334           return EMOJI; // 5. Uncategorized: combining enclosing keycap
335         }
336         if( character == 0x2122 )
337         {
338           return EMOJI; // 5. Uncategorized: trade mark sign
339         }
340         if( character == 0x2139 )
341         {
342           return EMOJI; // 5. Uncategorized: information source
343         }
344         if( ( 0x2100 <= character ) && ( character <= 0x218f ) )
345         {
346           return LATIN;
347         }
348         // U+2194 5. Uncategorized: left right arrow
349         // U+2B55 5. Uncategorized: heavy large circle
350         if( ( 0x2194 <= character ) && ( character <= 0x2B55 ) )
351         {
352           return EMOJI;
353         }
354         if( ( 0x2c60 <= character ) && ( character <= 0x2c7f ) )
355         {
356           return LATIN;
357         }
358       }
359     }
360     else // > 0x2c7f
361     {
362       if( character <= 0xfdff )
363       {
364         if( ( 0x2d00 <= character ) && ( character <= 0x2d2f ) )
365         {
366           return GEORGIAN;
367         }
368         if( ( 0x2de0 <= character ) && ( character <= 0x2dff ) )
369         {
370           return CYRILLIC;
371         }
372         if( ( 0x2e80 <= character ) && ( character <= 0x2eff ) )
373         {
374           return CJK;
375         }
376         if( ( 0x2f00 <= character ) && ( character <= 0x2fdf ) )
377         {
378           return CJK;
379         }
380         if( ( 0x3000 <= character ) && ( character <= 0x303f ) )
381         {
382           return CJK;
383         }
384         if( ( 0x3040 <= character ) && ( character <= 0x309f ) )
385         {
386           return HIRAGANA;
387         }
388         if( ( 0x30a0 <= character ) && ( character <= 0x30ff ) )
389         {
390           return KATAKANA;
391         }
392         if( ( 0x3130 <= character ) && ( character <= 0x318f ) )
393         {
394           return HANGUL;
395         }
396         if( ( 0x3200 <= character ) && ( character <= 0x32ff ) )
397         {
398           return CJK;
399         }
400         if( ( 0x3400 <= character ) && ( character <= 0x4dbf ) )
401         {
402           return CJK;
403         }
404         if( ( 0x4e00 <= character ) && ( character <= 0x62ff ) )
405         {
406           return CJK;
407         }
408         if( ( 0x6300 <= character ) && ( character <= 0x77ff ) )
409         {
410           return CJK;
411         }
412         if( ( 0x7800 <= character ) && ( character <= 0x8cff ) )
413         {
414           return CJK;
415         }
416         if( ( 0x8d00 <= character ) && ( character <= 0x9fff ) )
417         {
418           return CJK;
419         }
420         if( ( 0xa640 <= character ) && ( character <= 0xa69f ) )
421         {
422           return CYRILLIC;
423         }
424         if( ( 0xa720 <= character ) && ( character <= 0xa7ff ) )
425         {
426           return LATIN;
427         }
428         if( ( 0xa960 <= character ) && ( character <= 0xa97f ) )
429         {
430           return HANGUL;
431         }
432         if( ( 0xab30 <= character ) && ( character <= 0xab6f ) )
433         {
434           return LATIN;
435         }
436         if( ( 0xac00 <= character ) && ( character <= 0xd7af ) )
437         {
438           return HANGUL;
439         }
440         if( ( 0xd7b0 <= character ) && ( character <= 0xd7ff ) )
441         {
442           return HANGUL;
443         }
444         if( ( 0xfb00 <= character ) && ( character <= 0xfb06 ) )
445         {
446           return LATIN;
447         }
448         if( ( 0xfb13 <= character ) && ( character <= 0xfb17 ) )
449         {
450           return ARMENIAN;
451         }
452         if( ( 0xfb1d <= character ) && ( character <= 0xfb4f ) )
453         {
454           return HEBREW;
455         }
456         if( ( 0xfb50 <= character ) && ( character <= 0xfdff ) )
457         {
458           return ARABIC;
459         }
460       }
461       else // > 0xfdff
462       {
463         if( ( 0xfe70 <= character ) && ( character <= 0xfeff ) )
464         {
465           return ARABIC;
466         }
467         if( ( 0xff00 <= character ) && ( character <= 0xffef ) )
468         {
469           return LATIN;
470         }
471         if( ( 0x1ee00 <= character ) && ( character <= 0x1eeff ) )
472         {
473           return ARABIC;
474         }
475         // U+1f170 4. Enclosed characters: negative squared latin capital letter A
476         // U+1f6c5 6b. Additional transport and map symbols
477         if( ( 0x1f170 <= character ) && ( character <= 0x1f6c5 ) )
478         {
479           return EMOJI;
480         }
481         if( ( 0x20000 <= character ) && ( character <= 0x215ff ) )
482         {
483           return CJK;
484         }
485         if( ( 0x21600 <= character ) && ( character <= 0x230ff ) )
486         {
487           return CJK;
488         }
489         if( ( 0x23100 <= character ) && ( character <= 0x245ff ) )
490         {
491           return CJK;
492         }
493         if( ( 0x24600 <= character ) && ( character <= 0x260ff ) )
494         {
495           return CJK;
496         }
497         if( ( 0x26100 <= character ) && ( character <= 0x275ff ) )
498         {
499           return CJK;
500         }
501         if( ( 0x27600 <= character ) && ( character <= 0x290ff ) )
502         {
503           return CJK;
504         }
505         if( ( 0x29100 <= character ) && ( character <= 0x2a6df ) )
506         {
507           return CJK;
508         }
509         if( ( 0x2a700 <= character ) && ( character <= 0x2b73f ) )
510         {
511           return CJK;
512         }
513         if( ( 0x2b740 <= character ) && ( character <= 0x2b81f ) )
514         {
515           return CJK;
516         }
517       }
518     }
519   }
520
521   return UNKNOWN;
522 }
523
524 bool IsWhiteSpace( Character character )
525 {
526   return character < WHITE_SPACE_THRESHOLD;
527 }
528
529 bool IsNewParagraph( Character character )
530 {
531   return ( ( CHAR_FL == character )  ||
532            ( CHAR_VT == character )  ||
533            ( CHAR_FF == character )  ||
534            ( CHAR_NEL == character ) ||
535            ( CHAR_LS == character )  ||
536            ( CHAR_PS == character ) );
537 }
538
539 bool IsZeroWidthNonJoiner( Character character )
540 {
541   return CHAR_ZWNJ == character;
542 }
543
544 bool IsZeroWidthJoiner( Character character )
545 {
546   return CHAR_ZWJ == character;
547 }
548
549 bool IsZeroWidthSpace( Character character )
550 {
551   return CHAR_ZWS == character;
552 }
553
554 bool IsLeftToRightMark( Character character )
555 {
556   return CHAR_LTRM == character;
557 }
558
559 bool IsRightToLeftMark( Character character )
560 {
561   return CHAR_RTLM == character;
562 }
563
564 bool IsThinSpace( Character character )
565 {
566   return CHAR_TS == character;
567 }
568
569 } // namespace TextAbstraction
570
571 } // namespace Dali