Installation
pnpm dlx shadcn@latest add https://dithercn.dev/r/not-found.jsonUsage
import Link from "next/link";
import { DitherButton } from "@/components/dithercn/dither-button";
import { NotFound } from "@/components/dithercn/not-found";
export default function NotFoundPage() {
return (
<main className="grid min-h-svh place-items-center">
<NotFound
actions={
<DitherButton asChild>
<Link href="/">Back to home</Link>
</DitherButton>
}
/>
</main>
);
}The code is set in your page's own font, then rasterised onto a grid of cells and turned into block letters. The faces are densest at the top and thin towards the baseline; the cells behind them, down and to the right, form an extruded side in a sparse dither. On mount the digits print in level by level, and after that a band of light crosses the faces every few seconds.
code, title, description, detail and actions are all yours, so the same block covers 410, 500 and maintenance pages. detail is a short mono line under the text, a good place for the requested path or an error reference.
Examples
Server error
A 500 in red with a reference people can quote to support, and an outline retry button that fills with red hatching on hover.
Inside a card
A missing resource inside the app shell rather than a whole page: grey dotted digits, a shallow side, finer cells and no animation.
Props
| Prop | Type | Default |
|---|---|---|
| code The big code. Any short string works. | Type: string | Default "404" |
| title The heading. | Type: ReactNode | Default "Page not found" |
| description A sentence under the heading. | Type: ReactNode | Default "The link may be broken, or the page may have moved." |
| detail A short mono line, such as the requested path or an error reference. | Type: ReactNode | Default – |
| actions Buttons or links, such as a way home. | Type: ReactNode | Default – |
| titleAs Heading level. Use h1 on a page of its own. | Type: "h1" | "h2" | Default "h1" |
| color A palette name such as "red", a CSS variable name, or any CSS colour. | Type: DitherColor | Default "ink" |
| fill Texture of the digit faces. | Type: "gradient" | "dotted" | "hatched" | "solid" | Default "gradient" |
| bloom A soft glow in the code's colour. | Type: "off" | "low" | "high" | Default "off" |
| cell Size of one dither cell in CSS pixels. | Type: number | Default 4 |
| depth Depth of the extruded side in cells. 0 gives flat digits. | Type: number | Default 4 |
| animate Print the digits in on mount and sweep light across them. | Type: boolean | Default true |
Notes
- The digits are a decorative canvas hidden from assistive technology; the heading carries the message. Put the status in
titleordescriptionif it matters to the reader. - The grid follows the block's width, so the digits fill the space on a phone and stop at 672 pixels wide on a desktop. They are re-set when your web fonts finish loading.
- Under reduced motion, or with
animate={false}, the digits are drawn once, finished. Offscreen and in hidden tabs, the light sweep pauses.