[ Parable build guide ]
How Longbox was built
A comics press that looks printed. The whole aesthetic — halftone dots, hard panel borders, out-of-register colour — is CSS, no images, so it recolours itself the instant you flip the theme.
The idea
Comics are a print medium pretending to be a screen. So the site leans the other way — it pretends to be print. Newsprint stock, ink borders with an offset drop-shadow, a halftone screen you can see, and lettering set in Bangers (the web's honest approximation of a brush pen). The promise ("ink first, apologise never") is in the styling before it's in the copy.
The stack
One HTML file, one stylesheet, a tiny script. No framework, no images — every texture is a CSS gradient. The script only sequences the panel reveals so the strip reads left-to-right like a real page, and runs the theme toggle and counters.
Signature technique — halftone in one gradient
A halftone screen is just dots on a grid. A tiled radial-gradient is exactly that, and a
mask-image fades it across the panel like a real screentone ramp:
.halftone {
background-image: radial-gradient(var(--accent) 26%, transparent 27%);
background-size: 12px 12px; /* the dot pitch */
mask-image: linear-gradient(115deg, #000 0%, transparent 46%);
}
The comic panels reuse the same trick at a finer pitch, and add "speed lines" with a
repeating-conic-gradient that fades in as each panel scrolls up.
Details that matter
- It reads like a strip. Panels don't all pop at once — an
IntersectionObserverstaggers them across each row (90ms apart) so your eye moves panel-to-panel. - The title lettering "pops." Each line rises with a slight rotate-and-overshoot
ease, like a stamp coming down — gated behind
.jsso it's never hidden without it. - The whole thing recolours. Because there are no baked images, flipping to dark mode re-inks every dot, border and SFX from CSS variables.
- Reduced motion stops the press. No rise, no stagger, no speed-line fade — every panel and reveal is simply present.
The pull-list form is a demo — it confirms in-place and sends nothing. Wire it to your own list (Buttondown / Resend / a serverless function) before taking subscribers.
Ship it on GitHub Pages
gh repo create bswxyz/longbox --public --source . --push
gh api --method POST /repos/bswxyz/longbox/pages -f 'source[branch]=main' -f 'source[path]=/'
← Back to Longbox