T1 true tritone
Fully riso, zero hue loss. Three plates mapped straight onto #170f0d / #b7775b / #f8d7bc. Reads as a two-colour screen print and still reads as you. The most stylised of the four and the most honest to the medium.
capad.fyi · hero · riso, likeness first
That was not a taste disagreement, it was a bug, and it is measurable. The
old treatment ran grayscale(1) contrast(1.5) brightness(.6) and then
multiplied three plates together. Your face is 50.4% saturated, so
grayscale(1) threw away exactly half the colour information in it,
brightness(.6) pulled the key plate down, and multiply
darkened again at every layer. Skin lives in the midtones, so skin suffers most.
A generic ink palette cannot fix that. Yours can.
So the palette is now sampled off the photograph rather than invented: #170f0d deep shadow, #7a4634 shadow, #b7775b midtone skin, #e4a584 light, #f8d7bc highlight. Everything below is built from those five values. Nothing is greyed out.
Same riso idea, four different relationships between "this is a screen print" and "this is a photograph of a person". All four keep hue. The question is only how much of the original survives underneath.
T1 true tritone
Fully riso, zero hue loss. Three plates mapped straight onto #170f0d / #b7775b / #f8d7bc. Reads as a two-colour screen print and still reads as you. The most stylised of the four and the most honest to the medium.
T2 one warm ink
Maximum likeness. The photo is the base, untouched. A single warm plate takes ink in the shadows and is a no-op on highlights, because its bright end is white and white multiplies to nothing. The misregistration fringe lands on your silhouette and nowhere else.
T3 halftone, shadows only
The halftone you asked for, rebuilt. A shadow plate whose alpha comes from luminance, screened at two frequencies so the dots interfere the way two misaligned screens do. You get the texture without losing the face.
T4 photocopy chew, in colour
The chew you liked, without the ink crush. One displacement filter eroding the alpha edge, colour untouched. Cheap in effect, and unlike the halftone it costs nothing at render time once rasterised. The ragged edge is the whole idea here.
| Likeness | T4 keeps all of it. T2 nearly all. T3 all of it above the midtones. T1 is the biggest departure and still carries your hue. |
|---|---|
| Reads as riso | T1 most, T3 next, T2 least, T4 not really — T4 reads as photocopy, which is a different and equally good excuse. |
| Cost | T1 and T2 are one static filter each. T3 is one filter plus two masks. T4 is one displacement filter, which is per-pixel but only rasterises once while static. |
| Combines with drag | All four. T2 and T3 gain the most from it, because their second plate is offset independently. |
One continuous surface at 1440px: hero, work, testimonials, contact. The paper value and the film grain do not change at a section boundary, so every fold below is carried by motion rather than by a background swap. That is the constraint that shapes all three.
| Fold 1 | The print settles as it leaves. The riso misregistration eases toward zero as the hero scrolls up, and drifts again when you scroll back. The print appears to be pulled into register by leaving. One custom property, already written, no new work. |
|---|---|
| Fold 2 | Nothing happens, on purpose. The project cards and the testimonial deck are the same material — translucent white, 1px light border, the same shadow. A reader crossing the boundary should not perceive a change, and the dot rail is the only persistent element that tells them where they are. |
| Fold 3 | The card becomes the panel. The deck's front card and the contact panel are one shared .glass surface, so the contact widget can expand the card in place rather than cross-fade into a new one. This is the fold most likely to feel cheap if faked with opacity, so it wants a real shared element. |
| The grain | One fixed overlay for the whole document, never re-created per section. That is what stops the folds reading as seams. It is also the single most expensive thing on the page under a software rasteriser, which is the open perf question. |
You picked both, so here they are in one panel: the inks lean toward the pointer, and grabbing the plate lets you pull the registration apart or push it home. The two compose rather than compete — the pointer sets where you are looking, the drag sets what you are correcting.
LIVE — try it
Move the pointer and the shadow plate leans after it. Press and drag horizontally and you take over the registration directly. Let go near zero and it locks. Everything is one custom property; there is no second code path.
what it costs
| Per move | One getBoundingClientRect per pointer event on the plate, and one custom-property write. No layout read after the first, no class churn, no filter re-run beyond what the offset already forces. |
|---|---|
| Per frame | Nothing scheduled. There is no rAF loop in this behaviour at all, which is why it does not compete with the testimonials deck for budget. |
| Touch | touch-action:pan-y so a vertical swipe still scrolls the page and only a horizontal drag is captured. A drag that fights the scroller is worse than no drag. |
| Reduced motion | The pointer lean is a direct response to a direct pointer, so it stays. The idle breathing does not. A drag that did nothing would be a broken control. |
| The honest risk | Both behaviours write the same property, so on a touch device a horizontal drag to register is one gesture away from a back-swipe. That is a real conflict and it needs testing on hardware, not in a mockup. |