Emit @keyframes in prefixed setup (#16850)

Closes #16829

We were only adding keyframes used in variables starting with
`--animate` (without adding a potential prefix).

## Test plan

- Added a unit test
This commit is contained in:
Philipp Spiess 2025-02-27 17:35:25 +01:00 committed by GitHub
parent 5532d48e8e
commit 66ef77ce76
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 72 additions and 4 deletions

View File

@ -18,6 +18,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
### Fixed
- Ensure `not-*` does not remove `:is(…)` from variants ([#16825](https://github.com/tailwindlabs/tailwindcss/pull/16825))
- Ensure `@keyframes` are correctly emitted when using a prefixed setup ([#16850](https://github.com/tailwindlabs/tailwindcss/pull/16850))
## [4.0.9] - 2025-02-25

View File

@ -429,7 +429,7 @@ export function optimizeAst(ast: AstNode[], designSystem: DesignSystem) {
variableDependencies,
)
if (variableUsed) {
if (declaration.property.startsWith('--animate-')) {
if (declaration.property.startsWith(designSystem.theme.prefixKey('--animate-'))) {
let parts = declaration.value!.split(/\s+/)
for (let part of parts) usedKeyframeNames.add(part)
}

View File

@ -1613,6 +1613,73 @@ describe('Parsing theme values from CSS', () => {
`)
})
test('keyframes are generated when used in an animation within a prefixed setup', async () => {
expect(
await compileCss(
css`
@theme prefix(tw) {
--animate-foo: used 1s infinite;
--animate-bar: unused 1s infinite;
@keyframes used {
to {
opacity: 1;
}
}
@keyframes unused {
to {
opacity: 0;
}
}
}
@tailwind utilities;
`,
['tw:animate-foo'],
),
).toMatchInlineSnapshot(`
":root, :host {
--tw-animate-foo: used 1s infinite;
}
.tw\\:animate-foo {
animation: var(--tw-animate-foo);
}
@keyframes used {
to {
opacity: 1;
}
}"
`)
})
test('custom properties are generated when used from a CSS var with a prefixed setup', async () => {
expect(
await compileCss(
css`
@theme prefix(tw) {
--color-tomato: #e10c04;
}
@tailwind utilities;
.red {
color: var(--tw-color-tomato);
}
`,
[],
),
).toMatchInlineSnapshot(`
":root, :host {
--tw-color-tomato: #e10c04;
}
.red {
color: var(--tw-color-tomato);
}"
`)
})
// https://github.com/tailwindlabs/tailwindcss/issues/16374
test('custom properties in keyframes preserved', async () => {
expect(

View File

@ -117,12 +117,12 @@ export class Theme {
if (!this.prefix) return this.values.entries()
return Array.from(this.values, (entry) => {
entry[0] = this.#prefixKey(entry[0])
entry[0] = this.prefixKey(entry[0])
return entry
})
}
#prefixKey(key: string) {
prefixKey(key: string) {
if (!this.prefix) return key
return `--${this.prefix}-${key.slice(2)}`
}
@ -190,7 +190,7 @@ export class Theme {
fallback = value.value
}
return `var(${escape(this.#prefixKey(themeKey))}${fallback ? `, ${fallback}` : ''})`
return `var(${escape(this.prefixKey(themeKey))}${fallback ? `, ${fallback}` : ''})`
}
markUsedVariable(themeKey: string) {