Socket
Socket
Sign inDemoInstall

react-tailwindcss-select

Package Overview
Dependencies
3
Maintainers
1
Versions
51
Alerts
File Explorer

Advanced tools

Install Socket

Detect and block malicious and high-risk dependencies

Install

    react-tailwindcss-select

A select input made with React js and Tailwind CSS


Version published
Weekly downloads
5.6K
increased by10.46%
Maintainers
1
Install size
203 kB
Created
Weekly downloads
Β 

Readme

Source

πŸ“¦ React tailwindcss select

React-tailwindcss-select is a simple component ready to be inserted into your project
This component inspired by React-select is a select input made with Tailwindcss and React.

MIT License

Features

  • βœ… Select field for a single item
  • βœ… Selection field for multiple items
  • βœ… Optional button to clear the field
  • βœ… Optional search for an item
  • βœ… Optional deactivation of an option
  • βœ… TypeScript support
  • βœ… Group options
  • βœ… Customization of the select field style
  • ⬜ Fixed Options (multiple items select)

Why ❔

A select with the above features is above all indispensable in many projects. On a project using tailwindcss, when I install react-select or other such packages, the style of the latter is affected by that of tailwind.

Rather than looking for a component that uses tailwind, I preferred to make my own based on react-select which I like (and also because I generally like to reinvent the wheel πŸ˜…).

preview react-tailwindcss-select

Online Demo

You can find the online demo at here

Install

You can use yarn

yarn add react-tailwindcss-select

Or via npm

npm install react-tailwindcss-select

make sure you have installed the peer dependencies as well with the below versions.

"react": "^18.2.0"

Usage

This component also exports a tiny CSS file built by tailwind. All CSS classes used in designing and customizing the select component are all custom tailwind classes which ensures that an existing tailwind project would not need to include this CSS file again.

Tailwind Project

A tailwind project would only have to import the react component using import Select from 'react-tailwindcss-select' and specify the component in the tailwind configuration to generate the styles of the classes used by react-tailwindcss-select.

Use this code to add the component to the tailwind configuration

// in your tailwind.config.js
module.exports = {
    // ...
    content: [
        "./src/**/*.{js,jsx,ts,tsx}",
        "./node_modules/react-tailwindcss-select/dist/index.esm.js"
    ]
    // ...
};

None Tailwind Project

On a project that does not use tailwind, you need to import the component's CSS as well. To do this use these two codes: import Select from 'react-tailwindcss-select' and import 'react-tailwindcss-select/dist/index.css'

Warning

In this case when you don't use tailwind on your project, think about isolating the component and its style so that tailwind doesn't affect the style of the elements in your project. For this, you can use the shadow dom.

Then use react-tailwindcss-select in your app:

With React Component
import React from "react";
import Select from "react-tailwindcss-select";

const options = [
    { value: "fox", label: "🦊 Fox" },
    { value: "Butterfly", label: "πŸ¦‹ Butterfly" },
    { value: "Honeybee", label: "🐝 Honeybee" }
];

class App extends React.Component {
    constructor(props) {
        super(props);
        this.state = { animal: null };

        this.handleChange = this.handleChange.bind(this);
    }

    handleChange(value) {
        console.log("value:", value);
        this.setState({ animal: value });
    }

    render() {
        const { animal } = this.state;

        return (
            <Select
                value={animal}
                onChange={this.handleChange}
                options={options}
            />
        );
    }
}
With React Hooks
import { useState } from "react";
import Select from "react-tailwindcss-select";

const options = [
    { value: "fox", label: "🦊 Fox" },
    { value: "Butterfly", label: "πŸ¦‹ Butterfly" },
    { value: "Honeybee", label: "🐝 Honeybee" }
];

const App = () => {
    const [animal, setAnimal] = useState(null);

    const handleChange = value => {
        console.log("value:", value);
        setAnimal(value);
    };

    return (
        <Select
            value={animal}
            onChange={handleChange}
            options={options}
        />
    );
};

export default App;

Theming options

Supported themes Theme supported

To change the default theme, simply add the primaryColor props to your select field with the theme value. By default, the primaryColor is set to blue

Indigo example

import { useState } from "react";
import Select from "react-tailwindcss-select";

const options = [
    { value: "fox", label: "🦊 Fox" },
    { value: "Butterfly", label: "πŸ¦‹ Butterfly" },
    { value: "Honeybee", label: "🐝 Honeybee" }
];

const App = () => {
    const [animal, setAnimal] = useState(null);

    const handleChange = value => {
        console.log("value:", value);
        setAnimal(value);
    };

    return (
        <Select
            primaryColor={"indigo"}
            value={animal}
            onChange={handleChange}
            options={options}
        />
    );
};

export default App;

Props

This table shows all the options available in react-tailwindcss-select.

OptionTypeDefaultDescription
classNamesObjectundefinedThis prop allows you to style most of the components used by this library.
isClearableBooleantrueIndicates if you can empty the select field.
isDisabledBooleanfalseIndicates if you can disable the select field.
isMultipleBooleanfalseIndicates if you can do a multiple selection.
isSearchableBooleantrueIndicates if you can search the elements of the select field.
formatGroupLabelFunctionnullAllows you to use a custom rendering template for each subgroup title
formatOptionLabelFunctionnullAllows you to use a custom rendering template for each option in the list
loadingBooleanfalseIndicates if you want a loader to appear in the field.
menuIsOpenBooleanfalseIndicates if you want the options menu to be displayed by default.
noOptionsMessageStringNo results foundDefault message when there is no option in the select field.
onChangeFunctionThis callback, if present, is triggered when the select field value is modified.
onSearchInputChangeFunctionThis callback, if present, is triggered when the search input field value is modified.
optionsArray[]All options or options groups available in the selection field.
placeholderStringSelect...The placeholder shown for the select field.
primaryColorStringblueDefault theme of the field.
searchInputPlaceholderStringSearch...The placeholder shown for the search input field.
valueObjectnullCurrent value of select field.

onChange

This callback, if present, is triggered when the select field value is modified. This callback takes as a parameter the current value(s) selected. These values respect the same structure as the elements of the options.

currentValue => {
    console.log("currentValue:", currentValue);
};

onSearchInputChange

This callback, if present, is triggered when the search input field value is modified. This callback takes as parameter a React.ChangeEvent<HTMLInputElement>.

e => {
    console.log("value:", e.target.value);
};

options

All options are available in the select field. Each option element must have a value property that serves as an identifier for the element, a label property that is the text that is displayed in the options list, and an optional disabled property to specify whether the element is active.

// default element
const options = [{ value: "fox", label: "🦊 Fox" }];
// default element with `disabled`
const options = [{ value: "fox", label: "🦊 Fox", disabled: true }];
Group item

If you want to group options you can use the following code.

const options = [
    {
        label: "Mammal",
        options: [
            { value: "Dolphin", label: "🐬 Dolphin" },
            { value: "Giraffe", label: "πŸ¦’ Giraffe" }
        ]
    },
    {
        label: "Carnivore",
        options: [
            { value: "Tiger", label: "πŸ… Tiger" },
            { value: "Lion", label: "🦁 Lion" }
        ]
    },
    // πŸ‘‰ You can put the grouped and ungrouped options together
    { value: "Zombie", label: "🧟 Zombie" }
];

Info

πŸ‘‰ You can put the grouped and ungrouped options together.

value

The current value of the select field. These objects must follow the same structure as an options element. Thus, the following would work:

// default element Simple Select
const value = { value: "fox", label: "🦊 Fox" };
// default element with `disabled` Simple Select
const value = { value: "fox", label: "🦊 Fox", disabled: true };
// default element Multiple Select
const value = [{ value: "fox", label: "🦊 Fox" }];
// default element with `disabled` Multiple Select
const value = [{ value: "fox", label: "🦊 Fox", disabled: true }];

formatGroupLabel

formatGroupLabel allows you to use a custom rendering template for each subgroup title

import { useState } from "react";
import Select from "react-tailwindcss-select";

const options = [
    {
        label: "Mammal",
        options: [
            { value: "Dolphin", label: "🐬 Dolphin" },
            { value: "Giraffe", label: "πŸ¦’ Giraffe" }
        ]
    },
    {
        label: "Carnivore",
        options: [
            { value: "Tiger", label: "πŸ… Tiger" },
            { value: "Lion", label: "🦁 Lion" }
        ]
    }
];

const App = () => {
    const [animal, setAnimal] = useState(null);

    const handleChange = value => {
        console.log("value:", value);
        setAnimal(value);
    };

    return (
        <Select
            value={animal}
            onChange={handleChange}
            options={options}
            isMultiple={true}
            formatGroupLabel={data => (
                <div className={`py-2 text-xs flex items-center justify-between`}>
                    // πŸ‘‰ data represents each subgroup
                    <span className="font-bold">{data.label}</span>
                    <span className="bg-gray-200 h-5 h-5 p-1.5 flex items-center justify-center rounded-full">
                        {data.options.length}
                    </span>
                </div>
            )}
        />
    );
};

export default App;

Info

πŸ‘‰ data represents each subgroup.

formatOptionLabel

formatOptionLabel allows you to use a custom rendering template for each option in the list.

import { useState } from "react";
import Select from "react-tailwindcss-select";

const options = [
    { value: "fox", label: "🦊 Fox" },
    { value: "Butterfly", label: "πŸ¦‹ Butterfly" },
    { value: "Honeybee", label: "🐝 Honeybee" }
];

const App = () => {
    const [animal, setAnimal] = useState(null);

    const handleChange = value => {
        console.log("value:", value);
        setAnimal(value);
    };

    return (
        <Select
            value={animal}
            onChange={handleChange}
            options={options}
            formatOptionLabel={data => (
                <li
                    className={`block transition duration-200 px-2 py-2 cursor-pointer select-none truncate rounded ${
                        !data.isSelected
                            ? `text-white bg-blue-500`
                            : `bg-blue-100 text-blue-500`
                    }`}
                >
                    // data represents each option in the list
                    {data.label}
                </li>
            )}
        />
    );
};

export default App;

Info

πŸ‘‰ data represents each option in the list.

classNames

As of version 1.6.0 of react-tailwindcss-select you can now use the classNames prop for styling.

Info

πŸ‘‰ Note: this is not to be confused with the className prop, which will add a class to the component.

classNames takes an object with keys to represent the various inner components that react-tailwindcss-select is made up of.

Each key takes a callback function or a string. If a key is not filled in, the default classes of the component will be used.

All keys
interface SelectProps {
    // ....
    classNames?: {
        menuButton?: (value?: { isDisabled?: boolean }) => string;
        menu?: string;
        tagItem?: (value?: { item?: Option, isDisabled?: boolean }) => string;
        tagItemText?: string;
        tagItemIconContainer?: string;
        tagItemIcon?: string;
        list?: string;
        listGroupLabel?: string;
        listItem?: (value?: { isSelected?: boolean }) => string;
        listDisabledItem?: string;
        ChevronIcon?: (value?: { open?: boolean }) => string;
        searchContainer?: string;
        searchBox?: string;
        searchIcon?: string;
        closeIcon?: string;
    };
    // ...
}
Example of a custom style
import { useState } from "react";
import Select from "react-tailwindcss-select";

const options = [
    { value: "fox", label: "🦊 Fox" },
    { value: "Butterfly", label: "πŸ¦‹ Butterfly" },
    { value: "Honeybee", label: "🐝 Honeybee" }
];

const App = () => {
    const[animal, setAnimal] =useState(null);

    const handleChange = value => {
        console.log("value:", value);
        setAnimal(value);
    };

    return(
        <Select
            value={animal}
            onChange={handleChange}
            options={options}
            classNames={{
                menuButton: ({ isDisabled }) => (
                    `flex text-sm text-gray-500 border border-gray-300 rounded shadow-sm transition-all duration-300 focus:outline-none ${
                        isDisabled
                            ? "bg-gray-200"
                            : "bg-white hover:border-gray-400 focus:border-blue-500 focus:ring focus:ring-blue-500/20"
                    }`
                ),
                menu: "absolute z-10 w-full bg-white shadow-lg border rounded py-1 mt-1.5 text-sm text-gray-700",
                listItem: ({ isSelected }) => (
                    `block transition duration-200 px-2 py-2 cursor-pointer select-none truncate rounded ${
                        isSelected
                            ? `text-white bg-blue-500`
                            : `text-gray-500 hover:bg-blue-100 hover:text-blue-500`
                    }`
                )
            }}
        />
    );
};

export default App;

PlayGround

Clone the master branch and run commands:

# Using npm
npm install && npm dev

# Using yarn
yarn install && yarn dev

Open a browser and navigate to http://localhost:8888

Contributing

Got ideas on how to make this better? Open an issue!

Don't forget to see CONTRIBUTING.md

Thanks

This component is inspired by the excellent react-select library by Jed Watson.

I thank you in advance for your contribution to this project.

License

MIT Licensed. Copyright (c) Lewhe Onesine 2022.

Keywords

FAQs

Last updated on 11 Mar 2023

Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Install

Related posts

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚑️ by Socket Inc