Spotlight Card
loomui/spotlight-cardFreeComponent
A surface with a soft highlight that follows the pointer and fades out on leave.
Live preview
live · rendered by the registry
Rendered by loomui on their own page — this is the component running, not a screenshot of it.Install it
npx shadcn@latest add https://loomui.design/r/spotlight-card.jsonSource
1"use client"23import * as React from "react"45import { cn } from "@/lib/utils"67export interface SpotlightCardProps extends React.ComponentProps<"div"> {8 /** Diameter of the surface highlight in pixels. */9 size?: number10 /** Fill of the surface wash. Any CSS colour. Keep the alpha low. */11 color?: string12 /** Fill of the border highlight. Brighter than `color` on purpose. */13 borderColor?: string14 /** Mark the whole card as a target: pointer cursor and a focus ring. */15 interactive?: boolean16 /** Render a plain card with no highlight. */17 disabled?: boolean18}1920/** Shows only the 1px ring of a layer, hiding the fill inside it. */21const RING_MASK: React.CSSProperties = {22 padding: 1,23 WebkitMask:24 "linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0)",25 WebkitMaskComposite: "xor",26 mask: "linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0)",27 maskComposite: "exclude",28}2930export function SpotlightCard({31 children,32 className,33 size = 320,34 color = "color-mix(in oklch, currentColor 10%, transparent)",35 borderColor = "color-mix(in oklch, var(--primary, currentColor) 60%, transparent)",36 interactive = false,37 disabled = false,38 style,39 ...props40}: SpotlightCardProps) {41 const ref = React.useRef<HTMLDivElement>(null)42 const frame = React.useRef(0)4344 // Pointer position is written to CSS custom properties on the next frame.45 // Nothing here goes through state, so moving the mouse costs no renders.46 const handlePointerMove = React.useCallback(47 (event: React.PointerEvent<HTMLDivElement>) => {48 if (disabled) {49 return50 }51 const node = ref.current52 if (!node) {53 return54 }5556 const { clientX, clientY } = event57 cancelAnimationFrame(frame.current)58 frame.current = requestAnimationFrame(() => {59 const rect = node.getBoundingClientRect()60 node.style.setProperty("--spotlight-x", `${clientX - rect.left}px`)61 node.style.setProperty("--spotlight-y", `${clientY - rect.top}px`)62 })63 },64 [disabled]65 )6667 React.useEffect(() => () => cancelAnimationFrame(frame.current), [])6869 const highlight = (fill: string) =>70 `radial-gradient(var(--spotlight-size) circle at var(--spotlight-x, 50%) var(--spotlight-y, 50%), ${fill}, transparent 70%)`7172 const layer =73// … truncated
What it pulls in
Other registry items
Files it writes
More from loomui
All 91 items| Component | Registry | Kind | Access | Installs | Command |
|---|---|---|---|---|---|
| Aurora Backdropaurora-backdrop | loomui | Components | Free | no deps | |
| Bento Gridbento-grid | loomui | Components | Free | no deps | |
| Card Stackcard-stack | loomui | Components | Free | no deps | |
| Compare Slidercompare-slider | loomui | Components | Free | no deps | |
| Confetti Buttonconfetti-button | loomui | Components | Free | no deps | |
| Count Upcount-up | loomui | Components | Free | no deps | |
| Credit Cardcredit-card | loomui | Components | Free | no deps | |
| Drawerdrawer | loomui | Components | Free | 1 dep |
