react-ios-style-picker is a highly customizable, easy-to-use React component library designed to mimic the native iOS picker interface. This library provides an accessible way to integrate picker functionality into your React applications. The components are built with flexibility in mind, allowing for extensive customization in terms of appearance and behavior.
The library includes two main components:
- Picker: Enables users to select options from a scrollable list, which can be customized with various styles and callback functions.
- BottomSheet: A versatile component that slides up from the bottom of the screen, perfect for housing pickers, menus, or other content in a modal overlay.
Whether you're building a mobile-first design or adding mobile-friendly elements to a responsive web application, react-ios-style-picker provides the tools you need to incorporate sleek, intuitive selection interfaces.
- iOS-like Interface: Provides a user experience similar to the native iOS picker, making it ideal for creating consistent and familiar interfaces across web and mobile platforms.
- Customizable Appearance: Offers extensive styling options to match the picker and bottom sheet components with your application's theme.
- Flexible Functionality: Supports a variety of use cases from simple date pickers to more complex custom selector interfaces.
- Accessibility Focused: Designed with accessibility in mind with ARIA attributes and keyboard support.
- TypeScript Support: Fully typed with TypeScript for better development experience.
- Tree-shakeable: Optimized for modern bundlers with proper side effects configuration.
To use these components in your project, you need to install the library via npm or yarn:
npm install react-ios-style-pickeror
yarn add react-ios-style-pickerThe Picker component allows users to select an item from a scrollable list. It is customizable with styles and callback functions.
| Prop | Type | Default | Description |
|---|---|---|---|
list |
(string | number)[] |
required | Array of items to display in the picker |
itemHeight |
number |
50 |
Height of each item in pixels |
initialSelected |
string | number |
- | Initially selected item |
onSelectedChange |
(selected: string | number) => void |
- | Callback function called when a new item is selected |
itemClassName |
string |
- | Additional CSS class for each item |
itemStyle |
React.CSSProperties |
- | Inline styles for each item |
className |
string |
- | CSS class for the wrapper div |
style |
React.CSSProperties |
- | Inline styles for the wrapper div |
listClassName |
string |
- | CSS class for the list element |
listStyle |
React.CSSProperties |
- | Inline styles for the list element |
showGradientMask |
boolean |
true |
Show gradient mask at top and bottom |
showCenterIndicator |
boolean |
true |
Show center selection indicator |
theme |
"light" | "dark" | "auto" |
"auto" |
Theme mode |
import { Picker } from "react-ios-style-picker";
function App() {
const [selected, setSelected] = React.useState("Option 2");
return (
<Picker
list={["Option 1", "Option 2", "Option 3"]}
itemHeight={40}
initialSelected={selected}
onSelectedChange={(value) => {
console.log(`Selected: ${value}`);
setSelected(value);
}}
/>
);
}import { Picker, ScrollPickerProps } from "react-ios-style-picker";
function App() {
const options: ScrollPickerProps['list'] = ["Apple", "Banana", "Cherry"];
const [selected, setSelected] = React.useState<string | number>("Banana");
return (
<Picker
list={options}
itemHeight={50}
initialSelected={selected}
onSelectedChange={setSelected}
theme="dark"
showGradientMask={true}
showCenterIndicator={true}
/>
);
}import { Picker } from "react-ios-style-picker";
function StyledPicker() {
return (
<Picker
list={Array.from({ length: 100 }, (_, i) => i + 1)}
itemHeight={60}
className="my-picker-wrapper"
listClassName="my-custom-list"
itemClassName="my-custom-item"
itemStyle={{
fontSize: "18px",
fontWeight: "500",
color: "#333",
}}
style={{
width: "200px",
margin: "0 auto",
}}
/>
);
}The BottomSheet component is used to display content in a sliding panel from the bottom. It is ideal for modal views.
| Prop | Type | Default | Description |
|---|---|---|---|
children |
React.ReactNode | React.ReactNode[] |
required | Content to display inside the BottomSheet |
isOpen |
boolean |
required | Whether the BottomSheet is visible |
onClose |
() => void |
required | Function to call when the BottomSheet needs to be closed |
className |
string |
"" |
Additional CSS class for the overlay |
style |
React.CSSProperties |
{} |
Inline styles for the BottomSheet content |
button |
React.ReactNode |
- | Optional button to display in the BottomSheet |
theme |
"light" | "dark" | "auto" |
"auto" |
Theme mode |
import { BottomSheet } from "react-ios-style-picker";
function App() {
const [isOpen, setIsOpen] = React.useState(false);
return (
<>
<button onClick={() => setIsOpen(true)}>Open BottomSheet</button>
<BottomSheet
isOpen={isOpen}
onClose={() => setIsOpen(false)}
>
<div>Content goes here</div>
</BottomSheet>
</>
);
}import { BottomSheet, BottomSheetProps } from "react-ios-style-picker";
function App() {
const [isOpen, setIsOpen] = React.useState<boolean>(false);
const handleClose: BottomSheetProps['onClose'] = () => {
setIsOpen(false);
};
return (
<>
<button onClick={() => setIsOpen(true)}>Open BottomSheet</button>
<BottomSheet
isOpen={isOpen}
onClose={handleClose}
theme="light"
>
<h2>Title</h2>
<p>Your content here</p>
</BottomSheet>
</>
);
}import { Picker, BottomSheet } from "react-ios-style-picker";
function DatePickerSheet() {
const [isOpen, setIsOpen] = React.useState(false);
const [selectedYear, setSelectedYear] = React.useState(2024);
const years = Array.from({ length: 50 }, (_, i) => 2000 + i);
return (
<>
<button onClick={() => setIsOpen(true)}>
Select Year: {selectedYear}
</button>
<BottomSheet
isOpen={isOpen}
onClose={() => setIsOpen(false)}
button={
<button onClick={() => setIsOpen(false)}>Done</button>
}
>
<Picker
list={years}
initialSelected={selectedYear}
onSelectedChange={setSelectedYear}
itemHeight={50}
/>
</BottomSheet>
</>
);
}The components are built with accessibility in mind:
- Picker: Includes ARIA attributes (
role="listbox",aria-label,aria-activedescendant) for screen readers - BottomSheet:
- Supports ESC key to close
- Includes
role="dialog"andaria-modal="true" - Manages focus automatically
The library includes default CSS styles that are automatically imported. The CSS is modular and can be customized using:
- CSS Classes: Add custom classes via
className,listClassName,itemClassNameprops - Inline Styles: Use
style,listStyle,itemStyleprops - Theme Mode: Use
themeprop to switch between light/dark modes - CSS Variables: Override CSS custom properties in your own stylesheet
- Chrome (latest)
- Firefox (latest)
- Safari (latest)
- Edge (latest)
MIT © reeseo3o
Contributions are welcome! Please feel free to submit a Pull Request.
If you find a bug or have a feature request, please file an issue at GitHub Issues.
