fix(run): draw the lane console through the canvas renderer

Scrolling a console left stray characters glued to the left edge of blank
lines. Copying an affected line yields clean text, so the buffer was always
correct — only the painting drifted, which no CSS can correct.

xterm's default DOM renderer aligns each row with a single `letter-spacing`
value. That holds only while every glyph comes from one monospace font, and
TerminalView passed no fontFamily, so xterm used its default
`courier-new, courier, monospace`: Vietnamese diacritics and CJK fall
through to a fallback face whose advance width differs, glyphs shove their
neighbours along, and the row's tail spills onto the row below.

The canvas renderer draws every cell at a fixed position, so a wide glyph
can no longer displace its neighbours. Loaded best-effort — a browser that
cannot hand back a 2D context keeps the DOM renderer rather than losing the
terminal entirely.

Ruled out first, each by replaying the real byte stream into xterm.js and
diffing against `tmux capture-pane`: wrapped Vietnamese at the margin, mixed
CJK, wheel scrolling through copy-mode, and a live 131->95->131 resize all
render byte-identically at matched widths.

client 448/448, tsc clean.
This commit is contained in:
2026-08-28 10:44:17 +07:00
parent ce5eadba89
commit cc4e71c127
4 changed files with 49 additions and 1 deletions
+1
View File
@@ -13,6 +13,7 @@
"dependencies": {
"@fontsource/inter": "^5.2.8",
"@fontsource/jetbrains-mono": "^5.2.8",
"@xterm/addon-canvas": "^0.7.0",
"@xterm/addon-fit": "^0.10.0",
"@xterm/xterm": "^5.5.0",
"d3": "^7.9.0",