Dynamic Styling in Tailwind
Published on
Tailwind generates CSS at build time. Class names must be statically analyzable, which means anything that depends on runtime values is outside of the compiler’s reach.
This is why expressions like h-[${height}] don’t work in Tailwind.
Once this constraint is clear, most dynamic styling problems fall into two categories:
- Switching between known styles
- Injecting new values at runtime
Conditional Class Selection
The simplest case is choosing between predefined classes. Using ternaries or helpers like cn works as long as all possible class names are known ahead of time.
<div
className={cn({
'w-16': !expanded,
'w-64': expanded,
})}
/>Attribute-Derived Styling
When styling depends on component state, it’s usually better to reflect that state directly in the DOM. ARIA attributes likearia-expanded and custom data-* attributes can represent the current component state. Styles derive from those attributes instead of duplicating the same conditions inclassName.
<div
aria-expanded={expanded}
className="w-16 aria-expanded:w-64"
/>Related Article: Attribute-Derived Styling.Passing Runtime Values with CSS Variables
Widths, offsets, or other values that are only known at runtime cannot be encoded into Tailwind classes. CSS variables are the only way to pass those values through while keeping the class name static.
<div
style={{ '--panel-width': ${width}px }}
className="w-[var(--panel-width)]"
/>