2 * widechar_width.h for Unicode 15.0.0
3 * See https://github.com/ridiculousfish/widecharwidth/
7 * the hashes for generate.py and the template are git object hashes,
8 * use `git log --all --find-object=<hash>` in the widecharwidth repository
9 * to see which commit they correspond to,
10 * or run `git hash-object` on the file to compare.
11 * The other hashes are simple `sha1sum` style hashes.
14 * generate.py: 1d24de5a7caf6e8cc4e5a688ea83db972efe4538
15 * template.js: 1249763c5b7c1e308aeb4ca64f1e15bce1fab9b3
16 * UnicodeData.txt: 3e1900295af0978ad6be3153de4c97d55198ab4b
17 * EastAsianWidth.txt: 2637ce61d024cb25c768023fa4d7594b53474919
18 * emoji-data.txt: 7754a51be6ebe38f906e4fe948720e0f3b78bfd7
21 #ifndef WIDECHAR_WIDTH_H
22 #define WIDECHAR_WIDTH_H
31 /* Special width values */
33 widechar_nonprint
= -1, // The character is not printable.
34 widechar_combining
= -2, // The character is a zero-width combiner.
35 widechar_ambiguous
= -3, // The character is East-Asian ambiguous width.
36 widechar_private_use
= -4, // The character is for private use.
37 widechar_unassigned
= -5, // The character is unassigned.
38 widechar_widened_in_9
= -6, // Width is 1 in Unicode 8, 2 in Unicode 9+.
39 widechar_non_character
= -7 // The character is a noncharacter.
42 /* An inclusive range of characters. */
43 struct widechar_range
{
48 /* Simple ASCII characters - used a lot, so we check them first. */
49 static const struct widechar_range widechar_ascii_table
[] = {
53 /* Private usage range. */
54 static const struct widechar_range widechar_private_table
[] = {
60 /* Nonprinting characters. */
61 static const struct widechar_range widechar_nonprint_table
[] = {
88 /* Width 0 combining marks. */
89 static const struct widechar_range widechar_combining_table
[] = {
402 /* Width 0 combining letters. */
403 static const struct widechar_range widechar_combiningletters_table
[] = {
408 /* Width 2 characters. */
409 static const struct widechar_range widechar_doublewide_table
[] = {
484 /* Ambiguous-width characters. */
485 static const struct widechar_range widechar_ambiguous_table
[] = {
667 /* Unassigned characters. */
668 static const struct widechar_range widechar_unassigned_table
[] = {
1397 /* Non-characters. */
1398 static const struct widechar_range widechar_nonchar_table
[] = {
1416 {0x10FFFE, 0x10FFFF}
1419 /* Characters that were widened from width 1 to 2 in Unicode 9. */
1420 static const struct widechar_range widechar_widened_table
[] = {
1489 template<typename Collection
>
1490 bool widechar_in_table(const Collection
&arr
, uint32_t c
) {
1491 auto where
= std::lower_bound(std::begin(arr
), std::end(arr
), c
,
1492 [](widechar_range p
, uint32_t c
) { return p
.hi
< c
; });
1493 return where
!= std::end(arr
) && where
->lo
<= c
;
1496 /* Return the width of character c, or a special negative value. */
1497 int widechar_wcwidth(uint32_t c
) {
1498 if (widechar_in_table(widechar_ascii_table
, c
))
1500 if (widechar_in_table(widechar_private_table
, c
))
1501 return widechar_private_use
;
1502 if (widechar_in_table(widechar_nonprint_table
, c
))
1503 return widechar_nonprint
;
1504 if (widechar_in_table(widechar_nonchar_table
, c
))
1505 return widechar_non_character
;
1506 if (widechar_in_table(widechar_combining_table
, c
))
1507 return widechar_combining
;
1508 if (widechar_in_table(widechar_combiningletters_table
, c
))
1509 return widechar_combining
;
1510 if (widechar_in_table(widechar_doublewide_table
, c
))
1512 if (widechar_in_table(widechar_ambiguous_table
, c
))
1513 return widechar_ambiguous
;
1514 if (widechar_in_table(widechar_unassigned_table
, c
))
1515 return widechar_unassigned
;
1516 if (widechar_in_table(widechar_widened_table
, c
))
1517 return widechar_widened_in_9
;
1522 #endif // WIDECHAR_WIDTH_H