import { OTPInput } from "input-otp-native"; import React, { useEffect } from "react"; import { View, Text } from "react-native"; import Animated, { useAnimatedStyle, withRepeat, withTiming, withSequence, useSharedValue, } from "react-native-reanimated"; import { useCSSVariable } from "uniwind"; import { cn } from "@turbostarter/ui"; import type { SlotProps } from "input-otp-native"; function InputOTPGroup({ className, ...props }: React.ComponentProps) { return ( ); } function InputOTPSlot({ char, isActive, hasFakeCaret, className, index, max, ...props }: React.ComponentProps & SlotProps & { index?: number; max?: number }) { const isFirst = index === 0; const isLast = index === (max ?? 6) - 1; return ( {char !== null && ( {char} )} {hasFakeCaret && } ); } function FakeCaret() { const opacity = useSharedValue(1); const foregroundColor = useCSSVariable("--foreground"); useEffect(() => { opacity.value = withRepeat( withSequence( withTiming(0, { duration: 500 }), withTiming(1, { duration: 500 }), ), -1, true, ); }, [opacity]); const animatedStyle = useAnimatedStyle(() => ({ opacity: opacity.value, })); const baseStyle = { width: 2, height: 20, borderRadius: 1, ...(foregroundColor && { backgroundColor: foregroundColor.toString() }), }; return ( ); } function InputOTPSeparator({ className, ...props }: React.ComponentProps) { return ( ); } export { OTPInput as InputOTP, InputOTPGroup, InputOTPSlot, InputOTPSeparator };