
Vertical Step indicator
May 06, 2023
1 min
A Picker component for React Native which emulates the native <select>
interfaces for iOS and Android
For iOS, by default we are wrapping an unstyled TextInput component. You can then pass down styles to customize it to your needs.
For Android, by default we are using the native Picker component. If you prefer, you can set useNativeAndroidPickerStyle to false, which will also render an unstyled TextInput component. You can then pass down styles to customize it to your needs.
For either platform, you can alternatively pass down a child element of your choice that will be wrapped in a touchable area.
npm install react-native-picker-select
npm install @react-native-picker/pickernpx pod-install
expo install @react-native-picker/picker
-import React from 'react';import {Button,Text,TextInput,Platform,ScrollView,StyleSheet,TouchableWithoutFeedback,View,} from 'react-native';import { Chevron } from 'react-native-shapes';import { Ionicons } from '@expo/vector-icons';import RNPickerSelect, { defaultStyles } from 'react-native-picker-select';// import RNPickerSelect, { defaultStyles } from './debug';const sports = [{label: 'Football',value: 'football',},{label: 'Baseball',value: 'baseball',},{label: 'Hockey',value: 'hockey',},];export default class App extends React.Component {constructor(props) {super(props);this.inputRefs = {firstTextInput: null,favSport0: null,favSport1: null,lastTextInput: null,favSport5: null,};this.state = {numbers: [{label: '1',value: 1,color: 'orange',},{label: '2',value: 2,color: 'green',},],favSport0: undefined,favSport1: undefined,favSport2: undefined,favSport3: undefined,favSport4: 'baseball',previousFavSport5: undefined,favSport5: null,favNumber: undefined,};this.InputAccessoryView = this.InputAccessoryView.bind(this);}InputAccessoryView() {return (<View style={defaultStyles.modalViewMiddle}><TouchableWithoutFeedbackonPress={() => {this.setState({favSport5: this.state.previousFavSport5,},() => {this.inputRefs.favSport5.togglePicker(true);});}}hitSlop={{ top: 4, right: 4, bottom: 4, left: 4 }}><View testID="needed_for_touchable"><Textstyle={[defaultStyles.done,{ fontWeight: 'normal', color: 'red' },]}>Cancel</Text></View></TouchableWithoutFeedback><Text>Name | Prefer</Text><TouchableWithoutFeedbackonPress={() => {this.inputRefs.favSport5.togglePicker(true);}}hitSlop={{ top: 4, right: 4, bottom: 4, left: 4 }}><View testID="needed_for_touchable"><Text style={defaultStyles.done}>Done</Text></View></TouchableWithoutFeedback></View>);}render() {const placeholder = {label: 'Select a sport...',value: null,color: '#9EA0A4',};return (<View style={styles.container}><ScrollViewstyle={styles.scrollContainer}contentContainerStyle={styles.scrollContentContainer}><Text>Standard TextInput</Text><TextInputref={el => {this.inputRefs.firstTextInput = el;}}returnKeyType="next"enablesReturnKeyAutomaticallyonSubmitEditing={() => {this.inputRefs.favSport0.togglePicker();}}style={Platform.OS === 'ios'? pickerSelectStyles.inputIOS: pickerSelectStyles.inputAndroid}blurOnSubmit={false}/><View paddingVertical={5} /><Text>useNativeAndroidPickerStyle (default)</Text>{/* and iOS onUpArrow/onDownArrow toggle example */}<RNPickerSelectplaceholder={placeholder}items={sports}onValueChange={value => {this.setState({favSport0: value,});}}onUpArrow={() => {this.inputRefs.firstTextInput.focus();}}onDownArrow={() => {this.inputRefs.favSport1.togglePicker();}}style={pickerSelectStyles}value={this.state.favSport0}ref={el => {this.inputRefs.favSport0 = el;}}/><View paddingVertical={5} /><Text>set useNativeAndroidPickerStyle to false</Text><RNPickerSelectplaceholder={placeholder}items={sports}onValueChange={value => {this.setState({favSport1: value,});}}style={pickerSelectStyles}value={this.state.favSport1}useNativeAndroidPickerStyle={false}ref={el => {this.inputRefs.favSport1 = el;}}/><View paddingVertical={5} /><Text>set placeholder to empty object</Text>{/* and hiding the InputAccessoryView on iOS */}<RNPickerSelectplaceholder={{}}items={sports}onValueChange={value => {this.setState({favSport2: value,});}}InputAccessoryView={() => null}style={pickerSelectStyles}value={this.state.favSport2}/><View paddingVertical={5} /><Text>custom icon using react-native-shapes</Text>{/* and useNativeAndroidPickerStyle={false} with underlineColorAndroid */}<RNPickerSelectplaceholder={placeholder}items={sports}onValueChange={value => {this.setState({favSport3: value,});}}style={{inputAndroid: {backgroundColor: 'transparent',},iconContainer: {top: 5,right: 15,},}}value={this.state.favSport3}useNativeAndroidPickerStyle={false}textInputProps={{ underlineColorAndroid: 'cyan' }}Icon={() => {return <Chevron size={1.5} color="gray" />;}}/><View paddingVertical={5} /><Text>custom icon using react-native-vector-icons</Text>{/* and value defined */}<RNPickerSelectplaceholder={placeholder}items={sports}onValueChange={value => {this.setState({favSport4: value,});}}style={{...pickerSelectStyles,iconContainer: {top: 10,right: 12,},}}value={this.state.favSport4}useNativeAndroidPickerStyle={false}textInputProps={{ underlineColor: 'yellow' }}Icon={() => {return <Ionicons name="md-arrow-down" size={24} color="gray" />;}}/><View paddingVertical={5} /><Text>custom icon using your own css</Text>{/* and placeholder style changes, showing colors on items, useNativeAndroidPickerStyle={false} */}<RNPickerSelectplaceholder={{label: 'Select a number or add another...',value: null,color: 'red',}}items={this.state.numbers}onValueChange={value => {this.setState({favNumber: value,});}}style={{...pickerSelectStyles,iconContainer: {top: 20,right: 10,},placeholder: {color: 'purple',fontSize: 12,fontWeight: 'bold',},}}value={this.state.favNumber}Icon={() => {return (<Viewstyle={{backgroundColor: 'transparent',borderTopWidth: 10,borderTopColor: 'gray',borderRightWidth: 10,borderRightColor: 'transparent',borderLeftWidth: 10,borderLeftColor: 'transparent',width: 0,height: 0,}}/>);}}/><Buttontitle="+1 number to the above list"onPress={() => {const { numbers } = this.state;const value = numbers.length + 1;numbers.push({label: `${value}`,value,color: 'dodgerblue',});this.setState({numbers,});}}/><View paddingVertical={5} /><Text>custom InputAccessoryView on iOS</Text><RNPickerSelectitems={sports}value={this.state.favSport5}onValueChange={value => {this.setState({favSport5: value,});}}onOpen={() => {this.setState({previousFavSport5: this.state.favSport5,});}}InputAccessoryView={this.InputAccessoryView}ref={ref => {this.inputRefs.favSport5 = ref;}}/></ScrollView></View>);}}const styles = StyleSheet.create({container: {flex: 1,},scrollContainer: {flex: 1,paddingHorizontal: 15,},scrollContentContainer: {paddingTop: 40,paddingBottom: 10,},});const pickerSelectStyles = StyleSheet.create({inputIOS: {fontSize: 16,paddingVertical: 12,paddingHorizontal: 10,borderWidth: 1,borderColor: 'gray',borderRadius: 4,color: 'black',paddingRight: 30, // to ensure the text is never behind the icon},inputAndroid: {fontSize: 16,paddingHorizontal: 10,paddingVertical: 8,borderWidth: 0.5,borderColor: 'purple',borderRadius: 8,color: 'black',paddingRight: 30, // to ensure the text is never behind the icon},});
Coming Soon…
Quick Links
Legal Stuff