From 42c4f52711ff5ef85d1246ca6f269b0bc728debe Mon Sep 17 00:00:00 2001 From: Mitchell Hashimoto Date: Mon, 20 Nov 2023 19:12:37 -0800 Subject: [PATCH] font: shaper should not look up U+200D for consistent fonts Related to #914 U+200D is the zero-width joiner character used for multi-codepoint Emojis. When faced with a multi-codepoint grapheme, the font shaper must find a font that provides _all codepoints_ consistently. However, U+200D isn't meant to be provided by any font. As a result, the font shaper search ends up iterating over every font looking for a match. --- src/font/shaper/run.zig | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/font/shaper/run.zig b/src/font/shaper/run.zig index d74e86c52..7bc56e2e9 100644 --- a/src/font/shaper/run.zig +++ b/src/font/shaper/run.zig @@ -213,6 +213,7 @@ pub const RunIterator = struct { if (cell.attrs.grapheme) { var it = self.row.codepointIterator(j); while (it.next()) |cp| { + // Do not send presentation modifiers if (cp == 0xFE0E or cp == 0xFE0F) continue; try self.hooks.addCodepoint(cp, @intCast(cluster)); } @@ -269,7 +270,7 @@ pub const RunIterator = struct { while (it.next()) |cp| { // Ignore Emoji ZWJs - if (cp == 0xFE0E or cp == 0xFE0F) continue; + if (cp == 0xFE0E or cp == 0xFE0F or cp == 0x200D) continue; // Find a font that supports this codepoint. If none support this // then the whole grapheme can't be rendered so we return null. @@ -288,7 +289,7 @@ pub const RunIterator = struct { it.reset(); while (it.next()) |cp| { // Ignore Emoji ZWJs - if (cp == 0xFE0E or cp == 0xFE0F) continue; + if (cp == 0xFE0E or cp == 0xFE0F or cp == 0x200D) continue; if (!self.group.group.hasCodepoint(idx, cp, presentation)) break; } else { // If the while completed, then we have a candidate that