import * as React from 'react'; import { cn } from '@/lib/utils'; import { Search } from 'lucide-react'; export interface InputProps extends React.InputHTMLAttributes { value?: string | number | readonly string[] | undefined; } const Input = React.forwardRef( ({ className, type, value, onChange, ...props }, ref) => { const isControlled = value !== undefined; const { defaultValue, ...restProps } = props; const inputValue = isControlled ? value : defaultValue; const handleChange: React.ChangeEventHandler = (e) => { if (type === 'number') { const numValue = e.target.value === '' ? '' : Number(e.target.value); onChange?.({ ...e, target: { ...e.target, value: numValue, }, } as React.ChangeEvent); } else { onChange?.(e); } }; return ( ); }, ); Input.displayName = 'Input'; export interface ExpandedInputProps extends Omit { prefix?: React.ReactNode; suffix?: React.ReactNode; } const ExpandedInput = ({ suffix, prefix, className, ...props }: ExpandedInputProps) => { return (
{prefix} {suffix}
); }; const SearchInput = (props: InputProps) => { return ( } {...props} > ); }; type Value = string | readonly string[] | number | undefined; export const InnerBlurInput = React.forwardRef< HTMLInputElement, InputProps & { value: Value; onChange(value: Value): void } >(({ value, onChange, ...props }, ref) => { const [val, setVal] = React.useState(); const handleChange: React.ChangeEventHandler = React.useCallback((e) => { setVal(e.target.value); }, []); const handleBlur: React.FocusEventHandler = React.useCallback( (e) => { onChange?.(e.target.value); }, [onChange], ); React.useEffect(() => { setVal(value); }, [value]); return ( ); }); if (process.env.NODE_ENV !== 'production') { InnerBlurInput.whyDidYouRender = true; } export const BlurInput = React.memo(InnerBlurInput); export { ExpandedInput, Input, SearchInput }; type NumberInputProps = { onChange?(value: number): void } & InputProps; export const NumberInput = React.forwardRef< HTMLInputElement, NumberInputProps & { value: Value; onChange(value: Value): void } >(function NumberInput({ onChange, ...props }, ref) { return ( { const value = ev.target.value; onChange?.(value === '' ? 0 : Number(value)); // convert to number }} {...props} ref={ref} > ); });