Convert Figma logo to code with AI

reactjs logoreact-tabs

An accessible and easy tab component for ReactJS.

3,076
446
3,076
62

Top Related Projects

The Accessible Foundation for React Apps and Design Systems

Material UI: Comprehensive React component library that implements Google's Material Design. Free forever.

An enterprise-class UI design language and React UI library

Bootstrap components built with React

The Select Component for React.js

12,045

🏎 A set of primitives to build simple, flexible, WAI-ARIA compliant React autocomplete, combobox or select dropdown components.

Quick Overview

React-Tabs is a lightweight and accessible tab component for React applications. It provides a simple way to create tabbed interfaces with minimal setup, while ensuring proper accessibility and keyboard navigation.

Pros

  • Easy to use and integrate into existing React projects
  • Fully accessible, following WAI-ARIA guidelines
  • Customizable styling and behavior
  • Lightweight with minimal dependencies

Cons

  • Limited built-in styling options
  • May require additional configuration for complex use cases
  • Documentation could be more comprehensive
  • Lacks some advanced features found in larger UI libraries

Code Examples

Creating a basic tab interface:

import { Tab, Tabs, TabList, TabPanel } from 'react-tabs';
import 'react-tabs/style/react-tabs.css';

function MyTabs() {
  return (
    <Tabs>
      <TabList>
        <Tab>Title 1</Tab>
        <Tab>Title 2</Tab>
      </TabList>

      <TabPanel>
        <h2>Content 1</h2>
        <p>Tab content goes here</p>
      </TabPanel>
      <TabPanel>
        <h2>Content 2</h2>
        <p>More tab content</p>
      </TabPanel>
    </Tabs>
  );
}

Using custom styling:

import { Tab, Tabs, TabList, TabPanel } from 'react-tabs';

function StyledTabs() {
  return (
    <Tabs
      selectedTabClassName="bg-blue-500 text-white"
      selectedTabPanelClassName="border-blue-500"
    >
      <TabList className="flex border-b">
        <Tab className="px-4 py-2 cursor-pointer">Tab 1</Tab>
        <Tab className="px-4 py-2 cursor-pointer">Tab 2</Tab>
      </TabList>

      <TabPanel className="p-4 border-l border-r border-b">
        <h2>Content 1</h2>
      </TabPanel>
      <TabPanel className="p-4 border-l border-r border-b">
        <h2>Content 2</h2>
      </TabPanel>
    </Tabs>
  );
}

Handling tab selection:

import { Tab, Tabs, TabList, TabPanel } from 'react-tabs';

function TabsWithCallback() {
  const handleSelect = (index, lastIndex, event) => {
    console.log(`Selected tab: ${index}`);
  };

  return (
    <Tabs onSelect={handleSelect}>
      <TabList>
        <Tab>Tab 1</Tab>
        <Tab>Tab 2</Tab>
      </TabList>
      <TabPanel>Content 1</TabPanel>
      <TabPanel>Content 2</TabPanel>
    </Tabs>
  );
}

Getting Started

  1. Install the package:

    npm install react-tabs
    
  2. Import the components and styles:

    import { Tab, Tabs, TabList, TabPanel } from 'react-tabs';
    import 'react-tabs/style/react-tabs.css';
    
  3. Use the components in your React application:

    function App() {
      return (
        <Tabs>
          <TabList>
            <Tab>Tab 1</Tab>
            <Tab>Tab 2</Tab>
          </TabList>
          <TabPanel>Content for Tab 1</TabPanel>
          <TabPanel>Content for Tab 2</TabPanel>
        </Tabs>
      );
    }
    

Competitor Comparisons

The Accessible Foundation for React Apps and Design Systems

Pros of reach-ui

  • More comprehensive UI component library, offering a wider range of accessible components beyond just tabs
  • Follows WAI-ARIA design patterns, ensuring better accessibility out of the box
  • Provides a more flexible and customizable API for advanced use cases

Cons of reach-ui

  • Larger bundle size due to the inclusion of multiple components
  • Steeper learning curve for developers who only need a simple tab component
  • Less focused on tabs specifically, which may result in fewer tab-specific features

Code Comparison

reach-ui:

import { Tabs, TabList, Tab, TabPanels, TabPanel } from "@reach/tabs";

<Tabs>
  <TabList>
    <Tab>Tab 1</Tab>
    <Tab>Tab 2</Tab>
  </TabList>
  <TabPanels>
    <TabPanel>Content 1</TabPanel>
    <TabPanel>Content 2</TabPanel>
  </TabPanels>
</Tabs>

react-tabs:

import { Tabs, TabList, Tab, TabPanel } from "react-tabs";

<Tabs>
  <TabList>
    <Tab>Tab 1</Tab>
    <Tab>Tab 2</Tab>
  </TabList>
  <TabPanel>Content 1</TabPanel>
  <TabPanel>Content 2</TabPanel>
</Tabs>

Both libraries offer similar syntax for basic tab functionality, but reach-ui provides a separate TabPanels component for better organization.

Material UI: Comprehensive React component library that implements Google's Material Design. Free forever.

Pros of Material-UI

  • Comprehensive UI component library with a wide range of pre-built components
  • Implements Google's Material Design principles for a consistent and modern look
  • Extensive customization options and theming support

Cons of Material-UI

  • Larger bundle size due to its extensive feature set
  • Steeper learning curve for developers new to Material Design concepts
  • May require more setup and configuration for basic use cases

Code Comparison

Material-UI tabs implementation:

import { Tabs, Tab } from '@mui/material';

<Tabs value={value} onChange={handleChange}>
  <Tab label="Item One" />
  <Tab label="Item Two" />
  <Tab label="Item Three" />
</Tabs>

React-Tabs implementation:

import { Tabs, TabList, Tab, TabPanel } from 'react-tabs';

<Tabs>
  <TabList>
    <Tab>Title 1</Tab>
    <Tab>Title 2</Tab>
    <Tab>Title 3</Tab>
  </TabList>
  <TabPanel>Content 1</TabPanel>
  <TabPanel>Content 2</TabPanel>
  <TabPanel>Content 3</TabPanel>
</Tabs>

Material-UI offers a more comprehensive solution with additional features and styling options, while React-Tabs provides a simpler, more lightweight approach focused specifically on tab functionality. The choice between the two depends on project requirements, design preferences, and the need for additional UI components beyond tabs.

An enterprise-class UI design language and React UI library

Pros of Ant Design

  • Comprehensive UI component library with a wide range of components beyond just tabs
  • Consistent and polished design system with customizable themes
  • Extensive documentation and active community support

Cons of Ant Design

  • Larger bundle size due to its comprehensive nature
  • Steeper learning curve for developers new to the library
  • May require additional configuration for optimal performance in smaller projects

Code Comparison

React Tabs:

import { Tab, Tabs, TabList, TabPanel } from 'react-tabs';

<Tabs>
  <TabList>
    <Tab>Title 1</Tab>
    <Tab>Title 2</Tab>
  </TabList>
  <TabPanel>Content 1</TabPanel>
  <TabPanel>Content 2</TabPanel>
</Tabs>

Ant Design:

import { Tabs } from 'antd';

<Tabs>
  <Tabs.TabPane tab="Title 1" key="1">
    Content 1
  </Tabs.TabPane>
  <Tabs.TabPane tab="Title 2" key="2">
    Content 2
  </Tabs.TabPane>
</Tabs>

Both libraries offer similar functionality for creating tab components, but Ant Design provides a more concise syntax. React Tabs focuses specifically on tab functionality, while Ant Design offers a broader range of components and styling options. The choice between the two depends on project requirements, desired customization level, and overall UI consistency needs.

Bootstrap components built with React

Pros of react-bootstrap

  • Comprehensive UI component library with a wide range of pre-built components
  • Consistent styling and theming based on Bootstrap's design system
  • Active development and large community support

Cons of react-bootstrap

  • Larger bundle size due to the extensive component library
  • Less flexibility in customizing individual components compared to react-tabs
  • Steeper learning curve for developers unfamiliar with Bootstrap

Code Comparison

react-bootstrap:

import { Tabs, Tab } from 'react-bootstrap';

<Tabs defaultActiveKey="profile" id="uncontrolled-tab-example">
  <Tab eventKey="home" title="Home">
    <p>Home content</p>
  </Tab>
  <Tab eventKey="profile" title="Profile">
    <p>Profile content</p>
  </Tab>
</Tabs>

react-tabs:

import { Tabs, TabList, Tab, TabPanel } from 'react-tabs';

<Tabs>
  <TabList>
    <Tab>Home</Tab>
    <Tab>Profile</Tab>
  </TabList>
  <TabPanel>
    <p>Home content</p>
  </TabPanel>
  <TabPanel>
    <p>Profile content</p>
  </TabPanel>
</Tabs>

The code comparison shows that react-bootstrap offers a more concise syntax for creating tabs, while react-tabs provides more granular control over the tab structure. react-bootstrap's approach may be easier for quick implementations, whereas react-tabs allows for more customization of the tab components.

The Select Component for React.js

Pros of react-select

  • More versatile: Offers advanced features like multi-select, async loading, and custom styling
  • Highly customizable: Provides extensive theming and component customization options
  • Active development: Regularly updated with new features and bug fixes

Cons of react-select

  • Steeper learning curve: More complex API due to its extensive feature set
  • Larger bundle size: Includes more functionality, which may impact performance for simpler use cases

Code Comparison

react-select:

import Select from 'react-select';

const options = [
  { value: 'chocolate', label: 'Chocolate' },
  { value: 'strawberry', label: 'Strawberry' },
  { value: 'vanilla', label: 'Vanilla' }
];

<Select options={options} />

react-tabs:

import { Tab, Tabs, TabList, TabPanel } from 'react-tabs';

<Tabs>
  <TabList>
    <Tab>Title 1</Tab>
    <Tab>Title 2</Tab>
  </TabList>
  <TabPanel>Content 1</TabPanel>
  <TabPanel>Content 2</TabPanel>
</Tabs>

While react-select focuses on creating customizable dropdown menus, react-tabs is designed specifically for tabbed interfaces. react-select offers more flexibility for various selection scenarios, while react-tabs provides a simpler API for tab-based content organization. The choice between the two depends on the specific requirements of your project.

12,045

🏎 A set of primitives to build simple, flexible, WAI-ARIA compliant React autocomplete, combobox or select dropdown components.

Pros of downshift

  • More flexible and customizable, allowing for complex UI patterns beyond tabs
  • Provides low-level primitives for building accessible autocomplete, dropdown, and select components
  • Smaller bundle size and fewer dependencies

Cons of downshift

  • Requires more setup and configuration for basic use cases
  • Less opinionated, which may lead to inconsistent implementations across projects
  • Steeper learning curve for developers new to the library

Code Comparison

downshift:

<Downshift
  onChange={selection => console.log(selection)}
  itemToString={item => (item ? item.name : '')}
>
  {({ getInputProps, getItemProps, isOpen, inputValue, selectedItem, highlightedIndex }) => (
    <div>
      <input {...getInputProps()} />
      {isOpen && (
        <div>
          {items
            .filter(item => !inputValue || item.name.includes(inputValue))
            .map((item, index) => (
              <div
                {...getItemProps({
                  key: item.id,
                  index,
                  item,
                  style: {
                    backgroundColor: highlightedIndex === index ? 'lightgray' : 'white',
                    fontWeight: selectedItem === item ? 'bold' : 'normal',
                  },
                })}
              >
                {item.name}
              </div>
            ))}
        </div>
      )}
    </div>
  )}
</Downshift>

react-tabs:

<Tabs>
  <TabList>
    <Tab>Title 1</Tab>
    <Tab>Title 2</Tab>
  </TabList>

  <TabPanel>
    <h2>Any content 1</h2>
  </TabPanel>
  <TabPanel>
    <h2>Any content 2</h2>
  </TabPanel>
</Tabs>

Convert Figma logo designs to code with AI

Visual Copilot

Introducing Visual Copilot: A new AI model to turn Figma designs to high quality code using your components.

Try Visual Copilot

README

react-tabs npm version codecov

An accessible and easy tab component for ReactJS.

https://reactcommunity.org/react-tabs/

Version 5 or newer of react-tabs needs react version 18 or newer

Version 4 of react-tabs needs react version 16.8 or newer

react-tabs was tested on real mobile devices and browsers with
Browserstack

Installing

yarn add react-tabs

or

npm install --save react-tabs

Basic Example

import { Tab, Tabs, TabList, TabPanel } from 'react-tabs';
import 'react-tabs/style/react-tabs.css';

export default () => (
  <Tabs>
    <TabList>
      <Tab>Title 1</Tab>
      <Tab>Title 2</Tab>
    </TabList>

    <TabPanel>
      <h2>Any content 1</h2>
    </TabPanel>
    <TabPanel>
      <h2>Any content 2</h2>
    </TabPanel>
  </Tabs>
);

API

Components

react-tabs consists of 4 components which all need to be used together.

<Tabs />

If you specify additional props on the <Tabs /> component they will be forwarded to the rendered <div />.

className: string | Array<string> | { [string]: boolean }

default: "react-tabs"

Provide a custom class name for the outer <div /> of the tabs.

You can also supply an array of class names or an object where the class names are the key and the value is a boolean indicating if the name should be added. See the docs of classnames on how to supply different class names.

defaultFocus: boolean

default: false

If set to true the tabs will be focused on initial render. This allows immediate use of keyboard keys to switch tabs after the first render.

defaultIndex: number

default: 0

This allows changing the tab that should be open on initial render. This is a zero-based index, so first tab is 0, second tab is 1, ...

This can only be used in uncontrolled mode when react-tabs handles the current selected tab internally and for this reason cannot be used together with selectedIndex. See here for more info on modes.

direction: string

default: "ltr"

Provide the direction of the component, can be either rtl or ltr.

disabledTabClassName: string

default: "react-tabs__tab--disabled"

Provide a custom class name for disabled tabs.

This option can also be set directly at the <Tab /> component.

disableUpDownKeys: bool

default: false

Disable up & down arrow keys to change tabs.

domRef: (node: ?HTMLElement) => void

default: null

Register a callback that will receive the underlying DOM node for every mount. It will also receive null on unmount.

environment: Window

If you're rendering react-tabs within a different window context than the default one; for example, an iframe.

focusTabOnClick: boolean

default: true

By default the tab that is clicked will also be focused in the DOM. If set to false the tab will not be focused anymore.

Be aware that keyboard navigation will not work after click if set to false. Though one can still focus the tabs by pressing tab and then keyboard navigation will work.

forceRenderTabPanel: boolean

default: false

By default only the current active tab will be rendered to DOM. If set to true all tabs will be rendered to the DOM always.

This can also be enabled for each individual <TabPanel /> component with its prop forceRender.

onSelect: (index: number, lastIndex: number, event: Event) => ?boolean

default: undefined

This event handler is called every time a tab is about to change. It will be called with the index that it will be changed to, the lastIndex which was selected before and the underlying event which is usually either a keydown or click event. When index and lastIndex are equal it means the user clicked on the currently active tab.

The callback can optionally return false to cancel the change to the new tab.

Returning false when the change to the new tab should be canceled is also important in controlled mode, as react-tabs still internally handles the focus of the tabs.

In controlled mode the onSelect handler is a required prop.

selectedIndex: number

default: null

Set the currently selected tab. This is a zero-based index, so first tab is 0, second tab is 1, ...

This enables controlled mode, which also requires onSelect to be set. See here for more info on modes.

selectedTabClassName: string

default: "react-tabs__tab--selected"

Provide a custom class name for the active tab.

This option can also be set directly at the <Tab /> component.

selectedTabPanelClassName: string

default: "react-tabs__tab-panel--selected"

Provide a custom class name for the active tab panel.

This option can also be set directly at the <TabPanel /> component.

<TabList />

If you specify additional props on the <TabList /> component they will be forwarded to the rendered <ul />.

className: string | Array<string> | { [string]: boolean }

default: "react-tabs__tab-list"

Provide a custom class name for the <ul />.

You can also supply an array of class names or an object where the class names are the key and the value is a boolean indicating if the name should be added. See the docs of classnames on how to supply different class names.

<Tab />

If you specify additional props on the <Tab /> component they will be forwarded to the rendered <li />.

className: string | Array<string> | { [string]: boolean }

default: "react-tabs__tab"

Provide a custom class name for the <li />.

You can also supply an array of class names or an object where the class names are the key and the value is a boolean indicating if the name should be added. See the docs of classnames on how to supply different class names.

disabled: boolean

default: false

Disable this tab which will make it not do anything when clicked. Also a disabled class name will be added (see disabledClassName)

disabledClassName: string

default: "react-tabs__tab--disabled"

Provide a custom class name for disabled tabs.

This option can also be set for all <Tab /> components with the prop disabledTabClassName on <Tabs />.

selectedClassName: string

default: "react-tabs__tab--selected"

Provide a custom class name for the active tab.

This option can also be set for all <Tab /> components with the prop selectedTabClassName on <Tabs />.

tabIndex: string

default: if selected "0" otherwise null

Overrides the tabIndex to enabled tabbing between tabs.

<TabPanel />

If you specify additional props on the <TabPanel /> component they will be forwarded to the rendered <div />.

className: string | Array<string> | { [string]: boolean }

default: "react-tabs__tab-panel"

Provide a custom class name for the <div /> containing the tab content.

You can also supply an array of class names or an object where the class names are the key and the value is a boolean indicating if the name should be added. See the docs of classnames on how to supply different class names.

forceRender: boolean

default: false

By default the tab content will only be rendered when the tab is active. If set to true the tab will also be rendered if inactive.

This can also be enabled for all <TabPanel /> components with the prop forceRenderTabPanel on <Tabs />.

selectedClassName: string

default: "react-tabs__tab-panel--selected"

Provide a custom class name for the active tab panel.

This option can also be set for all <TabPanel /> components with the prop selectedTabPanelClassName on <Tabs />.

Controlled vs Uncontrolled mode

React tabs has two different modes it can operate in, which change the way how much you need to take care about the state yourself.

Uncontrolled mode

This is the default mode of react-tabs and makes the react-tabs components handle its state internally. You can change the starting tab with defaultIndex and you can listen for changes with onSelect.

In this mode you cannot force a tab change during runtime.

<Tabs defaultIndex={1} onSelect={(index) => console.log(index)}>
  <TabList>
    <Tab>Title 1</Tab>
    <Tab>Title 2</Tab>
  </TabList>
  <TabPanel></TabPanel>
  <TabPanel></TabPanel>
</Tabs>

Controlled mode

This mode has to be enabled by supplying selectedIndex to the <Tabs /> component.

In this mode react-tabs does not handle any tab selection state internally and leaves all the state management up to the outer application.

This mode also enforces you to set a handler for onSelect. defaultIndex does not have any effect and will therefore throw an error.

const App = () => {
  const [tabIndex, setTabIndex] = useState(0);

  return (
    <Tabs selectedIndex={tabIndex} onSelect={(index) => setTabIndex(index)}>
      <TabList>
        <Tab>Title 1</Tab>
        <Tab>Title 2</Tab>
      </TabList>
      <TabPanel></TabPanel>
      <TabPanel></TabPanel>
    </Tabs>
  );
};

Styling

react-tabs does not include any style loading by default. Default stylesheets are provided and can be included in your application if desired.

Webpack

When using webpack and an appropriate loader (css-loader, sass-loader, less-loader or style-loader) you can simply import the default stylesheet.

import 'react-tabs/style/react-tabs.css';
// or
import 'react-tabs/style/react-tabs.scss';
// or
import 'react-tabs/style/react-tabs.less';

SASS

When using SASS you can easily import the default styles

@import '../../path/to/node_modules/react-tabs/style/react-tabs.scss';

LESS

When using LESS you can easily import the default styles

@import '../../path/to/node_modules/react-tabs/style/react-tabs.less';

Custom Style

You can also always just simply copy the default style to your own css/scss/less and modify it to your own needs. The changelog will always tell you when classes change and we also consider changes that break the styling as semver major.

Custom Components

Set tabsRole

In case you want to create your own component wrapping the ones that the library provides, you have to set its tabsRole. This value is used inside react-tabs to check the role of a component inside <Tabs />.

Possible values for tabsRole are:

  • Tab
  • TabPanel
  • TabList
  • Tabs

Pass through properties

Note: Because of how react-tabs works internally (it uses cloning to opaquely control various parts of the tab state), you need to pass any incoming props to the component you're wrapping. The easiest way to do this is to use the rest and spread operators, e.g. see {...otherProps} below.

import { Tabs, TabList, Tab, TabPanel } from 'react-tabs';
import type { ReactTabsFunctionComponent, TabProps } from 'react-tabs';

// All custom elements should pass through other props
const CustomTab: ReactTabsFunctionComponent<TabProps> = ({
  children,
  ...otherProps
}) => (
  <Tab {...otherProps}>
    <h1>{children}</h1>
  </Tab>
);

CustomTab.tabsRole = 'Tab'; // Required field to use your custom Tab

const App = () => (
  <Tabs>
    <TabList>
      <CustomTab>Custom Tab 1</CustomTab>
      <CustomTab>Custom Tab 2</CustomTab>
    </TabList>
    <TabPanel>Panel 1</TabPanel>
    <TabPanel>Panel 2</TabPanel>
  </Tabs>
);

License

MIT

NPM DownloadsLast 30 Days