KQ-1806 · CORNER/TIDE
Corner Tide
A centred grid of glowing tiles drawn per pixel in one WebGL2 pass, each a superellipse whose corner exponent rides a slow travelling field of two crossing waves, so bands of tiles soften toward circles and sharpen back toward squares while keeping their size, each lit from within by a round core and a halo summed over its neighbours. The pointer pushes its own rounded patch through the grid, following on springs.glide and swelling in on springs.drift; a click sends a squaring ripple outward and each tile it passes rings back with the springs.recoil damping ratio, its core flashing as it squares. The keyboard's way in is a button behind the content: arrow keys move the patch a tile at a time, Enter or Space sends a ripple from it, Escape lifts it.
Basinworks · glazed tile
Corners, fired soft.
Enter or Space sends a squaring ripple from the patch. Arrow keys move the rounded patch a tile at a time; Escape lifts it.
exponent 2.0–6.0 · click to send a ripple
Install
One command — the source lands in your repo. Or copy it from the Code tab.
$ pnpm dlx shadcn@latest add @kinetiq/corner-tide
Props
- exponent
- number
- default 6
- How square the squarest tiles get: the corner exponent at the tide's crest, 3 to 12.
- minExponent
- number
- default 2
- How round the roundest tiles get: the corner exponent in the trough, 1.2 to 4 (2 is a circle).
- gap
- number
- default 6
- The gap between tiles, in px, 2 to 16.
- glow
- number
- default 0.5
- How much light each tile holds and spills around it, 0 to 1.
- cell
- number
- default 30
- One tile and its gap, in px, 16 to 64.
- colors
- readonly string[]
- default ["var(--accent-bright)", "var(--signal)"]
- The tiles' colours, one to three CSS colours laid across the grid; resolved on the element so they follow the theme.
- tide
- number
- default 0.85
- How far the tide swings the corners, 0 (every tile still at the middle exponent) to 1.
- speed
- number
- default 0.35
- How fast the tide travels, 0 to 1.
- patchRadius
- number
- default 70
- The reach of the pointer's rounded patch, in px.
- rippleSpeed
- number
- default 520
- How fast a squaring ripple travels outward, in px per second.
- children
- React.ReactNode
- default —
- Content above the tiles: a hero line, a heading, a call to action.
- interactive
- boolean
- default true
- The pointer and keys push the patch and send ripples.
- paused
- boolean
- default false
- Hold the tide where it is; the patch and ripples still answer.
- label
- string
- default "Tile grid"
- Names the grid for assistive technology.
- seed
- number
- default 4
- Seeds the tide's directions and phases, so two grids never swing alike.
- dpr
- number
- default 2
- Cap on the canvas's device pixel ratio, at most 2.
- onRipple
- (x: number, y: number) => void
- default —
- Fires when a ripple is sent, with its origin in px from the box's top left.
- disabled
- boolean
- default false
- Shows the tide but takes no input.
- className
- string
- default "h-56 w-full"
- Sizes the box.
| Prop | Type | Default | Description |
|---|---|---|---|
| exponent | number | 6 | How square the squarest tiles get: the corner exponent at the tide's crest, 3 to 12. |
| minExponent | number | 2 | How round the roundest tiles get: the corner exponent in the trough, 1.2 to 4 (2 is a circle). |
| gap | number | 6 | The gap between tiles, in px, 2 to 16. |
| glow | number | 0.5 | How much light each tile holds and spills around it, 0 to 1. |
| cell | number | 30 | One tile and its gap, in px, 16 to 64. |
| colors | readonly string[] | ["var(--accent-bright)", "var(--signal)"] | The tiles' colours, one to three CSS colours laid across the grid; resolved on the element so they follow the theme. |
| tide | number | 0.85 | How far the tide swings the corners, 0 (every tile still at the middle exponent) to 1. |
| speed | number | 0.35 | How fast the tide travels, 0 to 1. |
| patchRadius | number | 70 | The reach of the pointer's rounded patch, in px. |
| rippleSpeed | number | 520 | How fast a squaring ripple travels outward, in px per second. |
| children | React.ReactNode | — | Content above the tiles: a hero line, a heading, a call to action. |
| interactive | boolean | true | The pointer and keys push the patch and send ripples. |
| paused | boolean | false | Hold the tide where it is; the patch and ripples still answer. |
| label | string | "Tile grid" | Names the grid for assistive technology. |
| seed | number | 4 | Seeds the tide's directions and phases, so two grids never swing alike. |
| dpr | number | 2 | Cap on the canvas's device pixel ratio, at most 2. |
| onRipple | (x: number, y: number) => void | — | Fires when a ripple is sent, with its origin in px from the box's top left. |
| disabled | boolean | false | Shows the tide but takes no input. |
| className | string | "h-56 w-full" | Sizes the box. |