43 lines
832 B
TypeScript
43 lines
832 B
TypeScript
"use client";
|
|
|
|
import { motion } from "framer-motion";
|
|
|
|
type TextElement = "h1" | "h2" | "h3" | "p" | "span";
|
|
|
|
const MOTION_TAGS = {
|
|
h1: motion.h1,
|
|
h2: motion.h2,
|
|
h3: motion.h3,
|
|
p: motion.p,
|
|
span: motion.span,
|
|
} as const;
|
|
|
|
type AnimatedTextProps = {
|
|
text: string;
|
|
as?: TextElement;
|
|
className?: string;
|
|
duration?: number;
|
|
delay?: number;
|
|
};
|
|
|
|
export function AnimatedText({
|
|
text,
|
|
as = "h2",
|
|
className,
|
|
duration = 0.5,
|
|
delay = 0,
|
|
}: AnimatedTextProps) {
|
|
const MotionTag = MOTION_TAGS[as];
|
|
|
|
return (
|
|
<MotionTag
|
|
className={className}
|
|
initial={{ opacity: 0, y: 8 }}
|
|
animate={{ opacity: 1, y: 0 }}
|
|
transition={{ type: "tween", ease: "easeInOut", duration, delay }}
|
|
style={{ display: "block", willChange: "transform, opacity" }}
|
|
>
|
|
{text}
|
|
</MotionTag>
|
|
);
|
|
}
|