Copy Button
A button that copies text to the clipboard with animated check feedback.
npx shadcn@latest add @hazine/copy-button
Installation
npx shadcn@latest add @hazine/copy-buttonSource
"use client"
import * as React from "react"
import { CheckIcon, CopyIcon } from "lucide-react"
import { cn } from "@/lib/utils"
import { Button } from "@/components/ui/button"
interface CopyButtonProps extends React.ComponentProps<typeof Button> {
value: string
timeout?: number
}
export function CopyButton({
value,
timeout = 2000,
className,
children,
...props
}: CopyButtonProps) {
const [copied, setCopied] = React.useState(false)
const timer = React.useRef<ReturnType<typeof setTimeout>>(undefined)
React.useEffect(() => () => clearTimeout(timer.current), [])
async function copy() {
await navigator.clipboard.writeText(value)
setCopied(true)
clearTimeout(timer.current)
timer.current = setTimeout(() => setCopied(false), timeout)
}
return (
<Button
variant="ghost"
size={children ? "sm" : "icon-sm"}
aria-label={copied ? "Copied" : "Copy to clipboard"}
className={cn("shrink-0", className)}
onClick={copy}
{...props}
>
{copied ? (
<CheckIcon className="text-emerald-500" />
) : (
<CopyIcon />
)}
{children}
</Button>
)
}
Dependencies
- button
- lucide-react