Conditional Class Names
In this page:
Building a className with a Ternary
The simplest way to conditionally apply a class is a ternary expression directly inside the className prop, choosing between two class name strings based on a boolean condition, like whether a button is active or disabled.
Note: For just one or two conditions, a plain ternary is perfectly readable and needs no extra library.
Warning: Ternaries nested inside more ternaries inside a className string quickly become unreadable — that's the point to reach for a helper library.
Example: Building a className with a Ternary
<!DOCTYPE html>
<html>
<head>
<script src="https://unpkg.com/react@18/umd/react.development.js"></script>
<script src="https://unpkg.com/react-dom@18/umd/react-dom.development.js"></script>
<script src="https://unpkg.com/@babel/standalone/babel.min.js"></script>
</head>
<body>
<div id="root"></div>
<script type="text/babel">
function App() {
const [active, setActive] = React.useState(false);
return <button className={active ? "btn active" : "btn"} onClick={() => setActive(!active)}>Toggle</button>;
}
ReactDOM.createRoot(document.getElementById('root')).render(<App />);
</script>
</body>
</html>
Combining a Base Class with Modifiers
A common pattern is always applying a base class (like btn) plus zero or more modifier classes (like btn-primary or btn-disabled) depending on props, built up with a template literal that conditionally includes each modifier.
Note: This mirrors the BEM CSS naming convention (block__element--modifier), which pairs naturally with this pattern.
Warning: Forgetting a leading space between the base class and a conditionally-added modifier merges them into one invalid class name string.
Example: Combining a Base Class with Modifiers
<!DOCTYPE html>
<html>
<head>
<script src="https://unpkg.com/react@18/umd/react.development.js"></script>
<script src="https://unpkg.com/react-dom@18/umd/react-dom.development.js"></script>
<script src="https://unpkg.com/@babel/standalone/babel.min.js"></script>
</head>
<body>
<div id="root"></div>
<script type="text/babel">
function Button({ primary, disabled, children }) {
const className = `btn${primary ? " btn-primary" : ""}${disabled ? " btn-disabled" : ""}`;
return <button className={className} disabled={disabled}>{children}</button>;
}
ReactDOM.createRoot(document.getElementById('root')).render(<Button primary>Click</Button>);
</script>
</body>
</html>
Using a Helper Library for Complex Cases
Libraries like clsx or classnames take an object where keys are class names and values are booleans, automatically joining only the true ones into a final string. This scales much better than manual string building once you have several independent conditions.
Note: clsx({ active: isActive, disabled: isDisabled }) reads clearly even with several conditions at once.
Warning: It's a small npm package — it needs to be installed; there's no CDN-runnable equivalent shown here since it's a tiny, commonly-bundled utility.
Example: Using a Helper Library for Complex Cases
// Run in your local React project (npm install required)
import clsx from 'clsx';
function Button({ active, disabled, children }) {
return <button className={clsx('btn', { active, disabled })}>{children}</button>;
}
⚠️ This example uses an npm package with no CDN build available here — run this in your local React project.
- Building className strings with error-prone manual string concatenation instead of a helper like clsx or classnames.
- Forgetting a space when concatenating multiple classes manually, accidentally merging two class names into one invalid one.
- Applying a conditional class but forgetting to actually define any CSS rule for it.
- A component's className can be built dynamically based on props or state using template literals or ternaries.
- Libraries like clsx or classnames simplify combining multiple conditional classes cleanly.
- A common pattern is a base class always applied, plus conditional modifier classes.
- Conditional classes only have a visible effect if matching CSS rules actually exist for them.
No React-version restriction — template literals and ternaries are plain JavaScript.
Chapter Quiz — Complete all 8 topics to unlock
0/8 topics done
Complete these topics first: