diff --git a/terminal.h b/terminal.h index 45c6c98b..83406f41 100644 --- a/terminal.h +++ b/terminal.h @@ -87,6 +87,7 @@ struct damage { struct composed { wchar_t chars[20]; uint8_t count; + int width; }; struct row_uri_range { diff --git a/util.h b/util.h index af215111..aa9fc8ba 100644 --- a/util.h +++ b/util.h @@ -35,11 +35,3 @@ sdbm_hash(const char *s) return hash; } - -#include -static inline int -my_wcswidth(const wchar_t *s, size_t n) -{ - int ret = wcswidth(s, n); - return max(0, ret); -} diff --git a/vt.c b/vt.c index 496333d7..6ad539d7 100644 --- a/vt.c +++ b/vt.c @@ -716,9 +716,8 @@ action_utf8_print(struct terminal *term, wchar_t wc) if (cc->chars[wanted_count - 1] != wc) continue; - int grapheme_width = my_wcswidth(cc->chars, cc->count); - if (grapheme_width > 0) - term_print(term, CELL_COMB_CHARS_LO + i, grapheme_width); + if (cc->width > 0) + term_print(term, CELL_COMB_CHARS_LO + i, cc->width); return; } @@ -732,11 +731,18 @@ action_utf8_print(struct terminal *term, wchar_t wc) new_cc.chars[wanted_count - 1] = wc; if (term->composed_count < CELL_COMB_CHARS_HI) { + /* TODO: grapheme cluster width */ + int grapheme_width = wcswidth(new_cc.chars, new_cc.count); + if (new_cc.chars[new_cc.count - 1] == 0xfe0f) { + /* Emoji selector */ + grapheme_width = 2; + } + new_cc.width = grapheme_width; + term->composed_count++; term->composed = xrealloc(term->composed, term->composed_count * sizeof(term->composed[0])); term->composed[term->composed_count - 1] = new_cc; - int grapheme_width = my_wcswidth(new_cc.chars, new_cc.count); if (grapheme_width > 0) term_print(term, CELL_COMB_CHARS_LO + term->composed_count - 1, grapheme_width); return;