Skip to main content
Tailwind CSS provides two directives for creating custom variants: @variant for applying existing variants within custom utilities and nested CSS, and @custom-variant for defining entirely new variant modifiers.

@variant Directive

The @variant directive applies an existing variant to a block of CSS, creating the appropriate selector transformations.

Syntax

Basic Usage

Use @variant to apply conditional styling within custom utilities:
This generates:

Using with @custom-variant

You can use @variant with custom variants defined via @custom-variant:

Nested @variant

@variant can be used within custom utilities or @custom-variant bodies:

@custom-variant Directive

The @custom-variant directive defines new variant modifiers that can be used throughout your CSS.

Syntax

Creating Custom Variants

Body-less Selector Variant

Define simple variants with comma-separated selectors:
Use it with utilities:
Generated CSS:

Multiple Selectors

Combine different selector types:

At-Rule Variants

Create variants with media queries or other at-rules:
Generated CSS:

Body Syntax with @slot

For more complex variants, use the body syntax with @slot as a placeholder:
The @slot directive marks where the utility CSS should be inserted.

Nested Structure

Create complex selector structures:

Variant Naming Rules

string
Variant names must:
  • Start with a lowercase letter or number
  • Contain only alphanumeric characters, hyphens, or underscores
  • Not end with a hyphen or underscore
  • Match the pattern: /^@?[a-z0-9][a-zA-Z0-9_-]*(?<![_-])$/

Compound Variants

Use custom variants with compound modifiers like group and peer:

Variant Dependencies

Custom variants can use other custom variants:
Circular dependencies between variants will cause an error.
Error message:

Restrictions

Top-level Only

@custom-variant must be defined at the top level and cannot be nested.

Selector or Body Required

Body-less variants must have a selector. Variants with a body must have @slot.

Cannot Mix Selector and Body

You cannot use both a selector parameter and a body.

Valid Selectors

Selector lists cannot be empty or contain empty selectors.

Compound Capabilities

Custom variants can specify what types of selectors they work with:
  • StyleRules: Works with CSS selectors (:hover, .class, etc.)
  • AtRules: Works with at-rules (@media, @supports, etc.)
  • Never: Cannot be used in compound variants
From the source code (variants.ts:319-346):

Output

The @custom-variant directive is removed from the final CSS. Only the transformed utility classes are output: