import {
forwardRef,
useId,
type SelectHTMLAttributes
} from 'react';
import { cn } from '@/utils/classNames';
export interface SelectOption {
readonly value: string;
readonly label: string;
readonly disabled?: boolean;
}
export interface SelectProps extends Omit, 'size'> {
readonly label?: string;
readonly hideLabel?: boolean;
readonly hint?: string;
readonly error?: string;
readonly options: readonly SelectOption[];
readonly placeholder?: string;
readonly containerClassName?: string;
readonly selectSize?: 'sm' | 'md' | 'lg';
}
const sizeClasses = {
sm: 'h-9 rounded-xl px-3 pr-9 text-sm',
md: 'h-11 rounded-2xl px-4 pr-10 text-sm',
lg: 'h-12 rounded-2xl px-4 pr-10 text-base'
} as const;
export const Select = forwardRef(function Select(
{
className,
containerClassName,
error,
hideLabel = false,
hint,
id,
label,
options,
placeholder,
selectSize = 'md',
...props
},
ref,
) {
const generatedId = useId();
const selectId = id ?? generatedId;
const hintId = hint ? `${selectId}-hint` : undefined;
const errorId = error ? `${selectId}-error` : undefined;
const describedBy = [hintId, errorId, props['aria-describedby']].filter(Boolean).join(' ');
return (
{label ? (
) : null}
{hint ? (
{hint}
) : null}
{error ? (
{error}
) : null}
);
});