UNPKG

@arolariu/components

Version:

🎨 70+ beautiful, accessible React components built on Radix UI. TypeScript-first, tree-shakeable, SSR-ready. Perfect for modern web apps, design systems & rapid prototyping. Zero config, maximum flexibility! ⚡

74 lines (73 loc) • 2.54 kB
"use client"; import { jsx, jsxs } from "react/jsx-runtime"; import { motion } from "motion/react"; import { forwardRef, useCallback, useImperativeHandle, useRef, useState } from "react"; import { cn } from "../../lib/utilities.js"; const RippleButton = /*#__PURE__*/ forwardRef(({ children, onClick, className, rippleClassName, scale = 10, transition = { duration: 0.6, ease: "easeOut" }, ...props }, ref)=>{ const [ripples, setRipples] = useState([]); const buttonRef = useRef(null); useImperativeHandle(ref, ()=>buttonRef.current); const createRipple = useCallback((event)=>{ const button = buttonRef.current; if (!button) return; const rect = button.getBoundingClientRect(); const x = event.clientX - rect.left; const y = event.clientY - rect.top; const newRipple = { id: Date.now(), x, y }; setRipples((prev)=>[ ...prev, newRipple ]); setTimeout(()=>{ setRipples((prev)=>prev.filter((r)=>r.id !== newRipple.id)); }, 600); }, []); const handleClick = useCallback((event)=>{ createRipple(event); if (onClick) onClick(event); }, [ createRipple, onClick ]); return /*#__PURE__*/ jsxs(motion.button, { ref: buttonRef, onClick: handleClick, whileTap: { scale: 0.95 }, whileHover: { scale: 1.05 }, className: cn("text-primary-foreground bg-primary relative h-10 cursor-pointer overflow-hidden rounded-lg px-4 py-2 text-sm font-medium focus:outline-none", className), ...props, children: [ children, ripples.map((ripple)=>/*#__PURE__*/ jsx(motion.span, { initial: { scale: 0, opacity: 0.5 }, animate: { scale, opacity: 0 }, transition: transition, className: cn("bg-primary-foreground pointer-events-none absolute size-5 rounded-full", rippleClassName), style: { top: ripple.y - 10, left: ripple.x - 10 } }, ripple.id)) ] }); }); RippleButton.displayName = "RippleButton"; export { RippleButton }; //# sourceMappingURL=ripple-button.js.map