Fix RichTextLabel auto-wrapping on CJK

(cherry picked from commit 3a591aaeeb)
This commit is contained in:
Haoyu Qiu 2021-06-03 21:49:13 +08:00 committed by Rémi Verschelde
parent 0b594bf3c8
commit 65e14eb8de
No known key found for this signature in database
GPG Key ID: C3336907360768E1
2 changed files with 30 additions and 3 deletions

View File

@ -413,11 +413,17 @@ void Label::regenerate_word_cache() {
if (uppercase)
current = String::char_uppercase(current);
// ranges taken from http://www.unicodemap.org/
// ranges taken from https://en.wikipedia.org/wiki/Plane_(Unicode)
// if your language is not well supported, consider helping improve
// the unicode support in Godot.
bool separatable = (current >= 0x2E08 && current <= 0xFAFF) || (current >= 0xFE30 && current <= 0xFE4F);
//current>=33 && (current < 65||current >90) && (current<97||current>122) && (current<48||current>57);
bool separatable = (current >= 0x2E08 && current <= 0x9FFF) || // CJK scripts and symbols.
(current >= 0xAC00 && current <= 0xD7FF) || // Hangul Syllables and Hangul Jamo Extended-B.
(current >= 0xF900 && current <= 0xFAFF) || // CJK Compatibility Ideographs.
(current >= 0xFE30 && current <= 0xFE4F) || // CJK Compatibility Forms.
(current >= 0xFF65 && current <= 0xFF9F) || // Halfwidth forms of katakana
(current >= 0xFFA0 && current <= 0xFFDC) || // Halfwidth forms of compatibility jamo characters for Hangul
(current >= 0x20000 && current <= 0x2FA1F) || // CJK Unified Ideographs Extension B ~ F and CJK Compatibility Ideographs Supplement.
(current >= 0x30000 && current <= 0x3134F); // CJK Unified Ideographs Extension G.
bool insert_newline = false;
real_t char_width = 0;

View File

@ -384,6 +384,7 @@ int RichTextLabel::_process_line(ItemFrame *p_frame, const Vector2 &p_ofs, int &
l.char_count += text->text.length();
}
bool just_breaked_in_middle = false;
rchar = 0;
FontDrawer drawer(font, Color(1, 1, 1));
while (*c) {
@ -391,6 +392,7 @@ int RichTextLabel::_process_line(ItemFrame *p_frame, const Vector2 &p_ofs, int &
int end = 0;
int w = 0;
int fw = 0;
bool was_separatable = false;
lh = 0;
@ -410,6 +412,25 @@ int RichTextLabel::_process_line(ItemFrame *p_frame, const Vector2 &p_ofs, int &
break; //don't allow lines longer than assigned width
}
// For info about the unicode range, see Label::regenerate_word_cache.
const CharType current = c[end];
const bool separatable = (current >= 0x2E08 && current <= 0x9FFF) || // CJK scripts and symbols.
(current >= 0xAC00 && current <= 0xD7FF) || // Hangul Syllables and Hangul Jamo Extended-B.
(current >= 0xF900 && current <= 0xFAFF) || // CJK Compatibility Ideographs.
(current >= 0xFE30 && current <= 0xFE4F) || // CJK Compatibility Forms.
(current >= 0xFF65 && current <= 0xFF9F) || // Halfwidth forms of katakana
(current >= 0xFFA0 && current <= 0xFFDC) || // Halfwidth forms of compatibility jamo characters for Hangul
(current >= 0x20000 && current <= 0x2FA1F) || // CJK Unified Ideographs Extension B ~ F and CJK Compatibility Ideographs Supplement.
(current >= 0x30000 && current <= 0x3134F); // CJK Unified Ideographs Extension G.
const bool long_separatable = separatable && (wofs - backtrack + w + cw > p_width);
const bool separation_changed = end > 0 && was_separatable != separatable;
if (!just_breaked_in_middle && (long_separatable || separation_changed)) {
just_breaked_in_middle = true;
break;
}
was_separatable = separatable;
just_breaked_in_middle = false;
w += cw;
fw += cw;