# Fire

Flames rising from the edge of the box, with a hot base, tapering tongues that lick up and tear off, and embers that drift above them, drawn as a dither.

> For the complete documentation index, see [llms.txt](/llms.txt). Markdown variants are available by appending `.md` to any URL or sending an `Accept: text/markdown` header. The dithercn agent skill, for building any dither on the engine, is at [/.well-known/agent-skills/dithercn/SKILL.md](/.well-known/agent-skills/dithercn/SKILL.md).

> **This is an example, not the only option.** It is one component built on the dithercn engine. Install it when it is what you were asked for. For any other look, don't stretch its props to fit: write your own field on `DitherShader` ([Write your own dither](/docs/engine/write-your-own.md)), and read this example's source for technique. Its full source is in [https://dithercn.dev/r/fire.json](https://dithercn.dev/r/fire.json), under `files[].content`.

## Installation [#installation]

```bash
npx shadcn@latest add https://dithercn.dev/r/fire.json
```

## Usage [#usage]

```tsx
import { Fire } from "@/components/dithercn/fire";

export function Hero() {
  return (
    <section className="relative isolate min-h-[480px]">
      <Fire height={0.4} className="absolute inset-0 -z-10" />
      <h1>Your headline</h1>
    </section>
  );
}
```

The fire burns along one edge of the box. Its heat is noise that scrolls away from the edge, stretched upright and swayed from side to side, minus a falloff with height. Where the heat drops to zero the flame ends in a crisp edge, so the tongues taper to tips, split in two and tear off as licks that rise and vanish. Every part of it moves slowly enough that a dot at the edge of a flame seldom turns on more than twice a second, so the fire flickers without flashing.

The palette runs as a heat ramp: the first colour after the paper at the tips and edges, the last in the dense base. With the default palette that is a tint of the ink and then the ink, so it reads as fire printed in one colour. Give it warm colours, such as `["--dither-paper", "red", "orange", <a pale yellow>]`, for flames that glow from deep red at the tips to yellow-white at the base. Each dot takes one of the colours, so the ramp shows as mixed dots rather than blended paint.

Embers rise out of the flames, drift up in the wind and cool towards the first colour as they climb, then wink out each at its own height. Set `embers={0}` to turn them off.

## Examples [#examples]

### Campfire [#campfire]

`spread={0.5}` gathers the fire into one blaze in the middle of the box, tallest at its centre and dying down at its sides. A tall `height`, narrower tongues and more `embers` make it a campfire, in red, orange and a pale yellow core.

```tsx title="examples/fire-campfire.tsx"
import { Fire } from "@/components/dithercn/fire";

export default function FireCampfire() {
  return (
    <Fire
      spread={0.5}
      height={0.85}
      scale={1.6}
      wind={0.1}
      embers={2.2}
      palette={[
        "--dither-paper",
        "red",
        "orange",
        "color-mix(in oklch, var(--dither-color-orange) 35%, oklch(0.95 0.11 95))",
      ]}
      className="absolute inset-0"
    />
  );
}
```

### Behind a headline [#behind-a-headline]

A low `height` keeps the flames in the bottom third of a hero, and the headline sits on clear paper above them. This one uses the default palette, so the fire is drawn in the theme's ink, and leans a little to the left.

```tsx title="examples/fire-headline.tsx"
import { Fire } from "@/components/dithercn/fire";

export default function FireHeadline() {
  return (
    <section className="relative isolate flex size-full flex-col items-center gap-3 px-6 pt-14 text-center sm:pt-20">
      <Fire
        height={0.32}
        scale={1.4}
        wind={-0.2}
        embers={0.6}
        className="absolute inset-0 -z-10"
      />
      <h3 className="max-w-md text-3xl font-medium tracking-[-0.03em] text-balance">
        Ship it before it cools
      </h3>
      <p className="text-muted-foreground max-w-sm text-sm text-pretty">
        At a height of 0.32 the tongues stay in the bottom third, and the embers
        thin out well below the text.
      </p>
    </section>
  );
}
```

## Props [#props]

| Prop | Type | Default | Description |
| --- | --- | --- | --- |
| `height` | `number` | `0.55` | How far up the box the tallest tongues reach, from 0.1 to 1. Embers rise past it. |
| `scale` | `number` | `1` | Width of the tongues. Higher values make more, narrower ones. |
| `spread` | `number` | `1` | How much of the edge burns, from 0.1 to 1. Below 1 the flames gather into one fire in the middle, tallest at its centre. |
| `wind` | `number` | `0.15` | Sideways lean of the flames and embers, from -1 (left) to 1 (right). |
| `embers` | `number` | `1` | How many embers drift up above the flames, from 0 (none) to 3. |
| `intensity` | `number` | `1` | The brightest tone, from 0 to 1. Lower it to sit text on top. |
| `edge` | `"bottom" \| "top"` | `"bottom"` | The edge the fire burns along. With top, the flames hang down from it. |
| `palette` | `[DitherColor, DitherColor, ...DitherColor[]]` | `Paper, a tint of --dither-ink, then --dither-ink` | The paper, then a heat ramp from the tips to the base: palette names such as "red", CSS variable names, or any CSS colour. |
| `matrix` | `"bayer2" \| "bayer4" \| "bayer8" \| "blue-noise"` | `"bayer4"` | The threshold pattern. See Dither engine. |
| `cell` | `number` | `--dither-cell` | Size of one dither cell in CSS pixels. |
| `speed` | `number` | `1` | How fast the flames climb and the embers rise. |
| `animate` | `boolean` | `true` | false stops the motion: a still frame if it starts off, the current frame if it was moving. |
| `className` | `string` | `–` | Size and position. The fire fills this box. |

## Notes [#notes]

* It is decorative and hidden from assistive technology. Put real text on top of it, not inside it.
* With reduced motion turned on, it draws one still frame and stops.
* It does not flash. At the default `speed`, no dot turns on more than three times in any second, and almost every dot at most twice, whatever the other props. Each ember fades in and out over about half a second. A `speed` above 1 makes everything change faster.
* It pauses when scrolled out of view or when the tab is hidden, and releases its WebGL context when far offscreen. Without WebGL it shows a still SVG traced from the shader's own still frame: the flames in three layers from the tip colour to the core colour, the licks torn off above them, and embers.
* It takes five noise samples per cell for the flames, and the colour pass repeats them, at 30 fps and one pixel per dither cell. See [Performance](/docs/engine/performance).