term: append zero-width grapheme breaking characters to previous cell

When compiled with grapheme clustering support, zero-width characters
that also are grapheme breaks, were ignored (not stored in the
grid).

When utf8proc says the character is a grapheme break, we try to print
the character to the current cell. But this is only done when width >
0. As a result, zero width grapheme breaks were simply discarded.

This only happens when grapheme clustering is enabled; when disabled,
all zero width characters are appended.

Fix this by also requiring the width to be non-zero when if we should
append the character or not.

Closes #1960
This commit is contained in:
Daniel Eklöf 2025-02-16 07:25:25 +01:00
parent 4abbaf1345
commit 76503fb86a
No known key found for this signature in database
GPG key ID: 5BBD4992C116573F
2 changed files with 5 additions and 1 deletions

View file

@ -112,11 +112,15 @@
enabled ([#1947][1947]).
* Reflow of the cursor (active + saved) when at the end of the line
with a pending wrap (LCF set) ([#1954][1954]).
* Zero-width characters that also are grapheme breaks (e.g. U+200B,
ZERO WIDTH SPACE) being ignored (discarded and never stored in the
grid) ([#1960][1960]).
[1918]: https://codeberg.org/dnkl/foot/issues/1918
[1929]: https://codeberg.org/dnkl/foot/issues/1929
[1947]: https://codeberg.org/dnkl/foot/issues/1947
[1954]: https://codeberg.org/dnkl/foot/issues/1954
[1960]: https://codeberg.org/dnkl/foot/issues/1960
### Security

View file

@ -4153,7 +4153,7 @@ term_process_and_print_non_ascii(struct terminal *term, char32_t wc)
if (grapheme_clustering) {
/* Check if we're on a grapheme cluster break */
if (utf8proc_grapheme_break_stateful(
last, wc, &term->vt.grapheme_state))
last, wc, &term->vt.grapheme_state) && width > 0)
{
term_reset_grapheme_state(term);
goto out;