Components
Base Components
Native Select
A styled native HTML select element with option and optgroup support.
Example
Installation
Create a native-select.tsx file and paste the following code into it.
import * as React from "react"import { ChevronDownIcon, ChevronsUpDown } from "lucide-react"import { cn } from "@/lib/utils"const NativeSelect = React.forwardRef< HTMLSelectElement, Omit<React.ComponentProps<"select">, "size"> & { size?: "sm" | "default" }>(({ className, size = "default", ...props }, ref) => { return ( <div className="group/native-select relative w-full h-fit has-[select:disabled]:opacity-50" data-slot="native-select-wrapper" > <select ref={ref} data-slot="native-select" data-size={size} className={cn( "border-input placeholder:text-muted-foreground selection:bg-primary selection:text-primary-foreground dark:bg-input/30 dark:hover:bg-input/50 h-9 w-full min-w-0 appearance-none rounded-md border bg-transparent px-3 py-2 pr-9 text-sm shadow-xs transition-[color,box-shadow] outline-none disabled:pointer-events-none disabled:cursor-not-allowed data-[size=sm]:h-8 data-[size=sm]:py-1", "focus-visible:border-ring focus-visible:ring-ring/50 focus-visible:ring-[3px]", "aria-invalid:ring-destructive/20 dark:aria-invalid:ring-destructive/40 aria-invalid:border-destructive", className )} {...props} /> <ChevronsUpDown className="text-muted-foreground pointer-events-none absolute top-1/2 right-3.5 size-4 -translate-y-1/2 opacity-50 select-none" aria-hidden="true" data-slot="native-select-icon" /> </div> )})NativeSelect.displayName = "NativeSelect"function NativeSelectOption({ ...props }: React.ComponentProps<"option">) { return <option data-slot="native-select-option" {...props} />}function NativeSelectOptGroup({ className, ...props}: React.ComponentProps<"optgroup">) { return ( <optgroup data-slot="native-select-optgroup" className={cn(className)} {...props} /> )}export { NativeSelect, NativeSelectOptGroup, NativeSelectOption }Check the import paths to ensure they match your project setup.
Usage
import {
NativeSelect,
NativeSelectOption,
NativeSelectOptGroup,
} from "@/components/ui/native-select";<NativeSelect value={value} onChange={(e) => setValue(e.target.value)}>
<NativeSelectOption value="">Choose...</NativeSelectOption>
<NativeSelectOption value="a">Option A</NativeSelectOption>
<NativeSelectOption value="b">Option B</NativeSelectOption>
</NativeSelect><select> props. Use NativeSelectOption for <option> and NativeSelectOptGroup for <optgroup>. The component supports a size prop for "default" or "sm".
Examples
Default
With label
With optgroup
UseNativeSelectOptGroup to group options under a label.
Sizes
Use thesize prop to switch between default and small.
Disabled
API Reference
NativeSelect
A styled native<select> with consistent focus and invalid styles. Accepts all native select props plus size ("default" | "sm").
disabledboolean
Default: -
size"default" | "sm"
Default: default
| Prop | Type | Default | Description |
|---|---|---|---|
| disabled | boolean | - | - |
| size | "default" | "sm" | default | - |
NativeSelectOption
Renders a native<option>. Use value and optional disabled.
No prop metadata found for component "NativeSelectOption".
NativeSelectOptGroup
Renders a native<optgroup> to group options. Use the label prop for the group heading.
No prop metadata found for component "NativeSelectOptGroup".