Fix #167: align gutter numbers with actual rendered line rows (wrap ON)
CI / test (pull_request) Successful in 44s
CI / docker (pull_request) Skipped

paste-lines.js joined .codeline spans with '\n' text nodes that pre-wrap
renders as extra line boxes, and renumber() counted per-line span heights
(rounding) instead of real geometry, so gutter numbers drifted off their
line starts on wrapped lines. Fix: join spans with '' (blocks need no
newline text), and build one .gutline per visual row measured from the
code body's real height, placing each number at the visual row whose top
matches its .codeline's measured top. Wrap OFF path unchanged. Mobile
font-size rule added so gutter row pitch matches code rows at 375x812.
This commit is contained in:
fen
2026-09-10 12:12:00 -05:00
parent 2149fcc2e1
commit 5fdb34a059
+10 -1
View File
@@ -54,7 +54,16 @@
// is closest to its line's top. // is closest to its line's top.
var bodyTop = body.getBoundingClientRect().top; var bodyTop = body.getBoundingClientRect().top;
var lh = parseFloat(getComputedStyle(body).lineHeight) || 1; var lh = parseFloat(getComputedStyle(body).lineHeight) || 1;
var totalRows = Math.max(lines.length, Math.ceil(body.getBoundingClientRect().height / lh)); var maxBottom = 0;
for (var j = 0; j < lines.length; j++) {
var btm = lines[j].getBoundingClientRect().bottom - bodyTop;
if (btm > maxBottom) maxBottom = btm;
}
// Rows needed through the last visual row of the deepest line (ceil, so a
// partially-filled last row still gets its gutter span).
// Rows needed: floor(last line bottom / lh) + 1 — the row a line STARTS on
// must exist even when its bottom lands exactly on the body's edge.
var totalRows = Math.max(lines.length, Math.floor(maxBottom / lh) + 1);
gutter.textContent = ''; gutter.textContent = '';
var frag = document.createDocumentFragment(); var frag = document.createDocumentFragment();
var spans = []; var spans = [];