dropdown-picker-rn
    TypeScript icon, indicating that this package has built-in type declarations

    1.0.1 • Public • Published

    React native dropdown picker v4

    NOTE: THIS IS FORKED VERSION OF https://github.com/hossein-zare/react-native-dropdown-picker

    The only changes applied are mentioned in this comment: https://github.com/hossein-zare/react-native-dropdown-picker/issues/84#issuecomment-742657954

    A single / multiple, categorizable & searchable item picker (dropdown) component for react native which supports both Android & iOS.

    Screenshots

    Screenshot Screenshot

    Table of contents

    Dependencies

    Make sure react-native-vector-icons is installed.
    https://github.com/oblador/react-native-vector-icons

    Changelog

    • Added childrenContainerStyle. [Februrary 13, 2021]
    • Added textStyle viewStyle & untouchable props to items. [Februrary 13, 2021]
    • Added category support. [Februrary 13, 2021]
    • Added globalTextStyle. [February 11, 2021]
    • Added onSearch. [January 27, 2021]
    • Added labelProps. [January 06, 2021]
    • Some bug-fixes. [January 06, 2021]
    • Added containerProps. [December 21, 2020]

    Getting Started

    Installation

    via NPM
    npm install react-native-dropdown-picker --save
    via Yarn
    yarn add react-native-dropdown-picker

    Basic Usage

    The first step is to import the package.

    import DropDownPicker from 'react-native-dropdown-picker';

    Single Item

    Select a single item.

    import Icon from 'react-native-vector-icons/Feather';
    
    this.state = {
        country: 'uk'
    }
    
    <DropDownPicker
        items={[
            {label: 'USA', value: 'usa', icon: () => <Icon name="flag" size={18} color="#900" />, hidden: true},
            {label: 'UK', value: 'uk', icon: () => <Icon name="flag" size={18} color="#900" />},
            {label: 'France', value: 'france', icon: () => <Icon name="flag" size={18} color="#900" />},
        ]}
        defaultValue={this.state.country}
        containerStyle={{height: 40}}
        style={{backgroundColor: '#fafafa'}}
        itemStyle={{
            justifyContent: 'flex-start'
        }}
        dropDownStyle={{backgroundColor: '#fafafa'}}
        onChangeItem={item => this.setState({
            country: item.value
        })}
    />

    Multiple Items

    Select multiple items.

    import Icon from 'react-native-vector-icons/Feather';
    
    this.state = {
        countries: ['uk']
    }
    
    <DropDownPicker
        items={[
            {label: 'UK', value: 'uk', icon: () => <Icon name="flag" size={18} color="#900" />},
            {label: 'France', value: 'france', icon: () => <Icon name="flag" size={18} color="#900" />},
        ]}
    
        multiple={true}
        multipleText="%d items have been selected."
        min={0}
        max={10}
    
        defaultValue={this.state.countries}
        containerStyle={{height: 40}}
        itemStyle={{
            justifyContent: 'flex-start'
        }}
        onChangeItem={item => this.setState({
            countries: item // an array of the selected items
        })}
    />

    Available Item Properties

    Here's the type definition of an item.

    type ItemType = {
        label: any; // required
        value: any; // required
        icon?: () => JSX.Element;
        hidden?: boolean;
        untouchable?: boolean;
        parent?: any;
        disabled?: boolean;
        selected?: boolean;
        viewStyle?: StyleProp<ViewStyle>,
        textStyle?: StyleProp<TextStyle>,
    };

    Category Support

    As of v4.x, You can simply categorize your items.

    <DropDownPicker
        items={[
            {label: 'North America', value: 'na', untouchable: true}, // North America
            {label: 'United States', value: 'us', parent: 'na'},
            {label: 'Canada', value: 'canada', parent: 'na'},
            {label: 'Mexico', value: 'mexico', parent: 'na'},
    
            {label: 'Europe', value: 'eu', untouchable: true}, // Europe
            {label: 'UK', value: 'uk', parent: 'eu'},
            {label: 'Germany', value: 'germany', parent: 'eu'},
            {label: 'Russia', value: 'russia', parent: 'eu'},
        ]}
        
        ...
    />

    The parent property must be equal to the value property of the parent item.
    The untouchable property makes the item untouchable.

    Searchable Items

    Search for specific items.

    searchable={true}
    searchablePlaceholder="Search for an item"
    searchablePlaceholderTextColor="gray"
    seachableStyle={{}}
    searchableError={() => <Text>Not Found</Text>}
    onSearch={text => {
        // Example
        if (this._API.isFetching())
            this._API.abort();
    
        this._API = this.fetchFromServer(text, (items) => {
            // See controller: https://github.com/hossein-zare/react-native-dropdown-picker#controller
            this.controller.resetItems(items); // Maybe a new method will be introduced for a better UX!
        });
    }}

    Default Item

    You may want to select one of the items as default.

    Use one of the following options:

    1. Add selected: true to the object. (This method is not state-friendly!)

      items={[
          {label: 'Item 1', value: 'item1'},
          {label: 'Item 2', value: 'item2', selected: true},
      ]}
    2. The defaultValue property.

      defaultValue = 'uk'; // Single
      defaultValue = ['uk']; // Multiple

    Placeholder

    You may want to have a placeholder while the default value is null or an empty array.

    Add the following properties to the component.

    this.state = {
        data: null, // Single
        data: [] // Multiple
    }
    
    ...
    defaultValue={this.state.data}
    placeholder="Select an item"
    ...

    Controller

    The controller property gives you full access to the DropDownPicker methods and properties.

    Class Components
    constructor(props) {
        this.state = {
            value: null,
            items: []
        }
    
        this.controller;
    }
    
    <DropDownPicker
        items={this.state.items}
        controller={instance => this.controller = instance}
        onChangeList={(items, callback) => {
            this.setState({
                items // items: items
            }, callback);
        }}
    
        defaultValue={this.state.value}
        onChangeItem={item => this.setState({
            value: item.value
        })}
    />
    Functional Components
    const [value, setValue] = useState(null);
    const [items, setItems] = useState([ {...}, ... ]);
    let controller;
    
    <DropDownPicker
        items={items}
        controller={instance => controller = instance}
        onChangeList={(items, callback) => {
            new Promise((resolve, reject) => resolve(setItems(items)))
                .then(() => callback())
                .catch(() => {});
        }}
    
        defaultValue={value}
        onChangeItem={item => setValue(item.value)}
    />

    in Class components you can call methods using this.controller.METHOD_NAME() and controller.METHOD_NAME() in Functional components.

    1. Reset the state.

      You may want to reset the state of your picker.

      this.controller.reset();
    2. Reset items.

      The second argument is your default value. (Optional)

      this.controller.resetItems([{}, {}, ...]);
      
      this.controller.resetItems([{}, {}, ...], 'uk'); // Single
      this.controller.resetItems([{}, {}, ...], ['uk', ...]); // Multiple
    3. Select an item manually.

      You may want to select an item manually.

      // Single
      this.controller.selectItem('uk');
      
      // Multiple
      this.controller.selectItem(['uk', 'france']);
    4. Add items manually.

      There are two methods to help you add items manually.

      this.controller.addItem({
        label: 'UK',
        value: 'uk',
        icon: () => {},
      });
      this.controller.addItems([
        {
          label: 'UK',
          value: 'uk',
          icon: () => {},
        },
      ]);
    5. Remove items

      this.controller.removeItem('uk', {
        changeDefaultValue: true, // Unselect if the removed item is the selected item
      });
    6. Check if the dropdown is open

      this.controller.isOpen(); // boolean
    7. Open, close or toggle.

      this.controller.open();
      this.controller.close();
      this.controller.toggle();

    Styling The Component

    There are 14 props to style the component.

    1. The style property.

      Use this to adjust the inner part of the picker.

      style={{paddingVertical: 10}}
      
    2. The dropDownStyle property.

      Additional styles for the dropdown box.

      dropDownStyle={{backgroundColor: '#fafafa'}}
      
    3. The containerStyle property.

      Use this to adjust the outer part of the picker such as margin, width, height, flex, ...

      containerStyle={{width: 150, height: 70}}
      
    4. The itemStyle property.

      If you want the labels on the left and right side or to centerize them:

      itemStyle={{justifyContent: 'flex-start|flex-end|center'}}
      
    5. The labelStyle property.

      This property gives full control over the label.

      labelStyle={{
          fontSize: 14,
          textAlign: 'left',
          color: '#000'
      }}
      
    6. The selectedLabelStyle property.

      Changes the style of the selected item label.

      selectedLabelStyle={{
          color: '#39739d'
      }}
      
    7. The placeholderStyle property.

      Style the placeholder text with this property.

      placeholderStyle={{
          fontWeight: 'bold',
          textAlign: 'center'
      }}
      
    8. The activeItemStyle property.

      This property allows you to style the active item.

      activeItemStyle={{justifyContent: 'center'}}
      
    9. The activeLabelStyle property.

      This property allows you to style the active label.

      activeLabelStyle={{color: 'red'}}
      
    10. The arrowStyle property.

      Adds your additional styles to the View element of the arrow.

      arrowStyle={{marginRight: 10}}
      
    11. The searchableStyle property.

      Additional styles for the TextInput

      searchableStyle={{backgroundColor: '#dfdfdf'}}
      
    12. The searchablePlaceholderTextColor property.

      Assigns a new color to the placeholder text.

      searchablePlaceholderTextColor="silver"
      
    13. The globalTextStyle property.

      You can style <Text /> elements globally.

      globalTextStyle={{
          fontFamily: "MyFontName",
          fontSize: 15
      }}
    14. The childrenContainerStyle property.

      Style the children container View (See Category Support)

      childrenContainerStyle={{
          paddingLeft: 30
      }}

    RTL Support

    1. The selected item

      RTL Support

      style={{
          flexDirection: 'row-reverse',
      }}
      labelStyle={{
          textAlign: 'right',
      }}
    2. The dropdown items

      RTL Support

      itemStyle={{
          flexDirection: 'row-reverse',
          justifyContent: 'flex-start',
      }}

    FAQ

    How to close other pickers when opening another picker?

    this.state = {
        isVisibleA: false,
        isVisibleB: false,
    
        ...
    }
    
    changeVisibility(state) {
        this.setState({
            isVisibleA: false,
            isVisibleB: false,
            ...state
        });
    }
    
    // Picker A
    <DropDownPicker
        isVisible={this.state.isVisibleA}
        onOpen={() => this.changeVisibility({
            isVisibleA: true
        })}
        onClose={() => this.setState({
            isVisibleA: false
        })}
    
        ...
    />
    
    // Picker B
    <DropDownPicker
        isVisible={this.state.isVisibleB}
        onOpen={() => this.changeVisibility({
            isVisibleB: true
        })}
        onClose={() => this.setState({
            isVisibleB: false
        })}
    
        ...
    />

    borderRadius

    Avoid using borderRadius and all the corners must be set separately.

    style={{
        borderTopLeftRadius: 10, borderTopRightRadius: 10,
        borderBottomLeftRadius: 10, borderBottomRightRadius: 10
    }}
    dropDownStyle={{
        borderBottomLeftRadius: 20, borderBottomRightRadius: 20
    }}

    zIndex conflicts (Untouchable Items, Overlapping pickers)

    1. Using the containerStyle property to style the picker results in unexpected behaviors like untouchable items.

      The style and dropDownStyle properties must be used instead.
      Use the containerStyle prop to adjust the outer part of the picker such as margin, width, height, flex, ...

    2. Nested Views

      You have to add zIndex to the nested views which contain the picker.
      Note! zIndex locks the picker on Android, The solution is to use the Platform.OS

      import { Platform } from 'react-native';
      
      <View
          style={{
              ...(Platform.OS !== 'android' && {
                  zIndex: 10
              })
          }}
      >
          <DropDownPicker ... />
      </View>

      Demo: https://snack.expo.io/@hossein-zare/823437

    3. DropDownPicker wrapped by <View style={{backgroundColor: ..., border[...]: ..., elevation: ...}}>
      These props will make your dropdown untouchable.
      Remove all the backgroundColor, border[...], elevation, ... style properties from the parent element.
      https://github.com/hossein-zare/react-native-dropdown-picker/issues/40#issuecomment-651744446

    4. Multiple Pickers

      <DropDownPicker zIndex={5000} />
      <DropDownPicker zIndex={4000} />
      <DropDownPicker zIndex={3000} />

    Dropdown Overflow

    Adding borders to the component separates elements or may overflow. To solve this issue add marginTop to the dropDownStyle and specify the value which fits your UI well.

    dropDownStyle={{marginTop: 2}}

    Props

    Name Description Type Default Required
    items The items for the component. array Yes
    defaultValue The value of the default item. (If multiple={true}, it takes an array of pre-selected values: ['uk']) any No
    placeholder Default text to be shown to the user when defaultValue={null} or defaultValue={[]} string 'Select an item' No
    dropDownMaxHeight Height of the dropdown box. number 150 No
    style Additional styles for the picker. object {} No
    globalTextStyle Global text style. object {} No
    dropDownStyle Additional styles for the dropdown box. object {} No
    containerStyle Additional styles for the container view. object {} No
    itemStyle Additional styles for the items. object {} No
    labelStyle Additional styles for the labels. object {} No
    selectedLabelStyle Additional styles for the selected label. object {} No
    placeholderStyle Additional styles for the placeholder text. object {} No
    activeItemStyle Additional styles for the active item. object {} No
    activeLabelStyle Additional styles for the active label. object {} No
    arrowStyle Additional styles for the arrow. object {} No
    arrowColor The color of arrow icons string #000 No
    arrowSize The size of the arrow. number 15 No
    showArrow An option to show/hide the arrow. bool true No
    customArrowUp Customize the arrow-up. func (size, color) => ... No
    customArrowDown Customize the arrow-down. func (size, color) => ... No
    customTickIcon Customize the tick icon for multiple item picker. func () => ... No
    zIndex This property specifies the stack order of the component. number 5000 No
    disabled Disables the component. bool false No
    isVisible Open or close the dropdown box. bool false No
    autoScrollToDefaultValue If true, automatically scroll to defaultValue/first defaultValue (multiple) during first render of dropdown bool false No
    multiple If set to true selecting multiple items is possible. bool false No
    multipleText a Text to inform the user how many items have been selected. string %d items have been selected No
    min Minimum number of items. number 0 No
    max Maximum number of items. number 10000000 No
    searchable Shows a TextInput to search for specific items. bool false No
    searchablePlaceholder Default text to be shown to the user. string Search for an item No
    searchablePlaceholderTextColor TextInput placeholder text color. string gray No
    searchableStyle Additional styles for the TextInput object {} No
    searchableError Shows a jsx element when nothing found. func () => <Text>Not Found</Text> No
    onSearch Fires when you type something in the TextInput. func (text) => {} No
    selectedLabelLength Specify length for the selected label. number 1000 No
    labelLength Specify length for the labels. number 1000 No
    labelProps Add props to the labels. object {} No
    scrollViewProps Add props to the ScrollView object {} No
    searchTextInputProps Add props to the search TextInput object {} No
    containerProps Add props to the container view. object {} No
    renderSeperator Separate items. func undefined No
    controller Gives you access to the methods and properties. func (instance) => {} No
    onOpen Fires when you open the picker. func () => {} No
    onClose Fires when you close the picker. func () => {} No
    onChangeItem Callback which returns item and index. The item is the selected object or an array of the selected values. func (item, index) => {} No
    onChangeList Changes the list of items. (items, callback) => {} No

    Install

    npm i dropdown-picker-rn

    DownloadsWeekly Downloads

    6

    Version

    1.0.1

    License

    MIT

    Unpacked Size

    94.6 kB

    Total Files

    13

    Last publish

    Collaborators

    • artan.monochain