{"$schema":"https://ui.shadcn.com/schema/registry-item.json","name":"motion-primitives-text-scramble","type":"registry:component","title":"Text Scramble","description":"Tailark motion primitives text-scramble component","dependencies":["motion"],"files":[{"path":"core/motion-primitives/text-scramble.tsx","type":"registry:component","target":"@ui/motion-primitives/text-scramble.tsx","content":"'use client'\nimport { type JSX, useEffect, useRef, useState } from 'react'\nimport { LazyMotion, domAnimation, m, type MotionProps } from 'motion/react'\n\nexport type TextScrambleProps = {\n    children: string\n    duration?: number\n    speed?: number\n    characterSet?: string\n    as?: React.ElementType\n    className?: string\n    trigger?: boolean\n    onScrambleComplete?: () => void\n} & MotionProps\n\nconst defaultChars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789'\n\nexport function TextScramble({ children, duration = 0.8, speed = 0.04, characterSet = defaultChars, className, as: Component = 'p', trigger = true, onScrambleComplete, ...props }: TextScrambleProps) {\n    const MotionComponent = m.create(Component as keyof JSX.IntrinsicElements)\n    const [displayText, setDisplayText] = useState(children)\n    const onScrambleCompleteRef = useRef(onScrambleComplete)\n\n    useEffect(() => {\n        onScrambleCompleteRef.current = onScrambleComplete\n    })\n\n    useEffect(() => {\n        if (!trigger) return\n\n        const steps = duration / speed\n        let step = 0\n\n        const interval = setInterval(() => {\n            let scrambled = ''\n            const progress = step / steps\n\n            for (let i = 0; i < children.length; i++) {\n                if (children[i] === ' ') {\n                    scrambled += ' '\n                    continue\n                }\n\n                if (progress * children.length > i) {\n                    scrambled += children[i]\n                } else {\n                    scrambled += characterSet[Math.floor(Math.random() * characterSet.length)]\n                }\n            }\n\n            setDisplayText(scrambled)\n            step++\n\n            if (step > steps) {\n                clearInterval(interval)\n                setDisplayText(children)\n                onScrambleCompleteRef.current?.()\n            }\n        }, speed * 1000)\n\n        return () => clearInterval(interval)\n    }, [trigger, children, duration, speed, characterSet])\n\n    return (\n        <LazyMotion features={domAnimation}>\n        <MotionComponent\n            className={className}\n            {...props}>\n            {displayText}\n        </MotionComponent>\n        </LazyMotion>\n    )\n}\n"}]}