Add logical sizing utilities (inline-size, block-size) (#19612)

## Summary

Adds new utilities for CSS logical properties that provide
writing-direction-aware alternatives to width and height:

- `inline-*` for `inline-size` (logical equivalent of width)
- `min-inline-*` for `min-inline-size` (logical equivalent of min-width)
- `max-inline-*` for `max-inline-size` (logical equivalent of max-width)
- `block-*` for `block-size` (logical equivalent of height)
- `min-block-*` for `min-block-size` (logical equivalent of min-height)
- `max-block-*` for `max-block-size` (logical equivalent of max-height)

## New Utilities

### inline-size utilities

| Class | CSS Property |
|-------|-------------|
| `inline-auto` | `inline-size: auto` |
| `inline-full` | `inline-size: 100%` |
| `inline-min` | `inline-size: min-content` |
| `inline-max` | `inline-size: max-content` |
| `inline-fit` | `inline-size: fit-content` |
| `inline-screen` | `inline-size: 100vw` |
| `inline-svw` | `inline-size: 100svw` |
| `inline-lvw` | `inline-size: 100lvw` |
| `inline-dvw` | `inline-size: 100dvw` |
| `inline-{spacing}` | `inline-size: {value}` (e.g., `inline-4`,
`inline-px`) |
| `inline-{fraction}` | `inline-size: {percent}` (e.g., `inline-1/2`,
`inline-3/4`) |
| `inline-[{value}]` | `inline-size: {value}` (arbitrary values) |

### min-inline-size utilities

| Class | CSS Property |
|-------|-------------|
| `min-inline-auto` | `min-inline-size: auto` |
| `min-inline-full` | `min-inline-size: 100%` |
| `min-inline-min` | `min-inline-size: min-content` |
| `min-inline-max` | `min-inline-size: max-content` |
| `min-inline-fit` | `min-inline-size: fit-content` |
| `min-inline-screen` | `min-inline-size: 100vw` |
| `min-inline-svw` | `min-inline-size: 100svw` |
| `min-inline-lvw` | `min-inline-size: 100lvw` |
| `min-inline-dvw` | `min-inline-size: 100dvw` |
| `min-inline-{spacing}` | `min-inline-size: {value}` |
| `min-inline-[{value}]` | `min-inline-size: {value}` (arbitrary values)
|

### max-inline-size utilities

| Class | CSS Property |
|-------|-------------|
| `max-inline-none` | `max-inline-size: none` |
| `max-inline-full` | `max-inline-size: 100%` |
| `max-inline-min` | `max-inline-size: min-content` |
| `max-inline-max` | `max-inline-size: max-content` |
| `max-inline-fit` | `max-inline-size: fit-content` |
| `max-inline-screen` | `max-inline-size: 100vw` |
| `max-inline-svw` | `max-inline-size: 100svw` |
| `max-inline-lvw` | `max-inline-size: 100lvw` |
| `max-inline-dvw` | `max-inline-size: 100dvw` |
| `max-inline-{spacing}` | `max-inline-size: {value}` |
| `max-inline-[{value}]` | `max-inline-size: {value}` (arbitrary values)
|

### block-size utilities

| Class | CSS Property |
|-------|-------------|
| `block-auto` | `block-size: auto` |
| `block-full` | `block-size: 100%` |
| `block-min` | `block-size: min-content` |
| `block-max` | `block-size: max-content` |
| `block-fit` | `block-size: fit-content` |
| `block-screen` | `block-size: 100vh` |
| `block-lh` | `block-size: 1lh` |
| `block-svh` | `block-size: 100svh` |
| `block-lvh` | `block-size: 100lvh` |
| `block-dvh` | `block-size: 100dvh` |
| `block-{spacing}` | `block-size: {value}` (e.g., `block-4`,
`block-px`) |
| `block-{fraction}` | `block-size: {percent}` (e.g., `block-1/2`,
`block-3/4`) |
| `block-[{value}]` | `block-size: {value}` (arbitrary values) |

### min-block-size utilities

| Class | CSS Property |
|-------|-------------|
| `min-block-auto` | `min-block-size: auto` |
| `min-block-full` | `min-block-size: 100%` |
| `min-block-min` | `min-block-size: min-content` |
| `min-block-max` | `min-block-size: max-content` |
| `min-block-fit` | `min-block-size: fit-content` |
| `min-block-screen` | `min-block-size: 100vh` |
| `min-block-lh` | `min-block-size: 1lh` |
| `min-block-svh` | `min-block-size: 100svh` |
| `min-block-lvh` | `min-block-size: 100lvh` |
| `min-block-dvh` | `min-block-size: 100dvh` |
| `min-block-{spacing}` | `min-block-size: {value}` |
| `min-block-[{value}]` | `min-block-size: {value}` (arbitrary values) |

### max-block-size utilities

| Class | CSS Property |
|-------|-------------|
| `max-block-none` | `max-block-size: none` |
| `max-block-full` | `max-block-size: 100%` |
| `max-block-min` | `max-block-size: min-content` |
| `max-block-max` | `max-block-size: max-content` |
| `max-block-fit` | `max-block-size: fit-content` |
| `max-block-screen` | `max-block-size: 100vh` |
| `max-block-lh` | `max-block-size: 1lh` |
| `max-block-svh` | `max-block-size: 100svh` |
| `max-block-lvh` | `max-block-size: 100lvh` |
| `max-block-dvh` | `max-block-size: 100dvh` |
| `max-block-{spacing}` | `max-block-size: {value}` |
| `max-block-[{value}]` | `max-block-size: {value}` (arbitrary values) |

## Test plan

- [x] Added comprehensive unit tests for all new utilities
- [ ] Verify utilities work correctly in RTL layouts
- [ ] Test with vertical writing modes

---------

Co-authored-by: Claude <noreply@anthropic.com>
Co-authored-by: Robin Malfait <malfait.robin@gmail.com>
This commit is contained in:
Adam Wathan 2026-01-30 14:46:37 +01:00 • committed by GitHub
parent 991072fcac
commit 3d1e654c02
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
4 changed files with 1061 additions and 0 deletions

View file

@ -21,6 +21,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Add `pbs-*`, `pbe-*`, `mbs-*`, `mbe-*`, `scroll-pbs-*`, `scroll-pbe-*`, `scroll-mbs-*`, `scroll-mbe-*`, `border-bs-*`, `border-be-*` utilities for `padding-block-start`, `padding-block-end`, `margin-block-start`, `margin-block-end`, `scroll-padding-block-start`, `scroll-padding-block-end`, `scroll-margin-block-start`, `scroll-margin-block-end`, `border-block-start`, and `border-block-end` ([`#19601`](https://github.com/tailwindlabs/tailwindcss/pull/19601))
- _Experimental_: Add `@container-size` utility ([#18901](https://github.com/tailwindlabs/tailwindcss/pull/18901))
- Add `@tailwindcss/webpack` loader for Tailwind CSS v4 ([#19610](https://github.com/tailwindlabs/tailwindcss/pull/19610))
- Add `inline-*`, `min-inline-*`, `max-inline-*`, `block-*`, `min-block-*`, `max-block-*` utilities for `inline-size`, `min-inline-size`, `max-inline-size`, `block-size`, `min-block-size`, and `max-block-size` ([#19612](https://github.com/tailwindlabs/tailwindcss/pull/19612))
## [4.1.18] - 2025-12-11

View file

@ -2714,6 +2714,77 @@ exports[`getClassList 1`] = `
"bg-transparent/95",
"bg-transparent/100",
"block",
"block-0",
"block-0.5",
"block-1",
"block-1.5",
"block-2",
"block-2.5",
"block-3",
"block-3.5",
"block-4",
"block-5",
"block-6",
"block-7",
"block-8",
"block-9",
"block-10",
"block-11",
"block-12",
"block-14",
"block-16",
"block-20",
"block-24",
"block-28",
"block-32",
"block-36",
"block-40",
"block-44",
"block-48",
"block-52",
"block-56",
"block-60",
"block-64",
"block-72",
"block-80",
"block-96",
"block-1/2",
"block-1/3",
"block-1/4",
"block-1/5",
"block-1/6",
"block-1/12",
"block-2/3",
"block-2/4",
"block-2/5",
"block-2/6",
"block-2/12",
"block-3/4",
"block-3/5",
"block-3/6",
"block-3/12",
"block-4/5",
"block-4/6",
"block-4/12",
"block-5/6",
"block-5/12",
"block-6/12",
"block-7/12",
"block-8/12",
"block-9/12",
"block-10/12",
"block-11/12",
"block-auto",
"block-dvh",
"block-fit",
"block-full",
"block-lh",
"block-lvh",
"block-max",
"block-min",
"block-px",
"block-screen",
"block-svh",
"blur-none",
"border",
"border/0",
@ -4952,9 +5023,81 @@ exports[`getClassList 1`] = `
"indent-96",
"indent-px",
"inline",
"inline-0",
"inline-0.5",
"inline-1",
"inline-1.5",
"inline-2",
"inline-2.5",
"inline-3",
"inline-3.5",
"inline-4",
"inline-5",
"inline-6",
"inline-7",
"inline-8",
"inline-9",
"inline-10",
"inline-11",
"inline-12",
"inline-14",
"inline-16",
"inline-20",
"inline-24",
"inline-28",
"inline-32",
"inline-36",
"inline-40",
"inline-44",
"inline-48",
"inline-52",
"inline-56",
"inline-60",
"inline-64",
"inline-72",
"inline-80",
"inline-96",
"inline-auto",
"inline-block",
"inline-dvw",
"inline-fit",
"inline-flex",
"inline-full",
"inline-grid",
"inline-lg",
"inline-lvw",
"inline-max",
"inline-md",
"inline-1/2",
"inline-1/3",
"inline-1/4",
"inline-1/5",
"inline-1/6",
"inline-1/12",
"inline-2/3",
"inline-2/4",
"inline-2/5",
"inline-2/6",
"inline-2/12",
"inline-3/4",
"inline-3/5",
"inline-3/6",
"inline-3/12",
"inline-4/5",
"inline-4/6",
"inline-4/12",
"inline-5/6",
"inline-5/12",
"inline-6/12",
"inline-7/12",
"inline-8/12",
"inline-9/12",
"inline-10/12",
"inline-11/12",
"inline-min",
"inline-px",
"inline-screen",
"inline-svw",
"inline-table",
"inset-0",
"inset-0.5",
@ -7754,6 +7897,77 @@ exports[`getClassList 1`] = `
"mask-y-to-transparent/90",
"mask-y-to-transparent/95",
"mask-y-to-transparent/100",
"max-block-0",
"max-block-0.5",
"max-block-1",
"max-block-1.5",
"max-block-2",
"max-block-2.5",
"max-block-3",
"max-block-3.5",
"max-block-4",
"max-block-5",
"max-block-6",
"max-block-7",
"max-block-8",
"max-block-9",
"max-block-10",
"max-block-11",
"max-block-12",
"max-block-14",
"max-block-16",
"max-block-20",
"max-block-24",
"max-block-28",
"max-block-32",
"max-block-36",
"max-block-40",
"max-block-44",
"max-block-48",
"max-block-52",
"max-block-56",
"max-block-60",
"max-block-64",
"max-block-72",
"max-block-80",
"max-block-96",
"max-block-1/2",
"max-block-1/3",
"max-block-1/4",
"max-block-1/5",
"max-block-1/6",
"max-block-1/12",
"max-block-2/3",
"max-block-2/4",
"max-block-2/5",
"max-block-2/6",
"max-block-2/12",
"max-block-3/4",
"max-block-3/5",
"max-block-3/6",
"max-block-3/12",
"max-block-4/5",
"max-block-4/6",
"max-block-4/12",
"max-block-5/6",
"max-block-5/12",
"max-block-6/12",
"max-block-7/12",
"max-block-8/12",
"max-block-9/12",
"max-block-10/12",
"max-block-11/12",
"max-block-dvh",
"max-block-fit",
"max-block-full",
"max-block-lh",
"max-block-lvh",
"max-block-max",
"max-block-min",
"max-block-none",
"max-block-px",
"max-block-screen",
"max-block-svh",
"max-h-0",
"max-h-0.5",
"max-h-1",
@ -7828,6 +8042,78 @@ exports[`getClassList 1`] = `
"max-h-screen",
"max-h-svh",
"max-h-svw",
"max-inline-0",
"max-inline-0.5",
"max-inline-1",
"max-inline-1.5",
"max-inline-2",
"max-inline-2.5",
"max-inline-3",
"max-inline-3.5",
"max-inline-4",
"max-inline-5",
"max-inline-6",
"max-inline-7",
"max-inline-8",
"max-inline-9",
"max-inline-10",
"max-inline-11",
"max-inline-12",
"max-inline-14",
"max-inline-16",
"max-inline-20",
"max-inline-24",
"max-inline-28",
"max-inline-32",
"max-inline-36",
"max-inline-40",
"max-inline-44",
"max-inline-48",
"max-inline-52",
"max-inline-56",
"max-inline-60",
"max-inline-64",
"max-inline-72",
"max-inline-80",
"max-inline-96",
"max-inline-dvw",
"max-inline-fit",
"max-inline-full",
"max-inline-lg",
"max-inline-lvw",
"max-inline-max",
"max-inline-md",
"max-inline-1/2",
"max-inline-1/3",
"max-inline-1/4",
"max-inline-1/5",
"max-inline-1/6",
"max-inline-1/12",
"max-inline-2/3",
"max-inline-2/4",
"max-inline-2/5",
"max-inline-2/6",
"max-inline-2/12",
"max-inline-3/4",
"max-inline-3/5",
"max-inline-3/6",
"max-inline-3/12",
"max-inline-4/5",
"max-inline-4/6",
"max-inline-4/12",
"max-inline-5/6",
"max-inline-5/12",
"max-inline-6/12",
"max-inline-7/12",
"max-inline-8/12",
"max-inline-9/12",
"max-inline-10/12",
"max-inline-11/12",
"max-inline-min",
"max-inline-none",
"max-inline-px",
"max-inline-screen",
"max-inline-svw",
"max-w-0",
"max-w-0.5",
"max-w-1",
@ -8046,6 +8332,77 @@ exports[`getClassList 1`] = `
"me-96",
"me-auto",
"me-px",
"min-block-0",
"min-block-0.5",
"min-block-1",
"min-block-1.5",
"min-block-2",
"min-block-2.5",
"min-block-3",
"min-block-3.5",
"min-block-4",
"min-block-5",
"min-block-6",
"min-block-7",
"min-block-8",
"min-block-9",
"min-block-10",
"min-block-11",
"min-block-12",
"min-block-14",
"min-block-16",
"min-block-20",
"min-block-24",
"min-block-28",
"min-block-32",
"min-block-36",
"min-block-40",
"min-block-44",
"min-block-48",
"min-block-52",
"min-block-56",
"min-block-60",
"min-block-64",
"min-block-72",
"min-block-80",
"min-block-96",
"min-block-1/2",
"min-block-1/3",
"min-block-1/4",
"min-block-1/5",
"min-block-1/6",
"min-block-1/12",
"min-block-2/3",
"min-block-2/4",
"min-block-2/5",
"min-block-2/6",
"min-block-2/12",
"min-block-3/4",
"min-block-3/5",
"min-block-3/6",
"min-block-3/12",
"min-block-4/5",
"min-block-4/6",
"min-block-4/12",
"min-block-5/6",
"min-block-5/12",
"min-block-6/12",
"min-block-7/12",
"min-block-8/12",
"min-block-9/12",
"min-block-10/12",
"min-block-11/12",
"min-block-auto",
"min-block-dvh",
"min-block-fit",
"min-block-full",
"min-block-lh",
"min-block-lvh",
"min-block-max",
"min-block-min",
"min-block-px",
"min-block-screen",
"min-block-svh",
"min-h-0",
"min-h-0.5",
"min-h-1",
@ -8120,6 +8477,78 @@ exports[`getClassList 1`] = `
"min-h-screen",
"min-h-svh",
"min-h-svw",
"min-inline-0",
"min-inline-0.5",
"min-inline-1",
"min-inline-1.5",
"min-inline-2",
"min-inline-2.5",
"min-inline-3",
"min-inline-3.5",
"min-inline-4",
"min-inline-5",
"min-inline-6",
"min-inline-7",
"min-inline-8",
"min-inline-9",
"min-inline-10",
"min-inline-11",
"min-inline-12",
"min-inline-14",
"min-inline-16",
"min-inline-20",
"min-inline-24",
"min-inline-28",
"min-inline-32",
"min-inline-36",
"min-inline-40",
"min-inline-44",
"min-inline-48",
"min-inline-52",
"min-inline-56",
"min-inline-60",
"min-inline-64",
"min-inline-72",
"min-inline-80",
"min-inline-96",
"min-inline-auto",
"min-inline-dvw",
"min-inline-fit",
"min-inline-full",
"min-inline-lg",
"min-inline-lvw",
"min-inline-max",
"min-inline-md",
"min-inline-1/2",
"min-inline-1/3",
"min-inline-1/4",
"min-inline-1/5",
"min-inline-1/6",
"min-inline-1/12",
"min-inline-2/3",
"min-inline-2/4",
"min-inline-2/5",
"min-inline-2/6",
"min-inline-2/12",
"min-inline-3/4",
"min-inline-3/5",
"min-inline-3/6",
"min-inline-3/12",
"min-inline-4/5",
"min-inline-4/6",
"min-inline-4/12",
"min-inline-5/6",
"min-inline-5/12",
"min-inline-6/12",
"min-inline-7/12",
"min-inline-8/12",
"min-inline-9/12",
"min-inline-10/12",
"min-inline-11/12",
"min-inline-min",
"min-inline-px",
"min-inline-screen",
"min-inline-svw",
"min-w-0",
"min-w-0.5",
"min-w-1",

View file

@ -3662,6 +3662,561 @@ test('max-height', async () => {
).toEqual('')
})
test('inline-size', async () => {
expect(
await compileCss(
css`
@theme {
--spacing-4: 1rem;
--width-xl: 36rem;
}
@tailwind utilities;
`,
[
'inline-full',
'inline-auto',
'inline-screen',
'inline-svw',
'inline-lvw',
'inline-dvw',
'inline-min',
'inline-max',
'inline-fit',
'inline-4',
'inline-xl',
'inline-1/2',
'inline-[4px]',
],
),
).toMatchInlineSnapshot(`
":root, :host {
--spacing-4: 1rem;
--width-xl: 36rem;
}
.inline-1\\/2 {
inline-size: 50%;
}
.inline-4 {
inline-size: var(--spacing-4);
}
.inline-\\[4px\\] {
inline-size: 4px;
}
.inline-auto {
inline-size: auto;
}
.inline-dvw {
inline-size: 100dvw;
}
.inline-fit {
inline-size: fit-content;
}
.inline-full {
inline-size: 100%;
}
.inline-lvw {
inline-size: 100lvw;
}
.inline-max {
inline-size: max-content;
}
.inline-min {
inline-size: min-content;
}
.inline-screen {
inline-size: 100vw;
}
.inline-svw {
inline-size: 100svw;
}
.inline-xl {
inline-size: var(--width-xl);
}"
`)
expect(
await run([
'inline--1',
'inline--1/2',
'inline--1/-2',
'inline-1/-2',
'-inline-4',
'-inline-1/2',
'-inline-[4px]',
'inline-full/foo',
'inline-auto/foo',
'inline-screen/foo',
'inline-svw/foo',
'inline-lvw/foo',
'inline-dvw/foo',
'inline-min/foo',
'inline-max/foo',
'inline-fit/foo',
'inline-4/foo',
'inline-xl/foo',
'inline-1/2/foo',
'inline-[4px]/foo',
]),
).toEqual('')
})
test('min-inline-size', async () => {
expect(
await compileCss(
css`
@theme {
--spacing-4: 1rem;
--container-xl: 36rem;
}
@tailwind utilities;
`,
[
'min-inline-full',
'min-inline-auto',
'min-inline-min',
'min-inline-max',
'min-inline-fit',
'min-inline-4',
'min-inline-xl',
'min-inline-[4px]',
],
),
).toMatchInlineSnapshot(`
":root, :host {
--spacing-4: 1rem;
--container-xl: 36rem;
}
.min-inline-4 {
min-inline-size: var(--spacing-4);
}
.min-inline-\\[4px\\] {
min-inline-size: 4px;
}
.min-inline-auto {
min-inline-size: auto;
}
.min-inline-fit {
min-inline-size: fit-content;
}
.min-inline-full {
min-inline-size: 100%;
}
.min-inline-max {
min-inline-size: max-content;
}
.min-inline-min {
min-inline-size: min-content;
}
.min-inline-xl {
min-inline-size: var(--container-xl);
}"
`)
expect(
await run([
'min-inline',
'-min-inline-4',
'-min-inline-[4px]',
'min-inline-auto/foo',
'min-inline-full/foo',
'min-inline-min/foo',
'min-inline-max/foo',
'min-inline-fit/foo',
'min-inline-4/foo',
'min-inline-xl/foo',
'min-inline-[4px]/foo',
]),
).toEqual('')
})
test('max-inline-size', async () => {
expect(
await compileCss(
css`
@theme {
--spacing-4: 1rem;
--container-xl: 36rem;
}
@tailwind utilities;
`,
['max-inline-none', 'max-inline-full', 'max-inline-max', 'max-inline-fit', 'max-inline-4', 'max-inline-xl', 'max-inline-[4px]'],
),
).toMatchInlineSnapshot(`
":root, :host {
--spacing-4: 1rem;
--container-xl: 36rem;
}
.max-inline-4 {
max-inline-size: var(--spacing-4);
}
.max-inline-\\[4px\\] {
max-inline-size: 4px;
}
.max-inline-fit {
max-inline-size: fit-content;
}
.max-inline-full {
max-inline-size: 100%;
}
.max-inline-max {
max-inline-size: max-content;
}
.max-inline-none {
max-inline-size: none;
}
.max-inline-xl {
max-inline-size: var(--container-xl);
}"
`)
expect(
await run([
'max-inline',
'max-inline-auto',
'-max-inline-4',
'-max-inline-[4px]',
'max-inline-none/foo',
'max-inline-full/foo',
'max-inline-max/foo',
'max-inline-max/foo',
'max-inline-fit/foo',
'max-inline-4/foo',
'max-inline-xl/foo',
'max-inline-[4px]/foo',
]),
).toEqual('')
})
test('block-size', async () => {
expect(
await compileCss(
css`
@theme {
--spacing-4: 1rem;
}
@tailwind utilities;
`,
[
'block-full',
'block-auto',
'block-screen',
'block-svh',
'block-lvh',
'block-dvh',
'block-min',
'block-lh',
'block-max',
'block-fit',
'block-4',
'block-1/2',
'block-[4px]',
],
),
).toMatchInlineSnapshot(`
":root, :host {
--spacing-4: 1rem;
}
.block-1\\/2 {
block-size: 50%;
}
.block-4 {
block-size: var(--spacing-4);
}
.block-\\[4px\\] {
block-size: 4px;
}
.block-auto {
block-size: auto;
}
.block-dvh {
block-size: 100dvh;
}
.block-fit {
block-size: fit-content;
}
.block-full {
block-size: 100%;
}
.block-lh {
block-size: 1lh;
}
.block-lvh {
block-size: 100lvh;
}
.block-max {
block-size: max-content;
}
.block-min {
block-size: min-content;
}
.block-screen {
block-size: 100vh;
}
.block-svh {
block-size: 100svh;
}"
`)
expect(
await run([
'-block-4',
'block--1',
'block--1/2',
'block--1/-2',
'block-1/-2',
'-block-1/2',
'-block-[4px]',
'block-full/foo',
'block-auto/foo',
'block-screen/foo',
'block-svh/foo',
'block-lvh/foo',
'block-dvh/foo',
'block-lh/foo',
'block-min/foo',
'block-max/foo',
'block-fit/foo',
'block-4/foo',
'block-1/2/foo',
'block-[4px]/foo',
]),
).toEqual('')
})
test('min-block-size', async () => {
expect(
await compileCss(
css`
@theme {
--spacing-4: 1rem;
}
@tailwind utilities;
`,
[
'min-block-full',
'min-block-auto',
'min-block-screen',
'min-block-svh',
'min-block-lvh',
'min-block-dvh',
'min-block-min',
'min-block-lh',
'min-block-max',
'min-block-fit',
'min-block-4',
'min-block-[4px]',
],
),
).toMatchInlineSnapshot(`
":root, :host {
--spacing-4: 1rem;
}
.min-block-4 {
min-block-size: var(--spacing-4);
}
.min-block-\\[4px\\] {
min-block-size: 4px;
}
.min-block-auto {
min-block-size: auto;
}
.min-block-dvh {
min-block-size: 100dvh;
}
.min-block-fit {
min-block-size: fit-content;
}
.min-block-full {
min-block-size: 100%;
}
.min-block-lh {
min-block-size: 1lh;
}
.min-block-lvh {
min-block-size: 100lvh;
}
.min-block-max {
min-block-size: max-content;
}
.min-block-min {
min-block-size: min-content;
}
.min-block-screen {
min-block-size: 100vh;
}
.min-block-svh {
min-block-size: 100svh;
}"
`)
expect(
await run([
'min-block',
'-min-block-4',
'-min-block-[4px]',
'min-block-auto/foo',
'min-block-full/foo',
'min-block-screen/foo',
'min-block-svh/foo',
'min-block-lvh/foo',
'min-block-dvh/foo',
'min-block-lh/foo',
'min-block-min/foo',
'min-block-max/foo',
'min-block-fit/foo',
'min-block-4/foo',
'min-block-[4px]/foo',
]),
).toEqual('')
})
test('max-block-size', async () => {
expect(
await compileCss(
css`
@theme {
--spacing-4: 1rem;
}
@tailwind utilities;
`,
[
'max-block-none',
'max-block-full',
'max-block-screen',
'max-block-svh',
'max-block-lvh',
'max-block-dvh',
'max-block-lh',
'max-block-min',
'max-block-max',
'max-block-fit',
'max-block-4',
'max-block-[4px]',
],
),
).toMatchInlineSnapshot(`
":root, :host {
--spacing-4: 1rem;
}
.max-block-4 {
max-block-size: var(--spacing-4);
}
.max-block-\\[4px\\] {
max-block-size: 4px;
}
.max-block-dvh {
max-block-size: 100dvh;
}
.max-block-fit {
max-block-size: fit-content;
}
.max-block-full {
max-block-size: 100%;
}
.max-block-lh {
max-block-size: 1lh;
}
.max-block-lvh {
max-block-size: 100lvh;
}
.max-block-max {
max-block-size: max-content;
}
.max-block-min {
max-block-size: min-content;
}
.max-block-none {
max-block-size: none;
}
.max-block-screen {
max-block-size: 100vh;
}
.max-block-svh {
max-block-size: 100svh;
}"
`)
expect(
await run([
'max-block',
'max-block-auto',
'-max-block-4',
'-max-block-[4px]',
'max-block-none/foo',
'max-block-full/foo',
'max-block-screen/foo',
'max-block-svh/foo',
'max-block-lvh/foo',
'max-block-dvh/foo',
'max-block-lh/foo',
'max-block-min/foo',
'max-block-max/foo',
'max-block-fit/foo',
'max-block-4/foo',
'max-block-[4px]/foo',
]),
).toEqual('')
})
describe('container', () => {
test('creates the right media queries and sorts it before width', async () => {
expect(

View file

@ -1069,6 +1069,82 @@ export function createUtilities(theme: Theme) {
})
}
/**
* @css `inline-size`
* @css `min-inline-size`
* @css `max-inline-size`
* @css `block-size`
* @css `min-block-size`
* @css `max-block-size`
*/
for (let [key, value] of [
['full', '100%'],
['min', 'min-content'],
['max', 'max-content'],
['fit', 'fit-content'],
]) {
staticUtility(`inline-${key}`, [['inline-size', value]])
staticUtility(`block-${key}`, [['block-size', value]])
staticUtility(`min-inline-${key}`, [['min-inline-size', value]])
staticUtility(`min-block-${key}`, [['min-block-size', value]])
staticUtility(`max-inline-${key}`, [['max-inline-size', value]])
staticUtility(`max-block-${key}`, [['max-block-size', value]])
}
// inline-size viewport units (like width)
for (let [key, value] of [
['svw', '100svw'],
['lvw', '100lvw'],
['dvw', '100dvw'],
]) {
staticUtility(`inline-${key}`, [['inline-size', value]])
staticUtility(`min-inline-${key}`, [['min-inline-size', value]])
staticUtility(`max-inline-${key}`, [['max-inline-size', value]])
}
// block-size viewport units (like height)
for (let [key, value] of [
['svh', '100svh'],
['lvh', '100lvh'],
['dvh', '100dvh'],
]) {
staticUtility(`block-${key}`, [['block-size', value]])
staticUtility(`min-block-${key}`, [['min-block-size', value]])
staticUtility(`max-block-${key}`, [['max-block-size', value]])
}
staticUtility(`inline-auto`, [['inline-size', 'auto']])
staticUtility(`block-auto`, [['block-size', 'auto']])
staticUtility(`min-inline-auto`, [['min-inline-size', 'auto']])
staticUtility(`min-block-auto`, [['min-block-size', 'auto']])
staticUtility(`block-lh`, [['block-size', '1lh']])
staticUtility(`min-block-lh`, [['min-block-size', '1lh']])
staticUtility(`max-block-lh`, [['max-block-size', '1lh']])
staticUtility(`inline-screen`, [['inline-size', '100vw']])
staticUtility(`min-inline-screen`, [['min-inline-size', '100vw']])
staticUtility(`max-inline-screen`, [['max-inline-size', '100vw']])
staticUtility(`block-screen`, [['block-size', '100vh']])
staticUtility(`min-block-screen`, [['min-block-size', '100vh']])
staticUtility(`max-block-screen`, [['max-block-size', '100vh']])
staticUtility(`max-inline-none`, [['max-inline-size', 'none']])
staticUtility(`max-block-none`, [['max-block-size', 'none']])
for (let [name, namespaces, property] of [
['inline', ['--width', '--spacing', '--container'], 'inline-size'],
['min-inline', ['--min-width', '--spacing', '--container'], 'min-inline-size'],
['max-inline', ['--max-width', '--spacing', '--container'], 'max-inline-size'],
['block', ['--height', '--spacing'], 'block-size'],
['min-block', ['--min-height', '--height', '--spacing'], 'min-block-size'],
['max-block', ['--max-height', '--height', '--spacing'], 'max-block-size'],
] as [string, ThemeKey[], string][]) {
spacingUtility(name, namespaces, (value) => [decl(property, value)], {
supportsFractions: true,
})
}
utilities.static('container', () => {
let breakpoints = [...theme.namespace('--breakpoint').values()]
breakpoints.sort((a, z) => compareBreakpoints(a, z, 'asc'))