@onereach/styles 27.0.2-beta.6102.0 → 27.0.2-beta.6104.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/MIGRATION_TAILWIND_V4.md +149 -0
- package/README.md +14 -0
- package/compat/tailwind-v3-utilities.css +1 -0
- package/main-v3.css +1 -1
- package/main-v4.css +3 -0
- package/package.json +17 -6
- package/postcss/tailwind-v4-compat.cjs +420 -0
- package/rollup-plugin-tailwindcss-cli.css +2 -1
- package/tailwind/compatibility/important.js +13 -0
- package/tailwind/compatibility/legacy-spacing.js +133 -0
- package/tailwind/plugins/theme-background.js +4 -3
- package/tailwind/plugins/theme-border.js +4 -3
- package/tailwind/plugins/theme-divider.js +7 -6
- package/tailwind/plugins/theme-foreground.js +4 -3
- package/tailwind/plugins/theme-outline.js +4 -3
- package/tailwind/plugins/theme-preset.js +17 -16
- package/tailwind.config.js +1 -3
- package/tailwind.config.json +2681 -1030
- package/tailwind.config.preset.js +1 -230
- package/tailwind.config.preset.v4.js +231 -0
- package/legacy-utilities.layer.css +0 -67219
package/main-v3.css
CHANGED
package/main-v4.css
ADDED
package/package.json
CHANGED
|
@@ -1,24 +1,28 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@onereach/styles",
|
|
3
|
-
"version": "27.0.2-beta.
|
|
3
|
+
"version": "27.0.2-beta.6104.0",
|
|
4
4
|
"description": "Styles for or-ui-next",
|
|
5
5
|
"license": "Apache-2.0",
|
|
6
6
|
"files": [
|
|
7
7
|
"dist",
|
|
8
|
+
"MIGRATION_TAILWIND_V4.md",
|
|
8
9
|
"icons",
|
|
9
10
|
"src",
|
|
10
11
|
"tailwind/**",
|
|
12
|
+
"compat",
|
|
11
13
|
"base.layer.css",
|
|
12
14
|
"font.css",
|
|
13
|
-
"legacy-utilities.layer.css",
|
|
14
15
|
"legacy-ui-warning.scss",
|
|
15
16
|
"main-v3.css",
|
|
17
|
+
"main-v4.css",
|
|
18
|
+
"postcss",
|
|
16
19
|
"preflight-revert.css",
|
|
17
20
|
"rollup-plugin-tailwindcss-cli.css",
|
|
18
21
|
"scrollbar.css",
|
|
19
22
|
"tailwind.config.js",
|
|
20
23
|
"tailwind.config.json",
|
|
21
24
|
"tailwind.config.preset.js",
|
|
25
|
+
"tailwind.config.preset.v4.js",
|
|
22
26
|
"temporary-dark-v2.css",
|
|
23
27
|
"tokens.css",
|
|
24
28
|
"tokens-v3.css",
|
|
@@ -26,16 +30,19 @@
|
|
|
26
30
|
"screens.json"
|
|
27
31
|
],
|
|
28
32
|
"scripts": {
|
|
29
|
-
"build": "npm-run-all build:tokens:css build:tokens:css:v3 build:resolve-config",
|
|
33
|
+
"build": "npm-run-all build:tokens:css build:tokens:css:v3 build:resolve-config build:compat",
|
|
34
|
+
"build:compat": "node ./scripts/generateLegacyCompatibility.js",
|
|
30
35
|
"build:resolve-config": "node ./scripts/resolveConfig.js",
|
|
31
36
|
"build:tokens:css": "node ./utils/makeCssVaribales.js",
|
|
32
37
|
"build:tokens:css:v3": "node ./utils/makeCssVariablesV3.js",
|
|
33
38
|
"clean": "rimraf dist",
|
|
34
39
|
"fix": "stylelint --fix '**/*.scss'",
|
|
35
|
-
"lint": "stylelint '**/*.scss'"
|
|
40
|
+
"lint": "stylelint '**/*.scss'",
|
|
41
|
+
"test:contract": "node --test tests/*.test.cjs"
|
|
36
42
|
},
|
|
37
43
|
"dependencies": {
|
|
38
|
-
"@onereach/font-icons": "^27.0.2-beta.
|
|
44
|
+
"@onereach/font-icons": "^27.0.2-beta.6104.0",
|
|
45
|
+
"postcss-nested": "6.2.0",
|
|
39
46
|
"tailwindcss": "4.3.2"
|
|
40
47
|
},
|
|
41
48
|
"devDependencies": {
|
|
@@ -45,7 +52,11 @@
|
|
|
45
52
|
"postcss-cli": "^10.1.0",
|
|
46
53
|
"postcss-import": "^15.1.0",
|
|
47
54
|
"postcss-preset-env": "^9.1.0",
|
|
48
|
-
"sass": "^1.63.4"
|
|
55
|
+
"sass": "^1.63.4",
|
|
56
|
+
"tailwindcss-v3": "npm:tailwindcss@3.4.16"
|
|
57
|
+
},
|
|
58
|
+
"peerDependencies": {
|
|
59
|
+
"postcss": "^8.4.32"
|
|
49
60
|
},
|
|
50
61
|
"publishConfig": {
|
|
51
62
|
"access": "public"
|
|
@@ -0,0 +1,420 @@
|
|
|
1
|
+
const {
|
|
2
|
+
importantMarker,
|
|
3
|
+
} = require('../tailwind/compatibility/important');
|
|
4
|
+
const {
|
|
5
|
+
legacySpacingAliasEntries,
|
|
6
|
+
} = require('../tailwind/compatibility/legacy-spacing');
|
|
7
|
+
const postcss = require('postcss');
|
|
8
|
+
const postcssNested = require('postcss-nested');
|
|
9
|
+
const spacing = require('../tailwind.config.preset.v4').theme.spacing;
|
|
10
|
+
const screens = require('../screens.json');
|
|
11
|
+
|
|
12
|
+
const legacySpacingAliases = legacySpacingAliasEntries(spacing)
|
|
13
|
+
.sort(([, left], [, right]) => right.length - left.length);
|
|
14
|
+
const legacySpacingUtilityPattern = /^-?(?:p(?:[xytrblse])?|m(?:[xytrblse])?|gap(?:-[xy])?|w|h|min-[wh]|max-[wh])-/;
|
|
15
|
+
const responsiveVariantOrder = new Map(
|
|
16
|
+
['xs', ...Object.keys(screens)].map((variant, index) => [variant, index]),
|
|
17
|
+
);
|
|
18
|
+
const legacyCoreUtilities = new Map([
|
|
19
|
+
['leading-none', [
|
|
20
|
+
['line-height', '1'],
|
|
21
|
+
]],
|
|
22
|
+
['text-inherit', [
|
|
23
|
+
['font-size', 'inherit'],
|
|
24
|
+
['line-height', 'inherit'],
|
|
25
|
+
['color', 'inherit'],
|
|
26
|
+
]],
|
|
27
|
+
['outline-none', [
|
|
28
|
+
['outline', '2px solid transparent'],
|
|
29
|
+
['outline-offset', '2px'],
|
|
30
|
+
]],
|
|
31
|
+
['transition-transform', [
|
|
32
|
+
['transition-property', 'transform'],
|
|
33
|
+
]],
|
|
34
|
+
['max-w-none', [
|
|
35
|
+
['max-width', 'none'],
|
|
36
|
+
]],
|
|
37
|
+
['max-h-none', [
|
|
38
|
+
['max-height', 'none'],
|
|
39
|
+
]],
|
|
40
|
+
]);
|
|
41
|
+
const legacyCoreReplacementProps = new Map([
|
|
42
|
+
['leading-none', new Set(['--tw-leading', 'line-height'])],
|
|
43
|
+
['text-inherit', new Set(['font-size', 'line-height', 'color'])],
|
|
44
|
+
['outline-none', new Set([
|
|
45
|
+
'--tw-outline-style',
|
|
46
|
+
'outline',
|
|
47
|
+
'outline-offset',
|
|
48
|
+
'outline-style',
|
|
49
|
+
])],
|
|
50
|
+
['transition-transform', new Set([
|
|
51
|
+
'transition-property',
|
|
52
|
+
'transition-timing-function',
|
|
53
|
+
'transition-duration',
|
|
54
|
+
])],
|
|
55
|
+
['max-w-none', new Set(['max-width'])],
|
|
56
|
+
['max-h-none', new Set(['max-height'])],
|
|
57
|
+
]);
|
|
58
|
+
|
|
59
|
+
function tailwindV4Compat() {
|
|
60
|
+
return {
|
|
61
|
+
postcssPlugin: 'onereach-tailwind-v4-compat',
|
|
62
|
+
async OnceExit(root) {
|
|
63
|
+
utilityLayers(root).forEach(restoreNestedChildrenVariantOrder);
|
|
64
|
+
await flattenUtilityLayers(root);
|
|
65
|
+
|
|
66
|
+
utilityLayers(root).forEach((layer) => {
|
|
67
|
+
restoreStackedVariantOrder(layer);
|
|
68
|
+
restoreLegacySpacingClassNames(layer);
|
|
69
|
+
restoreImportantDeclarations(layer);
|
|
70
|
+
restoreLegacyCoreUtilities(layer);
|
|
71
|
+
restoreArbitraryValueOrder(layer);
|
|
72
|
+
reorderResponsiveVariantSiblings(layer);
|
|
73
|
+
});
|
|
74
|
+
},
|
|
75
|
+
};
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
function restoreNestedChildrenVariantOrder(root) {
|
|
79
|
+
root.walkRules((candidateRule) => {
|
|
80
|
+
const candidate = classNames(candidateRule.selector)
|
|
81
|
+
.find((className) => className.split(':').includes('children'));
|
|
82
|
+
|
|
83
|
+
if (!candidate) return;
|
|
84
|
+
|
|
85
|
+
const segments = candidate.split(':');
|
|
86
|
+
const variantDepth = segments.length - 1;
|
|
87
|
+
|
|
88
|
+
const paths = nestedContainerPaths(candidateRule, variantDepth);
|
|
89
|
+
|
|
90
|
+
if (paths.length === 0) return;
|
|
91
|
+
|
|
92
|
+
candidateRule.removeAll();
|
|
93
|
+
candidateRule.append(paths.map(({ containers, nodes }) => {
|
|
94
|
+
let content = nodes.map((node) => node.clone());
|
|
95
|
+
|
|
96
|
+
containers.forEach((container) => {
|
|
97
|
+
const wrapper = container.clone();
|
|
98
|
+
|
|
99
|
+
wrapper.removeAll();
|
|
100
|
+
wrapper.append(content);
|
|
101
|
+
content = wrapper;
|
|
102
|
+
});
|
|
103
|
+
|
|
104
|
+
return content;
|
|
105
|
+
}));
|
|
106
|
+
});
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
function nestedContainerPaths(container, depth, containers = []) {
|
|
110
|
+
if (depth === 0) {
|
|
111
|
+
return [{
|
|
112
|
+
containers,
|
|
113
|
+
nodes: container.nodes,
|
|
114
|
+
}];
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
return container.nodes
|
|
118
|
+
.filter((node) => ['atrule', 'rule'].includes(node.type))
|
|
119
|
+
.flatMap((child) => nestedContainerPaths(child, depth - 1, [
|
|
120
|
+
...containers,
|
|
121
|
+
child,
|
|
122
|
+
]));
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
async function flattenUtilityLayers(root) {
|
|
126
|
+
const layers = utilityLayers(root);
|
|
127
|
+
|
|
128
|
+
for (const layer of layers) {
|
|
129
|
+
const isolatedRoot = postcss.root();
|
|
130
|
+
|
|
131
|
+
isolatedRoot.append(layer.clone());
|
|
132
|
+
await postcss([postcssNested()]).process(isolatedRoot, { from: undefined });
|
|
133
|
+
layer.replaceWith(isolatedRoot.first);
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
function utilityLayers(root) {
|
|
138
|
+
const layers = [];
|
|
139
|
+
|
|
140
|
+
root.walkAtRules('layer', (layer) => {
|
|
141
|
+
if (layer.params.trim() === 'utilities') layers.push(layer);
|
|
142
|
+
});
|
|
143
|
+
|
|
144
|
+
return layers;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
function restoreStackedVariantOrder(root) {
|
|
148
|
+
root.walkRules((rule) => {
|
|
149
|
+
const candidate = classNames(rule.selector)
|
|
150
|
+
.find((className) => (
|
|
151
|
+
className.split(':').includes('children')
|
|
152
|
+
&& ['first', 'last'].some((variant) => className.split(':').includes(variant))
|
|
153
|
+
));
|
|
154
|
+
|
|
155
|
+
if (!candidate) return;
|
|
156
|
+
|
|
157
|
+
const variants = candidate.split(':');
|
|
158
|
+
const childIndex = variants.indexOf('children');
|
|
159
|
+
const position = variants.includes('first') ? 'first' : 'last';
|
|
160
|
+
const positionIndex = variants.indexOf(position);
|
|
161
|
+
|
|
162
|
+
if (childIndex < positionIndex) {
|
|
163
|
+
rule.selector = rule.selector.replace(
|
|
164
|
+
new RegExp(`\\s*>\\s*\\*:${position}-child`, 'g'),
|
|
165
|
+
`:${position}-child > *`,
|
|
166
|
+
);
|
|
167
|
+
} else {
|
|
168
|
+
rule.selector = rule.selector.replace(
|
|
169
|
+
new RegExp(`:${position}-child\\s*>\\s*\\*`, 'g'),
|
|
170
|
+
` > *:${position}-child`,
|
|
171
|
+
);
|
|
172
|
+
}
|
|
173
|
+
});
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
function restoreLegacySpacingClassNames(root) {
|
|
177
|
+
root.walkRules((rule) => {
|
|
178
|
+
let restoredLegacyClass = false;
|
|
179
|
+
|
|
180
|
+
rule.selector = rule.selector.replace(
|
|
181
|
+
/\.((?:\\.|[^\s.#>+~,[\]()=:])+)/g,
|
|
182
|
+
(selector, escapedClassName) => {
|
|
183
|
+
const utility = baseUtility(unescapeClassName(escapedClassName));
|
|
184
|
+
const aliasEntry = legacySpacingAliases.find(([, alias]) => (
|
|
185
|
+
utility.endsWith(`-${alias}`)
|
|
186
|
+
&& legacySpacingUtilityPattern.test(utility)
|
|
187
|
+
));
|
|
188
|
+
|
|
189
|
+
if (!aliasEntry) return selector;
|
|
190
|
+
|
|
191
|
+
const [legacyName, alias] = aliasEntry;
|
|
192
|
+
const aliasStart = escapedClassName.lastIndexOf(`-${alias}`);
|
|
193
|
+
|
|
194
|
+
restoredLegacyClass = true;
|
|
195
|
+
|
|
196
|
+
return `.${escapedClassName.slice(0, aliasStart)}-${escapeClassName(legacyName)}${escapedClassName.slice(aliasStart + alias.length + 1)}`;
|
|
197
|
+
},
|
|
198
|
+
);
|
|
199
|
+
|
|
200
|
+
if (restoredLegacyClass) {
|
|
201
|
+
restoreLegacyAxisDeclarations(rule);
|
|
202
|
+
}
|
|
203
|
+
});
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
function restoreLegacyAxisDeclarations(rule) {
|
|
207
|
+
const physicalAxis = classNames(rule.selector)
|
|
208
|
+
.map(baseUtility)
|
|
209
|
+
.map((utility) => utility.match(/^-?(px|py|mx|my)-.*[+*]/)?.[1])
|
|
210
|
+
.find(Boolean);
|
|
211
|
+
const declarationMap = {
|
|
212
|
+
px: ['padding-inline', 'padding-left', 'padding-right'],
|
|
213
|
+
py: ['padding-block', 'padding-top', 'padding-bottom'],
|
|
214
|
+
mx: ['margin-inline', 'margin-left', 'margin-right'],
|
|
215
|
+
my: ['margin-block', 'margin-top', 'margin-bottom'],
|
|
216
|
+
};
|
|
217
|
+
|
|
218
|
+
if (!physicalAxis) return;
|
|
219
|
+
|
|
220
|
+
const [logicalProperty, firstProperty, secondProperty] = declarationMap[physicalAxis];
|
|
221
|
+
|
|
222
|
+
rule.walkDecls(logicalProperty, (declaration) => {
|
|
223
|
+
declaration.cloneBefore({ prop: firstProperty });
|
|
224
|
+
declaration.cloneBefore({ prop: secondProperty });
|
|
225
|
+
declaration.remove();
|
|
226
|
+
});
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
function escapeClassName(className) {
|
|
230
|
+
return className.replace(/([!"#$%&'()*+,./:;<=>?@[\\\]^`{|}~])/g, '\\$1');
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
function unescapeClassName(className) {
|
|
234
|
+
return className.replace(/\\(.)/g, '$1');
|
|
235
|
+
}
|
|
236
|
+
|
|
237
|
+
function restoreImportantDeclarations(root) {
|
|
238
|
+
root.walkDecls(importantMarker, (marker) => {
|
|
239
|
+
marker.parent.nodes
|
|
240
|
+
.filter((node) => node.type === 'decl' && node !== marker)
|
|
241
|
+
.forEach((declaration) => {
|
|
242
|
+
declaration.important = true;
|
|
243
|
+
});
|
|
244
|
+
|
|
245
|
+
marker.remove();
|
|
246
|
+
});
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
function restoreLegacyCoreUtilities(root) {
|
|
250
|
+
const restoredContainers = new WeakSet();
|
|
251
|
+
|
|
252
|
+
root.walkRules((candidateRule) => {
|
|
253
|
+
const utility = classNames(candidateRule.selector)
|
|
254
|
+
.map(baseUtility)
|
|
255
|
+
.find((className) => legacyCoreUtilities.has(className));
|
|
256
|
+
|
|
257
|
+
if (!utility) return;
|
|
258
|
+
|
|
259
|
+
const declarations = legacyCoreUtilities.get(utility);
|
|
260
|
+
const replacedProps = legacyCoreReplacementProps.get(utility);
|
|
261
|
+
|
|
262
|
+
[candidateRule, ...descendantContainers(candidateRule)]
|
|
263
|
+
.filter((container) => directDeclarations(container).length > 0)
|
|
264
|
+
.forEach((container) => {
|
|
265
|
+
if (restoredContainers.has(container)) return;
|
|
266
|
+
|
|
267
|
+
const important = directDeclarations(container)
|
|
268
|
+
.some((declaration) => declaration.important);
|
|
269
|
+
|
|
270
|
+
directDeclarations(container)
|
|
271
|
+
.filter((declaration) => replacedProps.has(declaration.prop))
|
|
272
|
+
.forEach((declaration) => declaration.remove());
|
|
273
|
+
declarations.slice().reverse().forEach(([prop, value]) => {
|
|
274
|
+
container.prepend({ prop, value, important });
|
|
275
|
+
});
|
|
276
|
+
restoredContainers.add(container);
|
|
277
|
+
});
|
|
278
|
+
});
|
|
279
|
+
}
|
|
280
|
+
|
|
281
|
+
function classNames(selector) {
|
|
282
|
+
const names = [];
|
|
283
|
+
|
|
284
|
+
for (let index = 0; index < selector.length; index += 1) {
|
|
285
|
+
if (selector[index] !== '.' || selector[index - 1] === '\\') continue;
|
|
286
|
+
|
|
287
|
+
let name = '';
|
|
288
|
+
index += 1;
|
|
289
|
+
|
|
290
|
+
while (index < selector.length) {
|
|
291
|
+
const character = selector[index];
|
|
292
|
+
|
|
293
|
+
if (character === '\\' && index + 1 < selector.length) {
|
|
294
|
+
name += selector[index + 1];
|
|
295
|
+
index += 2;
|
|
296
|
+
continue;
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
if (/[\s.#>+~,[\]()=:]/.test(character)) break;
|
|
300
|
+
|
|
301
|
+
name += character;
|
|
302
|
+
index += 1;
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
if (name) names.push(name);
|
|
306
|
+
index -= 1;
|
|
307
|
+
}
|
|
308
|
+
|
|
309
|
+
return names;
|
|
310
|
+
}
|
|
311
|
+
|
|
312
|
+
function baseUtility(className) {
|
|
313
|
+
return className.split(':').at(-1).replace(/^!|!$/g, '');
|
|
314
|
+
}
|
|
315
|
+
|
|
316
|
+
function descendantContainers(rule) {
|
|
317
|
+
const containers = [];
|
|
318
|
+
|
|
319
|
+
rule.walk((node) => {
|
|
320
|
+
if (node !== rule && node.nodes) containers.push(node);
|
|
321
|
+
});
|
|
322
|
+
|
|
323
|
+
return containers;
|
|
324
|
+
}
|
|
325
|
+
|
|
326
|
+
function directDeclarations(container) {
|
|
327
|
+
return container.nodes?.filter((node) => node.type === 'decl') ?? [];
|
|
328
|
+
}
|
|
329
|
+
|
|
330
|
+
function restoreArbitraryValueOrder(root) {
|
|
331
|
+
reorderArbitraryValueSiblings(root);
|
|
332
|
+
|
|
333
|
+
root.each((node) => {
|
|
334
|
+
if (node.nodes) restoreArbitraryValueOrder(node);
|
|
335
|
+
});
|
|
336
|
+
}
|
|
337
|
+
|
|
338
|
+
function reorderArbitraryValueSiblings(container) {
|
|
339
|
+
const groups = new Map();
|
|
340
|
+
|
|
341
|
+
container.nodes?.forEach((node, index) => {
|
|
342
|
+
if (node.type !== 'rule') return;
|
|
343
|
+
|
|
344
|
+
const candidate = classNames(node.selector)
|
|
345
|
+
.find((className) => className.includes('[') && className.includes(']'));
|
|
346
|
+
|
|
347
|
+
if (!candidate) return;
|
|
348
|
+
|
|
349
|
+
const normalizedCandidate = candidate.replace(/\[[^\]]*]/g, '[]');
|
|
350
|
+
const declarationSignature = [];
|
|
351
|
+
|
|
352
|
+
node.walkDecls((declaration) => {
|
|
353
|
+
declarationSignature.push(declaration.prop);
|
|
354
|
+
});
|
|
355
|
+
declarationSignature.sort();
|
|
356
|
+
|
|
357
|
+
const key = `${normalizedCandidate}\0${declarationSignature.join('\0')}`;
|
|
358
|
+
const group = groups.get(key) ?? [];
|
|
359
|
+
|
|
360
|
+
group.push({ candidate, index, node });
|
|
361
|
+
groups.set(key, group);
|
|
362
|
+
});
|
|
363
|
+
|
|
364
|
+
groups.forEach((group) => {
|
|
365
|
+
if (group.length < 2) return;
|
|
366
|
+
|
|
367
|
+
const sorted = [...group].sort((left, right) => {
|
|
368
|
+
if (left.candidate === right.candidate) return 0;
|
|
369
|
+
|
|
370
|
+
return left.candidate < right.candidate ? -1 : 1;
|
|
371
|
+
});
|
|
372
|
+
|
|
373
|
+
group.forEach(({ index }, sortedIndex) => {
|
|
374
|
+
const node = sorted[sortedIndex].node;
|
|
375
|
+
|
|
376
|
+
container.nodes[index] = node;
|
|
377
|
+
node.parent = container;
|
|
378
|
+
});
|
|
379
|
+
});
|
|
380
|
+
}
|
|
381
|
+
|
|
382
|
+
function reorderResponsiveVariantSiblings(container) {
|
|
383
|
+
const nodes = container.nodes ?? [];
|
|
384
|
+
const responsiveNodes = nodes.flatMap((node) => {
|
|
385
|
+
const variant = responsiveVariantForNode(node);
|
|
386
|
+
|
|
387
|
+
if (!variant) return [];
|
|
388
|
+
|
|
389
|
+
return [{
|
|
390
|
+
node,
|
|
391
|
+
order: responsiveVariantOrder.get(variant),
|
|
392
|
+
}];
|
|
393
|
+
});
|
|
394
|
+
const sorted = [...responsiveNodes].sort((left, right) => left.order - right.order);
|
|
395
|
+
const responsiveSet = new Set(responsiveNodes.map(({ node }) => node));
|
|
396
|
+
|
|
397
|
+
container.nodes = [
|
|
398
|
+
...nodes.filter((node) => !responsiveSet.has(node)),
|
|
399
|
+
...sorted.map(({ node }) => node),
|
|
400
|
+
];
|
|
401
|
+
container.nodes.forEach((node) => {
|
|
402
|
+
node.parent = container;
|
|
403
|
+
});
|
|
404
|
+
}
|
|
405
|
+
|
|
406
|
+
function responsiveVariantForNode(node) {
|
|
407
|
+
const selectors = [];
|
|
408
|
+
|
|
409
|
+
if (node.type === 'rule') selectors.push(node.selector);
|
|
410
|
+
node.walkRules?.((rule) => selectors.push(rule.selector));
|
|
411
|
+
|
|
412
|
+
return selectors
|
|
413
|
+
.flatMap(classNames)
|
|
414
|
+
.flatMap((className) => className.split(':'))
|
|
415
|
+
.find((segment) => responsiveVariantOrder.has(segment));
|
|
416
|
+
}
|
|
417
|
+
|
|
418
|
+
tailwindV4Compat.postcss = true;
|
|
419
|
+
|
|
420
|
+
module.exports = tailwindV4Compat;
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
const spacingUtilities = [
|
|
2
|
+
'p',
|
|
3
|
+
'px',
|
|
4
|
+
'py',
|
|
5
|
+
'pt',
|
|
6
|
+
'pr',
|
|
7
|
+
'pb',
|
|
8
|
+
'pl',
|
|
9
|
+
'ps',
|
|
10
|
+
'pe',
|
|
11
|
+
'm',
|
|
12
|
+
'mx',
|
|
13
|
+
'my',
|
|
14
|
+
'mt',
|
|
15
|
+
'mr',
|
|
16
|
+
'mb',
|
|
17
|
+
'ml',
|
|
18
|
+
'ms',
|
|
19
|
+
'me',
|
|
20
|
+
'gap',
|
|
21
|
+
'gap-x',
|
|
22
|
+
'gap-y',
|
|
23
|
+
'w',
|
|
24
|
+
'h',
|
|
25
|
+
'min-w',
|
|
26
|
+
'min-h',
|
|
27
|
+
'max-w',
|
|
28
|
+
'max-h',
|
|
29
|
+
];
|
|
30
|
+
|
|
31
|
+
const childrenUtilities = spacingUtilities.filter((utility) => (
|
|
32
|
+
/^(?:p[trblxyse]?|m[trblxyse]?)$/.test(utility)
|
|
33
|
+
));
|
|
34
|
+
const firstLastChildrenUtilities = ['ms', 'me'];
|
|
35
|
+
const negativeUtilities = ['m', 'mx', 'my', 'mt', 'mr', 'mb', 'ml', 'ms', 'me'];
|
|
36
|
+
const stateVariants = ['dark', 'hover', 'mobile', 'desktop'];
|
|
37
|
+
|
|
38
|
+
function generateLegacyCompatibilityCss({ spacing, screens }) {
|
|
39
|
+
const candidates = new Set();
|
|
40
|
+
|
|
41
|
+
legacySpacingAliasEntries(spacing).forEach(([, alias]) => {
|
|
42
|
+
spacingUtilities.forEach((utility) => {
|
|
43
|
+
addCandidateVariants(candidates, `${utility}-${alias}`, screens);
|
|
44
|
+
});
|
|
45
|
+
|
|
46
|
+
negativeUtilities.forEach((utility) => {
|
|
47
|
+
addCandidateVariants(candidates, `-${utility}-${alias}`, screens);
|
|
48
|
+
});
|
|
49
|
+
|
|
50
|
+
childrenUtilities.forEach((utility) => {
|
|
51
|
+
addChildrenCandidateVariants(candidates, `${utility}-${alias}`, screens);
|
|
52
|
+
});
|
|
53
|
+
|
|
54
|
+
firstLastChildrenUtilities.forEach((utility) => {
|
|
55
|
+
addPositionalChildrenCandidateVariants(
|
|
56
|
+
candidates,
|
|
57
|
+
`${utility}-${alias}`,
|
|
58
|
+
screens,
|
|
59
|
+
);
|
|
60
|
+
});
|
|
61
|
+
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
return `@source inline("${[...candidates].join(' ')}");`;
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
function withLegacySpacingAliases(spacing) {
|
|
68
|
+
return Object.fromEntries([
|
|
69
|
+
...Object.entries(spacing),
|
|
70
|
+
...legacySpacingAliasEntries(spacing)
|
|
71
|
+
.map(([legacyName, alias]) => [alias, spacing[legacyName]]),
|
|
72
|
+
]);
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
function legacySpacingAliasEntries(spacing) {
|
|
76
|
+
return Object.keys(spacing)
|
|
77
|
+
.filter((name) => /[+*]/.test(name))
|
|
78
|
+
.map((name) => [name, legacySpacingAlias(name)]);
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
function legacySpacingAlias(name) {
|
|
82
|
+
const encodedName = name
|
|
83
|
+
.replaceAll('+', '-b')
|
|
84
|
+
.replaceAll('*', '-a');
|
|
85
|
+
|
|
86
|
+
return `or-tw4-legacy-${encodedName}`;
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
function addCandidateVariants(candidates, className, screens) {
|
|
90
|
+
addImportantCandidates(candidates, className);
|
|
91
|
+
stateVariants.forEach((variant) => {
|
|
92
|
+
addImportantCandidates(candidates, `${variant}:${className}`);
|
|
93
|
+
});
|
|
94
|
+
Object.keys(screens).forEach((screen) => {
|
|
95
|
+
addImportantCandidates(candidates, `${screen}:${className}`);
|
|
96
|
+
});
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
function addChildrenCandidateVariants(candidates, className, screens) {
|
|
100
|
+
addImportantCandidates(candidates, `children:${className}`);
|
|
101
|
+
addImportantCandidates(candidates, `activated:children:${className}`);
|
|
102
|
+
Object.keys(screens).forEach((screen) => {
|
|
103
|
+
addImportantCandidates(candidates, `${screen}:children:${className}`);
|
|
104
|
+
});
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
function addPositionalChildrenCandidateVariants(candidates, className, screens) {
|
|
108
|
+
['first', 'last'].forEach((position) => {
|
|
109
|
+
addImportantCandidates(candidates, `${position}:children:${className}`);
|
|
110
|
+
Object.keys(screens).forEach((screen) => {
|
|
111
|
+
addImportantCandidates(
|
|
112
|
+
candidates,
|
|
113
|
+
`${screen}:${position}:children:${className}`,
|
|
114
|
+
);
|
|
115
|
+
});
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
function addImportantCandidates(candidates, className) {
|
|
120
|
+
const segments = className.split(':');
|
|
121
|
+
const utility = segments.pop();
|
|
122
|
+
const variants = segments.length > 0 ? `${segments.join(':')}:` : '';
|
|
123
|
+
|
|
124
|
+
candidates.add(className);
|
|
125
|
+
candidates.add(`${variants}!${utility}`);
|
|
126
|
+
candidates.add(`${className}!`);
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
module.exports = {
|
|
130
|
+
generateLegacyCompatibilityCss,
|
|
131
|
+
legacySpacingAliasEntries,
|
|
132
|
+
withLegacySpacingAliases,
|
|
133
|
+
};
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
const plugin = require('tailwindcss/plugin');
|
|
2
2
|
|
|
3
|
+
const { markImportant } = require('../compatibility/important');
|
|
3
4
|
const { resolveThemeValue } = require('../utils');
|
|
4
5
|
|
|
5
6
|
const { variants } = require('./core');
|
|
@@ -203,9 +204,9 @@ module.exports = {
|
|
|
203
204
|
return {
|
|
204
205
|
backgroundColor: resolveThemeValue(theme, `backgroundColor.${token}` + suffix, token),
|
|
205
206
|
|
|
206
|
-
[variants['disabled']]: ['white', 'black', 'transparent'].includes(token) ? null : {
|
|
207
|
-
backgroundColor:
|
|
208
|
-
},
|
|
207
|
+
[variants['disabled']]: ['white', 'black', 'transparent'].includes(token) ? null : markImportant({
|
|
208
|
+
backgroundColor: resolveThemeValue(theme, 'backgroundColor.disabled' + suffix),
|
|
209
|
+
}),
|
|
209
210
|
|
|
210
211
|
transitionProperty: 'color, background-color, border-color, outline-color',
|
|
211
212
|
transitionDuration: theme('transitionDuration.short'),
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
const plugin = require('tailwindcss/plugin');
|
|
2
2
|
|
|
3
|
+
const { markImportant } = require('../compatibility/important');
|
|
3
4
|
const { resolveThemeValue } = require('../utils');
|
|
4
5
|
|
|
5
6
|
const { variants } = require('./core');
|
|
@@ -54,9 +55,9 @@ module.exports = {
|
|
|
54
55
|
borderStyle: 'solid',
|
|
55
56
|
borderColor: resolveThemeValue(theme, `borderColor.${token}` + suffix, token),
|
|
56
57
|
|
|
57
|
-
[variants['disabled']]: ['transparent'].includes(token) ? null : {
|
|
58
|
-
borderColor:
|
|
59
|
-
},
|
|
58
|
+
[variants['disabled']]: ['transparent'].includes(token) ? null : markImportant({
|
|
59
|
+
borderColor: resolveThemeValue(theme, 'borderColor.disabled' + suffix),
|
|
60
|
+
}),
|
|
60
61
|
|
|
61
62
|
transitionProperty: 'color, background-color, border-color, outline-color',
|
|
62
63
|
transitionDuration: theme('transitionDuration.short'),
|