From 9833b487a8b94fa6218b0daaea638354ed5fdefe Mon Sep 17 00:00:00 2001 From: Alexandre Kohler <64209066+kwy404@users.noreply.github.com> Date: Tue, 13 Oct 2026 10:17:03 -0300 Subject: [PATCH] Recognize missing viewport and font-relative length units (#20516) ## Summary `isLength` in `packages/tailwindcss/src/utils/infer-data-type.ts` checks arbitrary values against a fixed list of units. That list was carried over from v3 and is missing several CSS length units: the small, large, and dynamic viewport units `svi`, `svb`, `svmin`, `svmax`, `lvi`, `lvb`, `lvmin`, `lvmax`, `dvi`, `dvb`, `dvmin`, `dvmax`, and the font-relative units `cap`, `ic`, `rex`, `rch`, `rcap`, `ric`. Because these values are not detected as lengths, utilities that choose a property based on the value type fall back to the color branch. For example `text-[10dvmin]` generates `color: 10dvmin` instead of `font-size: 10dvmin` (while `text-[10dvw]` already works), and `border-[1dvmin]` generates `border-color: 1dvmin`. Today the only workaround is an explicit type hint like `text-[length:10dvmin]`. This adds the missing units, all of which are `` units defined in CSS Values and Units Level 4, to the list. Values that were already detected are unaffected. ## Test plan - Added a test to `packages/tailwindcss/src/utilities.test.ts` that compiles `text-[1]` for each of the 18 new units and compares the full generated rule. It fails without the change (the rules are emitted as `color: 1`) and passes with it. - `vitest run src/utilities.test.ts -t "viewport and font-relative"` (in `packages/tailwindcss`) - `vitest run` (in `packages/tailwindcss`): 42 files, 5016 tests passed - `prettier --check` on the changed files --------- Co-authored-by: Robin Malfait --- CHANGELOG.md | 1 + packages/tailwindcss/src/utilities.test.ts | 90 +++++++++++++++++++ .../tailwindcss/src/utils/infer-data-type.ts | 18 ++++ 3 files changed, 109 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index e615491e..f5b7d461 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -42,6 +42,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - Canonicalization: fix inline `theme(…)` alphas with more than 2 decimals being migrated to a modifier that changes the opacity by a factor of 100 (e.g. `theme(colors.red.500/.12345)` → `text-red-500/[12.345%]`, not `text-red-500/[12.345]`) ([#20563](https://github.com/tailwindlabs/tailwindcss/pull/20563)) - Canonicalization: keep inline `theme(…)` alphas as an arbitrary percentage when a custom `--opacity-*` theme value would change the opacity (e.g. `theme(colors.red.500/50%)` → `text-red-500/[50%]` with `--opacity-50: 10%`) ([#20563](https://github.com/tailwindlabs/tailwindcss/pull/20563)) - Ensure the `@property` fallback isn't applied in Safari versions that no longer support `margin-trim: inline` ([#20569](https://github.com/tailwindlabs/tailwindcss/pull/20569)) +- Treat viewport units like `dvmin` and `svi` and font-relative units like `cap` and `rex` as lengths in arbitrary values (e.g. `text-[10dvmin]` generates `font-size` instead of `color`) ([#20516](https://github.com/tailwindlabs/tailwindcss/pull/20516)) ## [4.3.3] - 2026-07-16 diff --git a/packages/tailwindcss/src/utilities.test.ts b/packages/tailwindcss/src/utilities.test.ts index edf3723e..76644625 100644 --- a/packages/tailwindcss/src/utilities.test.ts +++ b/packages/tailwindcss/src/utilities.test.ts @@ -26576,6 +26576,24 @@ test('text', async () => { 'text-[clamp(1rem,var(--size),3rem)]', 'text-[clamp(1rem,var(--size),3rem)]/9', 'text-[--spacing(2)]', + 'text-[1cap]', + 'text-[1ic]', + 'text-[1rex]', + 'text-[1rch]', + 'text-[1rcap]', + 'text-[1ric]', + 'text-[1svi]', + 'text-[1svb]', + 'text-[1svmin]', + 'text-[1svmax]', + 'text-[1lvi]', + 'text-[1lvb]', + 'text-[1lvmin]', + 'text-[1lvmax]', + 'text-[1dvi]', + 'text-[1dvb]', + 'text-[1dvmin]', + 'text-[1dvmax]', ], css` @theme { @@ -26669,6 +26687,78 @@ test('text', async () => { font-size: calc(var(--spacing) * 2); } + .text-\\[1cap\\] { + font-size: 1cap; + } + + .text-\\[1dvb\\] { + font-size: 1dvb; + } + + .text-\\[1dvi\\] { + font-size: 1dvi; + } + + .text-\\[1dvmax\\] { + font-size: 1dvmax; + } + + .text-\\[1dvmin\\] { + font-size: 1dvmin; + } + + .text-\\[1ic\\] { + font-size: 1ic; + } + + .text-\\[1lvb\\] { + font-size: 1lvb; + } + + .text-\\[1lvi\\] { + font-size: 1lvi; + } + + .text-\\[1lvmax\\] { + font-size: 1lvmax; + } + + .text-\\[1lvmin\\] { + font-size: 1lvmin; + } + + .text-\\[1rcap\\] { + font-size: 1rcap; + } + + .text-\\[1rch\\] { + font-size: 1rch; + } + + .text-\\[1rex\\] { + font-size: 1rex; + } + + .text-\\[1ric\\] { + font-size: 1ric; + } + + .text-\\[1svb\\] { + font-size: 1svb; + } + + .text-\\[1svi\\] { + font-size: 1svi; + } + + .text-\\[1svmax\\] { + font-size: 1svmax; + } + + .text-\\[1svmin\\] { + font-size: 1svmin; + } + .text-\\[12px\\] { font-size: 12px; } diff --git a/packages/tailwindcss/src/utils/infer-data-type.ts b/packages/tailwindcss/src/utils/infer-data-type.ts index 3317572f..a34a4467 100644 --- a/packages/tailwindcss/src/utils/infer-data-type.ts +++ b/packages/tailwindcss/src/utils/infer-data-type.ts @@ -208,7 +208,13 @@ const LENGTH_UNITS = [ 'em', 'ex', 'ch', + 'cap', + 'ic', 'rem', + 'rex', + 'rch', + 'rcap', + 'ric', 'lh', 'rlh', 'vw', @@ -219,10 +225,22 @@ const LENGTH_UNITS = [ 'vi', 'svw', 'svh', + 'svi', + 'svb', + 'svmin', + 'svmax', 'lvw', 'lvh', + 'lvi', + 'lvb', + 'lvmin', + 'lvmax', 'dvw', 'dvh', + 'dvi', + 'dvb', + 'dvmin', + 'dvmax', 'cqw', 'cqh', 'cqi',