mediahub-fe/components/landing-page/StaggeredDropdown.tsx

95 lines
2.6 KiB
TypeScript

import { FiChevronDown, FiYoutube, FiMusic, FiImage, FiFile } from "react-icons/fi";
import { motion } from "framer-motion";
import { Dispatch, SetStateAction, useState } from "react";
import { IconType } from "react-icons";
const StaggeredDropDown = () => {
const [open, setOpen] = useState(false);
return (
<div className="flex items-center justify-center bg-white ">
<motion.div animate={open ? "open" : "closed"} className="relative">
<button onClick={() => setOpen((pv) => !pv)} className="flex items-center text-black transition-colors">
<span className="font-medium text-md">Konten</span>
<motion.span variants={iconVariants}>
<FiChevronDown />
</motion.span>
</button>
<motion.ul
initial={wrapperVariants.closed}
variants={wrapperVariants}
style={{ originY: "top", translateX: "-50%" }}
className="flex flex-col z-50 gap-2 p-2 rounded-lg shadow-xl absolute top-[120%] left-[50%] w-48 overflow-hidden bg-white"
>
<Option setOpen={setOpen} Icon={FiYoutube} text="Audio Visual" />
<Option setOpen={setOpen} Icon={FiMusic} text="Audio" />
<Option setOpen={setOpen} Icon={FiImage} text="Foto" />
<Option setOpen={setOpen} Icon={FiFile} text="Teks" />
</motion.ul>
</motion.div>
</div>
);
};
const Option = ({ text, Icon, setOpen }: { text: string; Icon: IconType; setOpen: Dispatch<SetStateAction<boolean>> }) => {
return (
<motion.li
variants={itemVariants}
onClick={() => setOpen(false)}
className="flex items-center gap-2 w-full p-2 text-xs font-medium whitespace-nowrap rounded-md hover:bg-indigo-100 text-slate-700 hover:text-red-500 transition-colors cursor-pointer"
>
<motion.span variants={actionIconVariants}>
<Icon />
</motion.span>
<span>{text}</span>
</motion.li>
);
};
export default StaggeredDropDown;
const wrapperVariants = {
open: {
scaleY: 1,
transition: {
when: "beforeChildren",
staggerChildren: 0.1,
},
},
closed: {
scaleY: 0,
transition: {
when: "afterChildren",
staggerChildren: 0.1,
},
},
};
const iconVariants = {
open: { rotate: 180 },
closed: { rotate: 0 },
};
const itemVariants = {
open: {
opacity: 1,
y: 0,
transition: {
when: "beforeChildren",
},
},
closed: {
opacity: 0,
y: -15,
transition: {
when: "afterChildren",
},
},
};
const actionIconVariants = {
open: { scale: 1, y: 0 },
closed: { scale: 0, y: -7 },
};