UNPKG

yarn-spinner-runner-ts

Version:

TypeScript parser, compiler, and runtime for Yarn Spinner 3.x with React adapter [NPM package](https://www.npmjs.com/package/yarn-spinner-runner-ts)

78 lines 3.31 kB
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime"; import { useState, useEffect, useRef } from "react"; import { MarkupRenderer } from "./MarkupRenderer.js"; export function TypingText({ text, markup, typingSpeed = 100, showCursor = true, cursorCharacter = "|", cursorBlinkDuration = 530, cursorClassName = "", className = "", onComplete, disabled = false, }) { const [displayedLength, setDisplayedLength] = useState(disabled ? text.length : 0); const [cursorVisible, setCursorVisible] = useState(true); const cursorIntervalRef = useRef(null); const typingTimeoutRef = useRef(null); const onCompleteRef = useRef(onComplete); useEffect(() => { onCompleteRef.current = onComplete; }, [onComplete]); // Handle cursor blinking useEffect(() => { if (!showCursor || disabled) { return; } cursorIntervalRef.current = setInterval(() => { setCursorVisible((prev) => !prev); }, cursorBlinkDuration); return () => { if (cursorIntervalRef.current) { clearInterval(cursorIntervalRef.current); } }; }, [showCursor, cursorBlinkDuration, disabled]); // Handle typing animation useEffect(() => { if (disabled) { setDisplayedLength(text.length); if (onCompleteRef.current && text.length > 0) { onCompleteRef.current(); } return; } // Reset when text changes setDisplayedLength(0); if (text.length === 0) { if (onCompleteRef.current) { onCompleteRef.current(); } return; } let index = 0; const typeNextCharacter = () => { if (index < text.length) { index += 1; setDisplayedLength(index); if (typingSpeed <= 0) { requestAnimationFrame(typeNextCharacter); } else { typingTimeoutRef.current = setTimeout(typeNextCharacter, typingSpeed); } } else if (onCompleteRef.current) { onCompleteRef.current(); } }; if (typingSpeed <= 0) { requestAnimationFrame(typeNextCharacter); } else { typingTimeoutRef.current = setTimeout(typeNextCharacter, typingSpeed); } return () => { if (typingTimeoutRef.current) { clearTimeout(typingTimeoutRef.current); } }; }, [text, disabled, typingSpeed]); const visibleLength = markup ? Math.min(displayedLength, markup.text.length) : Math.min(displayedLength, text.length); return (_jsxs("span", { className: className, children: [_jsx("span", { children: markup ? (_jsx(MarkupRenderer, { text: text, markup: markup, length: visibleLength })) : (text.slice(0, visibleLength)) }), showCursor && !disabled && (_jsx("span", { className: `yd-typing-cursor ${cursorClassName}`, style: { opacity: cursorVisible ? 1 : 0, transition: `opacity ${cursorBlinkDuration / 2}ms ease-in-out`, }, children: cursorCharacter }))] })); } //# sourceMappingURL=TypingText.js.map