KQ-1144 · SCRATCH/CARD
Scratch Card
A reward under scratch-off foil: the pointer scrapes the foil away with a ragged brush while flakes of the foil that actually came off tumble and fall, and the scrape's sound follows the brush's speed. Once enough is cleared a glint crosses the card, the rest of the foil crumbles behind its front, and the reward settles on the recoil spring with a chime. The foil is a canvas that reads its colours from its own computed style and repaints when the theme changes; before the reveal it is a real button, and Enter or Space sweeps the same brush across the card with the same sound.
Drag across the foil to scratch it off, or press Enter to sweep it all away.
weekly reward · scratch the foil
Install
One command — the source lands in your repo. Or copy it from the Code tab.
$ pnpm dlx shadcn@latest add @kinetiq/scratch-card
Props
- children
- React.ReactNode
- default —
- The reward under the foil. It is inert and hidden from assistive technology until revealed, so it cannot be read or tabbed to through the foil.
- label
- string
- default —
- What is under the foil, e.g. "Weekly reward". The foil button is named "Scratch to reveal: {label}" and the revealed reward is a group with this name.
- revealed / defaultRevealed
- boolean
- default false
- Whether the foil is gone. Setting it back to false lays fresh foil over the reward before the next frame is painted.
- onRevealedChange
- (revealed: boolean) => void
- default —
- Fires with true from the scratch or sweep that cleared enough foil. Controlled, the foil dissolves when the host answers.
- onProgress
- (cleared: number) => void
- default —
- The share of foil cleared, 0 to 1 (two decimals), each time it moves by a whole percent.
- brush
- number
- default 18
- Brush radius in px, 10 to 34: a wider brush clears more per stroke and throws more flakes.
- autoReveal
- number
- default 60
- The percentage cleared, 40 to 80, at which the rest of the foil dissolves by itself.
- flakes
- boolean
- default true
- Flakes of the foil that comes off tumble and fall out of the card. The frame loop runs only while flakes are falling, on screen, in a visible page.
- foil
- "silver" | "gold"
- default "silver"
- The foil's colours, mixed from the theme's ink or warning hue, and the chime's pitch (gold rings a fourth higher).
- sound
- boolean
- default false
- Play the scrape (noise whose pitch and level follow the brush's speed), a paper crinkle for a single dab, and the reveal's chime and shimmer. Nothing plays, and no audio context exists, unless this is on.
- disabled
- boolean
- default false
- Disables the foil button: nothing scratches.
- className
- string
- default —
- Merged onto the card's classes.
| Prop | Type | Default | Description |
|---|---|---|---|
| children | React.ReactNode | — | The reward under the foil. It is inert and hidden from assistive technology until revealed, so it cannot be read or tabbed to through the foil. |
| label | string | — | What is under the foil, e.g. "Weekly reward". The foil button is named "Scratch to reveal: {label}" and the revealed reward is a group with this name. |
| revealed / defaultRevealed | boolean | false | Whether the foil is gone. Setting it back to false lays fresh foil over the reward before the next frame is painted. |
| onRevealedChange | (revealed: boolean) => void | — | Fires with true from the scratch or sweep that cleared enough foil. Controlled, the foil dissolves when the host answers. |
| onProgress | (cleared: number) => void | — | The share of foil cleared, 0 to 1 (two decimals), each time it moves by a whole percent. |
| brush | number | 18 | Brush radius in px, 10 to 34: a wider brush clears more per stroke and throws more flakes. |
| autoReveal | number | 60 | The percentage cleared, 40 to 80, at which the rest of the foil dissolves by itself. |
| flakes | boolean | true | Flakes of the foil that comes off tumble and fall out of the card. The frame loop runs only while flakes are falling, on screen, in a visible page. |
| foil | "silver" | "gold" | "silver" | The foil's colours, mixed from the theme's ink or warning hue, and the chime's pitch (gold rings a fourth higher). |
| sound | boolean | false | Play the scrape (noise whose pitch and level follow the brush's speed), a paper crinkle for a single dab, and the reveal's chime and shimmer. Nothing plays, and no audio context exists, unless this is on. |
| disabled | boolean | false | Disables the foil button: nothing scratches. |
| className | string | — | Merged onto the card's classes. |