Create suggested search bar with React-Select

Penny Pang
path2code
Published in
5 min readFeb 1, 2019

Here is an example of the search bar we will be making. We will be going through the set-up for react-select first and then style the search bar with emotion.js and react-select style keys.

example of React-Select search bar I made

1. Install react-select

npm install --save react-select to check if the library has been successfully installed, check in the node_modules folder for react-select. If it doesn’t come up, I normally just restart the computer and it’s there.

2. Importing react-select

import { Select } from 'react-select' at the top of the file.

3. Make a search list

inside ‘mydata.json’ file

My search list in the example above is from a data in json format imported as projectList

mydata.json is a one massive array containing objects with keys and values.

For our search list, we only want to extract the “project_name” to show up on the search list.

To make a search list, each object in the data must have at least 2 values: label (a string) and value (any type).

Importing projectList at the top along with all the other imports

import projectList from '../data/mydata.json'

To extract the label and value from projectlist.json, we can use JavaScript map() method

const searchList = projectList.map(
({ project_name }) => {
return{
value: project_name,
label: project_name
}
}
);

4. Create class component for Search Bar

creating a class component for the search bar allows me to have a search bar as its own ‘component’, controlling its state and render out react-select

class SearchBar extends React.Componenet{
state = {
selectedOption: null,
}
handleChange = selectedOption => {
this.setState({ selectedOption })
// code to make something happen after selecting an option
}
render(){
return ()
}
}

We set the initial state of the selectedOption to be null meaning that there’s no value in the beginning as we haven’t selected any option.

5. What goes inside the render() function

Inside the render() function from a SearchBar class component we made above, we are going to be returning react-select props

full react-select props documentation can be found here

These are the props i’ll be using:

value — having this props will make the selected option appear in your search bar after clicking it

options — this is probably what you need for your search bar to have the suggested drop-down menu

onChange — this props takes in the function that you wrote to update the initial state. This function will depend on what you want the web to happen after an option is selected from a drop-down menu.

placeholder — takes in the string that appears initially on the search bar before the user starts typing

openMenuOnClick — prevents the option to reveal/open-up when the user clicks the search bar

Styling Props

style — for custom styling the search bar

classNamePrefix — for overriding react-select CSS className

Here is the example of what I pass through each prop. We will add the styling props to the return() method after we style the search bar first.

return (
<div>
<Select
value={selectedOption}
options={searchList}
onChange={this.handleChange}
placeholder= "Search..."
openMenuOnClick={false}
/>
</div>
)

6. Styling Search Bar

There are many ways you can style it. I used both emotion.js and react-select style key.

Emotion.js

Emotion is a CSS in JavaScript style so it is very convenient to style a React Component without having a separate .css file

npm install --save @emotion

We will be importing @emotion/styled instead because we are going to use the styled.div style API for creating components.

import styled from '@emotion/styled'

The basic styling that we are going to change is the dimension of the search bar and the style of the vertical scroll bar

const StyledSearch = styled(Select)`
width: 300px;
padding: 20px;
.select__menu-list::-webkit-scrollbar{
width: 4px;
height: 0px;
}
.select__menu-list::-webkit-scrollbar-track{
background: #f1f1f1;
}
.select__menu-list::-webkit-scrollbar-thumb{
background: #888;
}
.select__menu-list::-webkit-scrollbar-thumb:hover{
background: #555;
}
`

StyledSearch has to be capital letter because we are styling React Component

Notice className .select__menu-list for styling the vertical scroll bar. This is because we are trying to override the react-select CSS className.

Since all the className starts with .select we can give a classNamePrefix= "select" in the return method.

Updating return( ) method for Emotion.js

return (
<div>
<Select
value={selectedOption}
options={searchList}
onChange={this.handleChange}
styles={customStyles}
placeholder= "Search..."
openMenuOnClick={false}

classNamePrefix= "select"
/>
</div>
)

further documentation on styling react-select with classname here

Style Key

The next part of styling uses style key (a little bit complex).

The key i’ll be using are:

control — for styling the search box

option — for styling the dropdown menu options (the searchList)

menu — for styling the dropdown menu box

input — what the user type into the search box

singleValue — applies to the selected option that the user chooses

Here is the code sample:

Updating return( ) method for Style Key

We now need to put in the styles props in the render() method

return (
<div>
<Select
value={selectedOption}
options={searchList}
onChange={this.handleChange}
styles={customStyles}
placeholder= "Search..."
openMenuOnClick={false}

classNamePrefix= "select"
styles={customStyles}
/>
</div>
)

7. EXTRA: adding search icon

React-select comes with a dropdown indicator. If you want to change it to search-icon, you can!

First, install FortAwesome

npm install --save @fortawesome

Importing FontAwesome and its search icon

import { FontAwesomeIcon } from '@fortawesome/react-fontawesome'import { faSearch } from '@fortawesome/free-solid-svg-icons

In the render() method just before the return() statement, use a constant DropdownIndicator to change its icon to search-icon

const DropdownIndicator = props => {
return(
components.DropdownIndicator && (
<components.DropdownIndicator {...props}>
<FontAwesomeIcon icon={faSearch} />
</components.DropdownIndicators>
)
)
}

Updating return( ) method for Search-Icon

use the components props to pass down the DropdownIndicators

return (
<div>
<Select
value={selectedOption}
options={searchList}
onChange={this.handleChange}
styles={customStyles}
placeholder= "Search..."
openMenuOnClick={false}

classNamePrefix= "select"
styles={customStyles}
components={ {DropdownIndicator} }
/>
</div>
)

Resources

--

--

Penny Pang
path2code

Full-time UX/UI Designer, Part-time online entrepreneur, Casual food blogger and innovation advocate