71 lines
2.0 KiB
JavaScript
71 lines
2.0 KiB
JavaScript
/**
|
|
* Tailwind 4 gracefully falls back from color-mix() to the base semantic
|
|
* color, but that turns utilities such as bg-primary/5 into an opaque fill on
|
|
* Chrome 109. Replace that fallback with an sRGB-channel based alpha color.
|
|
* The modern color-mix() declaration remains in its @supports block.
|
|
*/
|
|
|
|
const LEGACY_RGB_TOKENS = new Set([
|
|
"accent",
|
|
"background",
|
|
"border",
|
|
"brand-200",
|
|
"card",
|
|
"destructive",
|
|
"foreground",
|
|
"input",
|
|
"muted",
|
|
"muted-foreground",
|
|
"primary",
|
|
"primary-foreground",
|
|
"ring",
|
|
"secondary",
|
|
"sidebar-accent",
|
|
"sidebar-border",
|
|
"sidebar-foreground",
|
|
"workspace-brand",
|
|
]);
|
|
|
|
const TRANSPARENT_MIX_RE =
|
|
/color-mix\(\s*in\s+[\w-]+\s*,\s*var\(--([\w-]+)\)\s+([\d.]+)%\s*,\s*transparent\s*\)/i;
|
|
|
|
function legacyAlphaColor(value) {
|
|
const match = value.match(TRANSPARENT_MIX_RE);
|
|
if (!match || !LEGACY_RGB_TOKENS.has(match[1])) return null;
|
|
|
|
const [, token, percentage] = match;
|
|
return `rgb(var(--legacy-${token}-rgb) / ${percentage}%)`;
|
|
}
|
|
|
|
export default function legacyColorFallback() {
|
|
return {
|
|
postcssPlugin: "postcss-legacy-color-fallback",
|
|
OnceExit(root) {
|
|
root.walkAtRules("supports", (atRule) => {
|
|
if (!atRule.params.includes("color-mix")) return;
|
|
|
|
atRule.walkDecls((modernDeclaration) => {
|
|
const fallbackValue = legacyAlphaColor(modernDeclaration.value);
|
|
if (!fallbackValue) return;
|
|
|
|
// Tailwind emits the old-browser declaration immediately before
|
|
// the nested @supports block, in the same utility/variant rule.
|
|
let fallbackDeclaration = atRule.prev();
|
|
while (fallbackDeclaration?.type === "comment") {
|
|
fallbackDeclaration = fallbackDeclaration.prev();
|
|
}
|
|
|
|
if (
|
|
fallbackDeclaration?.type === "decl" &&
|
|
fallbackDeclaration.prop === modernDeclaration.prop
|
|
) {
|
|
fallbackDeclaration.value = fallbackValue;
|
|
}
|
|
});
|
|
});
|
|
},
|
|
};
|
|
}
|
|
|
|
legacyColorFallback.postcss = true;
|