Custom Styles and Arbitrary Values
|
This section documents Tailwind CSS v4.x — the CSS-first configuration line, whose v4.0 release shipped in January 2025 — as published at the official Tailwind CSS documentation, which is the reference these pages are written and verified against. No specific patch version is pinned. This content was generated with the assistance of AI and should be verified against the official documentation before being relied on in production, since Tailwind iterates quickly. This section’s bibliography lists the reference material consulted while preparing these pages. |
When no built-in utility fits, Tailwind gives you graduated escape hatches — from a one-off value in square
brackets, through your own reusable @utility, to plain CSS in a @layer. See
Adding Custom Styles.
Arbitrary values
Put any CSS value in square brackets and Tailwind generates the utility on demand. Use for spaces (it is
converted to a space; keep literal underscores in url() and escape one you need as \).
<div class="top-[117px] lg:top-[344px]"></div>
<div class="bg-[#bada55] text-[22px]"></div>
<div class="grid grid-cols-[1fr_500px_2fr]"></div>
<div class="max-h-[calc(100dvh-4rem)]"></div>
<span class="before:content-['Hello_world']"></span>
Arbitrary properties and variants
<!-- a property with no utility at all -->
<div class="[mask-type:luminance] hover:[mask-type:alpha]"></div>
<!-- set a CSS variable inline, responsively -->
<div class="[--gutter:1rem] lg:[--gutter:2rem]"></div>
<!-- a selector Tailwind has no variant for -->
<div class="[&_p]:mt-4 [&.is-open]:block [&::-webkit-scrollbar]:hidden
[@supports(display:grid)]:grid"></div>
The CSS-variable shorthand
For values that are genuinely dynamic (a colour from a CMS, a user setting), set a CSS variable with an inline
style and reference it with the (--var) shorthand — shorter than [var(--var)]:
<button style="--btn: #7c3aed; --btn-hover: #6d28d9"
class="bg-(--btn) hover:bg-(--btn-hover) text-white px-4 py-2 rounded">
Themed button
</button>
When the utility could take more than one CSS data type, add a hint:
<p class="text-(length:--fluid-size)">font-size from a variable</p>
<p class="text-(color:--brand)">colour from a variable</p>
Custom utilities with @utility
@utility registers a class that works with every variant (hover:, md:, dark:) — the v4 replacement
for a v3 @layer utilities block.
@import "tailwindcss";
/* static utility */
@utility content-auto { content-visibility: auto; }
/* nested selectors */
@utility scrollbar-none {
&::-webkit-scrollbar { display: none; }
scrollbar-width: none;
}
/* functional utility: `tab-*` accepts a number, a named value, or a bare integer */
@theme { --tab-size-github: 8; }
@utility tab-* {
tab-size: --value(--tab-size-*, integer, [integer]);
}
<pre class="tab-4 md:tab-github">…</pre>
--value() resolves the part after the dash; --modifier() resolves a / modifier; wrap a fallback with
--value(integer, --default(4)). See
Functional utilities.
Custom variants
@import "tailwindcss";
/* selector form */
@custom-variant theme-midnight (&:where([data-theme="midnight"] *));
/* at-rule form */
@custom-variant pointer-coarse (@media (pointer: coarse));
/* apply a Tailwind variant inside your own rule */
.panel {
background: white;
@variant dark { background: #0f172a; }
@variant hover, focus { background: #f1f5f9; }
}
@apply and @reference
@apply inlines existing utilities into a custom rule. Reach for it sparingly — mainly to style third-party
markup you cannot add classes to; prefer a framework component for your own repeated patterns.
@layer components {
.select2-dropdown { @apply rounded-b-md border border-gray-200 shadow-md; }
}
In a scoped stylesheet that is compiled separately (a Vue / Svelte <style> block, CSS Modules), the theme
and utilities are not in scope, so @apply and @variant fail. Pull them in with @reference — it imports
the definitions without duplicating any CSS into that file:
/* Component.vue <style> */
@reference "../app.css";
h1 { @apply text-2xl font-bold text-sky-600; }
Related pages
-
Customization and Configuration —
@theme,@source,@plugin, and the cascade layers. -
Utility-First Fundamentals — why components usually beat
@apply. -
Hover, Focus, and Other States — the built-in variants
@custom-variantextends.