import React, { forwardRef, useId } from 'react'; import { cn } from '../../utils/cn'; export interface InputProps extends Omit, 'size'> { /** * Input label */ label?: React.ReactNode; /** * Error message or error state */ error?: string | boolean; /** * Help text shown below the input */ helpText?: React.ReactNode; /** * Left icon or element */ leftIcon?: React.ReactNode; /** * Right icon or element */ rightIcon?: React.ReactNode; /** * Input size * @default 'md' */ size?: 'sm' | 'md' | 'lg'; /** * Visual variant of the input * @default 'default' */ variant?: 'default' | 'filled' | 'outline' | 'unstyled'; /** * Container className */ containerClassName?: string; /** * Label className */ labelClassName?: string; /** * Make the input fill the width of its container * @default false */ fullWidth?: boolean; } export const Input = forwardRef( ( { id, label, error, helpText, leftIcon, rightIcon, size = 'md', variant = 'default', className, containerClassName, labelClassName, fullWidth = false, disabled, type = 'text', required, ...props }, ref ) => { // Use React's useId hook for stable ID generation const generatedId = useId(); const inputId = id || `input-${generatedId}`; return (
{label && ( )}
{leftIcon && ( {leftIcon} )} {rightIcon && ( {rightIcon} )}
{error && typeof error === 'string' && (
{error}
)} {helpText && !error && (
{helpText}
)}
); } ); Input.displayName = 'Input'; export default Input;