v2
424c17b ยท 1 year ago 26 commits
 1import { useEffect, useRef } from "react"
 2
 3import { cn } from "../../lib/utils"
 4
 5const NavSlider = ({
 6	containerClassName,
 7	buttonClassName,
 8	indicatorClassName,
 9	activeNav,
10	setActiveNav,
11	children,
12}: {
13	containerClassName?: string
14	buttonClassName?: string
15	indicatorClassName?: string
16	activeNav: number
17	setActiveNav: Function
18	children: string[]
19}) => {
20	const navRef = useRef<HTMLDivElement>(null)
21	const indicatorRef = useRef<HTMLDivElement>(null)
22
23	const moveNavIndicator = (index: number) => {
24		const navItems = navRef.current!.children
25		const navItem = navItems[index]
26		const navItemRect = navItem.getBoundingClientRect()
27		const navRect = navRef.current!.getBoundingClientRect()
28		const left = navItemRect.left - navRect.left
29		const width = navItemRect.width
30		indicatorRef.current!.style.transform = `translateX(${left - 10}px)`
31		indicatorRef.current!.style.width = `${width + 20}px`
32	}
33
34	useEffect(() => moveNavIndicator(0), [])
35
36	return (
37		<div
38			className={cn(
39				"relative flex w-full max-w-fit items-center justify-between gap-10 rounded-md bg-[#1E293B] px-10 shadow-md font-medium",
40				containerClassName
41			)}
42			ref={navRef}
43		>
44			{children.map((child, index) => (
45				<button
46					key={index}
47					className={cn(
48						"py-3",
49						activeNav === index ? "text-white" : "text-gray-500",
50						buttonClassName
51					)}
52					onClick={() => {
53						moveNavIndicator(index)
54						setActiveNav(index)
55					}}
56				>
57					{child}
58				</button>
59			))}
60			<div
61				className={cn(
62					"absolute bottom-0 left-0 h-1 w-0 rounded-md bg-white transition-all duration-700",
63					indicatorClassName
64				)}
65				ref={indicatorRef}
66			></div>
67		</div>
68	)
69}
70
71NavSlider.displayName = "NavSlider"
72
73export default NavSlider