fix(desktop): paint an opaque ground under the Buzz Term splash

paintTerminalBanner cleared the overlay canvas and drew glyphs, with no
background fill, and .buzz-terminal-welcome sets no CSS background. On a
real 111x46 viewport the banner covers about 38% of cells, so the grid
canvas underneath showed through the gaps. That was invisible while the
shell prompt dismissed the banner within milliseconds of spawn; now that
the splash survives until the terminal is revealed, the shell's startup
output composites into the wordmark.

Fill the overlay with palette.background before the glyph loop. Same
theme source the grid uses for its own cell background, so the splash
reads as an opaque screen instead of a translucent layer.

Co-authored-by: npub17jjz49l9jjmhhk7cac63j8yt9z555n9cw8vk7v5jz4vzw4ppld5qgj57cc <f4a42a97e594b77bdbd8ee35191c8b28a94a4cb871d96f32921558275421fb68@buzz.block.builderlab.xyz>
Signed-off-by: npub17jjz49l9jjmhhk7cac63j8yt9z555n9cw8vk7v5jz4vzw4ppld5qgj57cc <f4a42a97e594b77bdbd8ee35191c8b28a94a4cb871d96f32921558275421fb68@buzz.block.builderlab.xyz>
This commit is contained in:
npub17jjz49l9jjmhhk7cac63j8yt9z555n9cw8vk7v5jz4vzw4ppld5qgj57cc
2026-08-02 17:34:39 -04:00
parent ee862deb20
commit 17fd17df54
2 changed files with 23 additions and 0 deletions
@@ -33,11 +33,15 @@ function canvas() {
const draws = [];
const clears = [];
const colors = [];
const fills = [];
const context = {
_fillStyle: "",
clearRect(...args) {
clears.push(args);
},
fillRect(...args) {
fills.push({ args, color: this._fillStyle, glyphsBefore: draws.length });
},
fillText(...args) {
draws.push(args);
colors.push(this._fillStyle);
@@ -62,6 +66,7 @@ function canvas() {
clears,
colors,
draws,
fills,
};
}
@@ -80,6 +85,19 @@ test("paints every emitted banner glyph at terminal cell coordinates", () => {
assert.deepEqual(target.clears, [[0, 0, 1000, 600]]);
});
test("lays an opaque theme background under the banner before any glyph", () => {
const banner = buildTerminalBanner(112, 46, 17 / 8.4);
assert.ok(banner);
const target = canvas();
assert.equal(paintTerminalBanner(target.canvas, banner, palette, 2), true);
assert.equal(target.fills.length, 1);
const [ground] = target.fills;
assert.deepEqual(ground.args, [0, 0, 1000, 600]);
assert.equal(ground.color, palette.background);
assert.equal(ground.glyphsBefore, 0);
assert.ok(target.draws.length > 0);
});
test("uses visibly distinct theme-derived colors across banner layers", () => {
const banner = buildTerminalBanner(112, 46, 17 / 8.4);
assert.ok(banner);
@@ -19,6 +19,11 @@ export function paintTerminalBanner(
if (!context) return false;
context.setTransform(dpr, 0, 0, dpr, 0, 0);
context.clearRect(0, 0, bounds.width, bounds.height);
// The overlay sits above the grid canvas, so it needs its own opaque
// ground: without one the shell output painted underneath shows through
// the gaps between banner glyphs.
context.fillStyle = palette.background;
context.fillRect(0, 0, bounds.width, bounds.height);
context.font = TERMINAL_CELL_METRICS.font;
context.textBaseline = "alphabetic";