Skip to content
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
added ImCharIsLineBreakableW to check whether this char can break any…
…where.
  • Loading branch information
cyx2015s committed Jul 27, 2025
commit c75a83bfd20014027779a7cca9a9cda7013057e5
22 changes: 11 additions & 11 deletions imgui_draw.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5381,8 +5381,8 @@ const char* ImFont::CalcWordWrapPosition(float size, const char* text, const cha
const char* word_end = text;
const char* prev_word_end = NULL;
bool inside_word = true;
bool last_char_is_cjk = false;
bool last_char_is_init = false;
bool last_char_is_line_breakable = false;
bool last_char_is_tail_prohibited = false;

const char* s = text;
IM_ASSERT(text_end != NULL);
Expand Down Expand Up @@ -5426,8 +5426,8 @@ const char* ImFont::CalcWordWrapPosition(float size, const char* text, const cha
}
blank_width += char_width;
inside_word = false;
last_char_is_cjk = false;
last_char_is_init = false;
last_char_is_line_breakable = false;
last_char_is_tail_prohibited = false;
}
else if (ImCharIsHeadProhibitedW(c))
{
Expand All @@ -5438,8 +5438,8 @@ const char* ImFont::CalcWordWrapPosition(float size, const char* text, const cha
inside_word = false;
// Wrap after this punctuation.
prev_word_end = word_end = next_s;
last_char_is_cjk = false;
last_char_is_init = false;
last_char_is_line_breakable = false;
last_char_is_tail_prohibited = false;
}
else
{
Expand All @@ -5451,26 +5451,26 @@ const char* ImFont::CalcWordWrapPosition(float size, const char* text, const cha
prev_word_end = word_end;
word_end = next_s;
}
else if (0x3003 <= c && c <= 0xFFFF)
else if (ImCharIsLineBreakableW(c))
{
// CJK characters are not separated by spaces, so we treat them as a single word.
// This is a very simple heuristic, but it works for most cases.
line_width += word_width + blank_width;
word_width = blank_width = 0.0f;
inside_word = true;
if ((!last_char_is_init && 0x3003 <= c && c <= 0xFFFF) || !last_char_is_cjk)
if ((!last_char_is_tail_prohibited && ImCharIsLineBreakableW(c)) || !last_char_is_line_breakable)
prev_word_end = s;
}
else if (!ImCharIsHeadProhibitedW(c) && last_char_is_cjk && !last_char_is_init)
else if (!ImCharIsHeadProhibitedW(c) && last_char_is_line_breakable && !last_char_is_tail_prohibited)
{
// Not a cjk character, not a head prohibited punctuation, previous char is not tail prohibited.
line_width += word_width + blank_width;
word_width = blank_width = 0.0f;
prev_word_end = s;
inside_word = true;
}
last_char_is_cjk = 0x3003 <= c && c <= 0xFFFF;
last_char_is_init = ImCharIsTailProhibitedW(c);
last_char_is_line_breakable = ImCharIsLineBreakableW(c);
last_char_is_tail_prohibited = ImCharIsTailProhibitedW(c);
word_width += char_width;
if (inside_word)
{
Expand Down
1 change: 1 addition & 0 deletions imgui_internal.h
Original file line number Diff line number Diff line change
Expand Up @@ -409,6 +409,7 @@ inline bool ImCharIsHeadProhibitedW(unsigned int c) { return c ==
// Only include characters can be typed within 1 or 2 hits on a standard keyboard.
// List: (【《「『
inline bool ImCharIsTailProhibitedW(unsigned int c) { return c == 0xff08 || c == 0x3010 || c == 0x300a || c == 0x300c || c == 0x300e; }
inline bool ImCharIsLineBreakableW(unsigned int c) { return (c >= 0x4E00 && c <= 0x9FFF) || (c >= 0x3400 && c <= 0x4DBF) || (c >= 0x20000 && c <= 0x2EBEF) || (c >= 0x3040 && c <= 0x30FF) || (c >= 0xAC00 && c <= 0xD7AF); }
inline bool ImCharIsXdigitA(char c) { return (c >= '0' && c <= '9') || (c >= 'A' && c <= 'F') || (c >= 'a' && c <= 'f'); }
IM_MSVC_RUNTIME_CHECKS_RESTORE

Expand Down