Dock
macOS-style animated dock with Gaussian neighbor icon magnification driven by spring physics.
Installation
File Structure
dock.tsx
Usage
import { Dock } from "@/components/unlumen-ui/dock";
const items = [
{ icon: "🌐", label: "Browser" },
{ icon: "📁", label: "Files", href: "/files" },
];
<Dock items={items} />;Custom magnification
<Dock
items={items}
magnification={3}
distance={120}
springOptions={{ stiffness: 400, damping: 25 }}
/>API Reference
Dock
| Prop | Type | Default | Description |
|---|---|---|---|
items | DockItem[] | - | Array of dock items to render. |
magnification? | number | 2.2 | Maximum scale factor applied to the icon directly under the cursor. |
distance? | number | 100 | Pixel radius from the cursor within which neighbor icons are magnified. |
iconSize? | number | 48 | Base icon size in pixels (width & height). |
gap? | number | 12 | Gap between icons in pixels. |
alwaysShowLabels? | boolean | false | When true, labels are always visible beneath icons instead of appearing only on hover. |
springOptions? | SpringOptions | { stiffness: 300, damping: 22, mass: 0.5 } | Motion spring options for the scale animation. |
className? | string | - | Extra classes on the dock container. |
DockItem
| Prop | Type | Default | Description |
|---|---|---|---|
icon | React.ReactNode | - | Icon content — emoji, image, or any React node. |
label | string | - | Tooltip text shown above the icon on hover. |
href? | string | - | If provided, the item renders as an anchor tag. |
onClick? | () => void | - | Click handler (used when href is not set). |
Notes
- Magnification uses a Gaussian bell curve:
scale = (magnification − 1) × exp(−d² / (2 × distance²)) + 1, so icons taper smoothly from the cursor outward. - Each icon's scale is independently driven by a
useSpringon auseTransformof the sharedmouseXMotionValue — no re-renders during animation. - The dock uses
origin-bottomso icons scale upward from their base, matching macOS behavior. - Tooltips animate with a 150ms ease-in/out on hover.
- The dock container has
backdrop-blur-mdapplied — ensure there's a background element behind it for the blur to be visible.
Keep in mind
Most components on this site are inspired by or recreated from existing work across the web. I'm not here to take credit; just to learn, experiment, and sometimes push things a bit further. If something looks familiar and I forgot to mention you, reach out and I'll fix that right away.