@master/css-engine 2.0.0-rc.70
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/README.md +57 -0
- package/dist/animation-rule.d.ts +12 -0
- package/dist/animation-rule.mjs +38 -0
- package/dist/common.d.ts +40 -0
- package/dist/common.mjs +114 -0
- package/dist/compile-manifest.d.ts +54 -0
- package/dist/compile-manifest.mjs +451 -0
- package/dist/compiler.d.ts +32 -0
- package/dist/compiler.mjs +38 -0
- package/dist/core.d.ts +141 -0
- package/dist/core.mjs +848 -0
- package/dist/emitted-globals.d.ts +4 -0
- package/dist/emitted-globals.mjs +1 -0
- package/dist/hydration-manifest.d.ts +4 -0
- package/dist/hydration-manifest.mjs +61 -0
- package/dist/index.d.ts +22 -0
- package/dist/index.mjs +15 -0
- package/dist/key-aliases.d.ts +4 -0
- package/dist/key-aliases.mjs +95 -0
- package/dist/layer.d.ts +17 -0
- package/dist/layer.mjs +78 -0
- package/dist/namespaces.d.ts +5 -0
- package/dist/namespaces.mjs +28 -0
- package/dist/native-value-namespaces.d.ts +9 -0
- package/dist/native-value-namespaces.mjs +346 -0
- package/dist/non-layer.d.ts +12 -0
- package/dist/non-layer.mjs +53 -0
- package/dist/rule.d.ts +7 -0
- package/dist/rule.mjs +14 -0
- package/dist/theme-layer.d.ts +21 -0
- package/dist/theme-layer.mjs +52 -0
- package/dist/utility-layer.d.ts +10 -0
- package/dist/utility-layer.mjs +118 -0
- package/dist/utility.d.ts +102 -0
- package/dist/utility.mjs +1263 -0
- package/dist/utils/collect-animation-names.d.ts +10 -0
- package/dist/utils/collect-animation-names.mjs +61 -0
- package/dist/utils/collect-variable-names.d.ts +3 -0
- package/dist/utils/collect-variable-names.mjs +18 -0
- package/dist/utils/compare-rule-priority.d.ts +14 -0
- package/dist/utils/compare-rule-priority.mjs +136 -0
- package/dist/utils/css-variables.d.ts +12 -0
- package/dist/utils/css-variables.mjs +197 -0
- package/dist/utils/find-native-css-rule-index.d.ts +1 -0
- package/dist/utils/find-native-css-rule-index.mjs +10 -0
- package/dist/utils/generate-at.d.ts +2 -0
- package/dist/utils/generate-at.mjs +32 -0
- package/dist/utils/generate-selector.d.ts +2 -0
- package/dist/utils/generate-selector.mjs +48 -0
- package/dist/utils/natural-compare.d.ts +2 -0
- package/dist/utils/natural-compare.mjs +6 -0
- package/dist/utils/parse-at.d.ts +44 -0
- package/dist/utils/parse-at.mjs +179 -0
- package/dist/utils/parse-pair.d.ts +8 -0
- package/dist/utils/parse-pair.mjs +46 -0
- package/dist/utils/parse-selector.d.ts +19 -0
- package/dist/utils/parse-selector.mjs +124 -0
- package/dist/utils/parse-value.d.ts +2 -0
- package/dist/utils/parse-value.mjs +37 -0
- package/dist/utils/replace-char-outside-quotes.d.ts +1 -0
- package/dist/utils/replace-char-outside-quotes.mjs +19 -0
- package/dist/utils/split-char-outside-quotes.d.ts +1 -0
- package/dist/utils/split-char-outside-quotes.mjs +27 -0
- package/dist/utils/wrap-at-rules.d.ts +1 -0
- package/dist/utils/wrap-at-rules.mjs +10 -0
- package/dist/variable-rule.d.ts +26 -0
- package/dist/variable-rule.mjs +105 -0
- package/package.json +1 -0
package/dist/core.mjs
ADDED
|
@@ -0,0 +1,848 @@
|
|
|
1
|
+
import { Utility } from './utility.mjs';
|
|
2
|
+
import ThemeLayer from './theme-layer.mjs';
|
|
3
|
+
import UtilityLayer from './utility-layer.mjs';
|
|
4
|
+
import NonLayer from './non-layer.mjs';
|
|
5
|
+
import VariableRule from './variable-rule.mjs';
|
|
6
|
+
import AnimationRule from './animation-rule.mjs';
|
|
7
|
+
import UtilityType from '@master/css-schema/utility-type';
|
|
8
|
+
import parseValue from './utils/parse-value.mjs';
|
|
9
|
+
import { isNativeCSSShorthandProperty } from '@master/css-schema/native-css-shorthand';
|
|
10
|
+
import { getCompiledManifest, cloneCompiledSettings, isPureNativeDeclarationUtilityDefinition } from './compile-manifest.mjs';
|
|
11
|
+
import { MATCH_NAME_BOUNDARY } from './common.mjs';
|
|
12
|
+
|
|
13
|
+
const builtinGroupUtility = {
|
|
14
|
+
id: 'group',
|
|
15
|
+
name: 'group',
|
|
16
|
+
type: UtilityType.Shorthand,
|
|
17
|
+
order: 0,
|
|
18
|
+
emit: {
|
|
19
|
+
type: 'group'
|
|
20
|
+
},
|
|
21
|
+
matchers: []
|
|
22
|
+
};
|
|
23
|
+
function isNameBoundary(char) {
|
|
24
|
+
return char === undefined || !/[a-zA-Z0-9-]/.test(char);
|
|
25
|
+
}
|
|
26
|
+
function getKeyedValue(className, keys) {
|
|
27
|
+
for (const key of keys){
|
|
28
|
+
const prefix = key + ':';
|
|
29
|
+
if (className.startsWith(prefix) && className.length > prefix.length) {
|
|
30
|
+
return className.slice(prefix.length);
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
function matchesStaticUtility(className, name) {
|
|
35
|
+
if (!className.startsWith(name)) return false;
|
|
36
|
+
const next = className[name.length];
|
|
37
|
+
return next === undefined || next === '!' || next === '*' || next === '>' || next === '+' || next === '~' || next === ':' || next === '[' || next === '@' || next === '_' || next === '.';
|
|
38
|
+
}
|
|
39
|
+
function getFunctionValueName(value) {
|
|
40
|
+
return /^-{0,2}([_a-zA-Z][-_a-zA-Z0-9]*)\(/.exec(value)?.[1];
|
|
41
|
+
}
|
|
42
|
+
function matchesNumericFunctionValue(value) {
|
|
43
|
+
const name = getFunctionValueName(value);
|
|
44
|
+
return name === 'calc' || name === 'clamp' || name === 'min' || name === 'max';
|
|
45
|
+
}
|
|
46
|
+
function matchesImageFunctionValue(value) {
|
|
47
|
+
const name = getFunctionValueName(value);
|
|
48
|
+
if (!name) return false;
|
|
49
|
+
return name === 'url' || name === 'element' || name === 'paint' || name === 'cross-fade' || name.endsWith('-gradient') || name.includes('image');
|
|
50
|
+
}
|
|
51
|
+
function matchesColorFunctionValue(value) {
|
|
52
|
+
const name = getFunctionValueName(value);
|
|
53
|
+
return Boolean(name) && !matchesNumericFunctionValue(value) && !matchesImageFunctionValue(value);
|
|
54
|
+
}
|
|
55
|
+
function hasTopLevelValueSeparator(value) {
|
|
56
|
+
let depth = 0;
|
|
57
|
+
let quote = '';
|
|
58
|
+
for(let index = 0; index < value.length; index++){
|
|
59
|
+
const char = value[index];
|
|
60
|
+
if (quote) {
|
|
61
|
+
if (char === '\\') {
|
|
62
|
+
index++;
|
|
63
|
+
} else if (char === quote) {
|
|
64
|
+
quote = '';
|
|
65
|
+
}
|
|
66
|
+
continue;
|
|
67
|
+
}
|
|
68
|
+
if (char === '"' || char === '\'') {
|
|
69
|
+
quote = char;
|
|
70
|
+
continue;
|
|
71
|
+
}
|
|
72
|
+
if (char === '(' || char === '[' || char === '{') {
|
|
73
|
+
depth++;
|
|
74
|
+
continue;
|
|
75
|
+
}
|
|
76
|
+
if (char === ')' || char === ']' || char === '}') {
|
|
77
|
+
if (depth > 0) depth--;
|
|
78
|
+
continue;
|
|
79
|
+
}
|
|
80
|
+
if (char === '|' && depth === 0) return true;
|
|
81
|
+
}
|
|
82
|
+
return false;
|
|
83
|
+
}
|
|
84
|
+
function matchesValueSegmentPolicy(value, matcher) {
|
|
85
|
+
return matcher.type !== 'variable' && matcher.type !== 'value' || matcher.segments === 'multiple' || !hasTopLevelValueSeparator(value);
|
|
86
|
+
}
|
|
87
|
+
function getClassKey(className) {
|
|
88
|
+
if (className[0] === '{') return;
|
|
89
|
+
const indexOfColon = className.indexOf(':');
|
|
90
|
+
if (indexOfColon <= 0) return;
|
|
91
|
+
return className.slice(0, indexOfColon);
|
|
92
|
+
}
|
|
93
|
+
function getMatchName(className) {
|
|
94
|
+
for(let index = 0; index < className.length; index++){
|
|
95
|
+
if (MATCH_NAME_BOUNDARY.has(className[index])) {
|
|
96
|
+
return index ? className.slice(0, index) : className;
|
|
97
|
+
}
|
|
98
|
+
}
|
|
99
|
+
return className;
|
|
100
|
+
}
|
|
101
|
+
class MasterCSS {
|
|
102
|
+
options;
|
|
103
|
+
definedUtilities = [];
|
|
104
|
+
variableMatcherUtilities = [];
|
|
105
|
+
valueMatcherUtilities = [];
|
|
106
|
+
keyMatcherUtilities = [];
|
|
107
|
+
patternMatcherUtilities = [];
|
|
108
|
+
arbitraryMatcherUtilities = [];
|
|
109
|
+
variableMatcherIndex = new Map();
|
|
110
|
+
valueMatcherIndex = new Map();
|
|
111
|
+
keyMatcherIndex = new Map();
|
|
112
|
+
patternMatcherIndex;
|
|
113
|
+
arbitraryStaticMatcherIndex;
|
|
114
|
+
settings;
|
|
115
|
+
rules = [];
|
|
116
|
+
classUtilities = new Map();
|
|
117
|
+
animationsNonLayer = new NonLayer(this);
|
|
118
|
+
baseLayer = new UtilityLayer('base', this);
|
|
119
|
+
themeLayer = new ThemeLayer('theme', this);
|
|
120
|
+
defaultsLayer = new UtilityLayer('defaults', this);
|
|
121
|
+
componentsLayer = new UtilityLayer('components', this);
|
|
122
|
+
utilitiesLayer = new UtilityLayer('utilities', this);
|
|
123
|
+
selectors = new Map();
|
|
124
|
+
variables = new Map();
|
|
125
|
+
modes = [];
|
|
126
|
+
atRules = new Map();
|
|
127
|
+
variants = new Map();
|
|
128
|
+
breakpointAtRules = new Map();
|
|
129
|
+
containerAtRules = new Map();
|
|
130
|
+
animations = new Map();
|
|
131
|
+
staticVariableTokens = new Set();
|
|
132
|
+
staticAnimationTokens = new Set();
|
|
133
|
+
emittedGlobals = {
|
|
134
|
+
variables: {},
|
|
135
|
+
animations: {}
|
|
136
|
+
};
|
|
137
|
+
nativeDeclarationFastPathBlockedProperties = new Set();
|
|
138
|
+
nativeDeclarationMatches = new Map();
|
|
139
|
+
nativeDeclarationUtilities = new Map();
|
|
140
|
+
nativeValueNamespaceUtilities = new Map();
|
|
141
|
+
keyAliases = new Map();
|
|
142
|
+
manifest;
|
|
143
|
+
static create(options) {
|
|
144
|
+
const { manifest, emittedGlobals, ...engineOptions } = options;
|
|
145
|
+
return new this(manifest, emittedGlobals, engineOptions);
|
|
146
|
+
}
|
|
147
|
+
constructor(manifest, emittedGlobals, options = {}){
|
|
148
|
+
this.options = options;
|
|
149
|
+
this.loadManifest(manifest);
|
|
150
|
+
this.registerEmittedGlobals(emittedGlobals);
|
|
151
|
+
if (new.target === MasterCSS) {
|
|
152
|
+
this.insertStaticResources();
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
get text() {
|
|
156
|
+
return this.rules.sort((a, b)=>{
|
|
157
|
+
const order = [
|
|
158
|
+
'theme',
|
|
159
|
+
'base',
|
|
160
|
+
'defaults',
|
|
161
|
+
'components',
|
|
162
|
+
'utilities'
|
|
163
|
+
];
|
|
164
|
+
const indexA = order.indexOf(a.name) === -1 ? Infinity : order.indexOf(a.name);
|
|
165
|
+
const indexB = order.indexOf(b.name) === -1 ? Infinity : order.indexOf(b.name);
|
|
166
|
+
return indexA - indexB;
|
|
167
|
+
}).map(({ text })=>text).join('');
|
|
168
|
+
}
|
|
169
|
+
getUtilityLayer(layerName = 'utilities') {
|
|
170
|
+
switch(layerName){
|
|
171
|
+
case 'base':
|
|
172
|
+
return this.baseLayer;
|
|
173
|
+
case 'defaults':
|
|
174
|
+
return this.defaultsLayer;
|
|
175
|
+
case 'components':
|
|
176
|
+
return this.componentsLayer;
|
|
177
|
+
case 'utilities':
|
|
178
|
+
return this.utilitiesLayer;
|
|
179
|
+
default:
|
|
180
|
+
throw new Error(`Unsupported utility layer: ${layerName}`);
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
getUtilityLayers() {
|
|
184
|
+
return [
|
|
185
|
+
this.baseLayer,
|
|
186
|
+
this.defaultsLayer,
|
|
187
|
+
this.componentsLayer,
|
|
188
|
+
this.utilitiesLayer
|
|
189
|
+
];
|
|
190
|
+
}
|
|
191
|
+
loadManifest(manifest) {
|
|
192
|
+
const compiledManifest = getCompiledManifest(manifest);
|
|
193
|
+
this.manifest = compiledManifest.manifest;
|
|
194
|
+
this.settings = cloneCompiledSettings(compiledManifest.settings);
|
|
195
|
+
this.definedUtilities = compiledManifest.definedUtilities;
|
|
196
|
+
this.variableMatcherUtilities = compiledManifest.variableMatcherUtilities;
|
|
197
|
+
this.valueMatcherUtilities = compiledManifest.valueMatcherUtilities;
|
|
198
|
+
this.keyMatcherUtilities = compiledManifest.keyMatcherUtilities;
|
|
199
|
+
this.patternMatcherUtilities = compiledManifest.patternMatcherUtilities;
|
|
200
|
+
this.arbitraryMatcherUtilities = compiledManifest.arbitraryMatcherUtilities;
|
|
201
|
+
this.variableMatcherIndex = compiledManifest.variableMatcherIndex;
|
|
202
|
+
this.valueMatcherIndex = compiledManifest.valueMatcherIndex;
|
|
203
|
+
this.keyMatcherIndex = compiledManifest.keyMatcherIndex;
|
|
204
|
+
this.patternMatcherIndex = compiledManifest.patternMatcherIndex;
|
|
205
|
+
this.arbitraryStaticMatcherIndex = compiledManifest.arbitraryStaticMatcherIndex;
|
|
206
|
+
this.selectors = compiledManifest.selectors;
|
|
207
|
+
this.variables = compiledManifest.variables;
|
|
208
|
+
this.modes = [
|
|
209
|
+
...compiledManifest.modes
|
|
210
|
+
];
|
|
211
|
+
this.atRules = compiledManifest.atRules;
|
|
212
|
+
this.variants = compiledManifest.variants;
|
|
213
|
+
this.breakpointAtRules = compiledManifest.breakpointAtRules;
|
|
214
|
+
this.containerAtRules = compiledManifest.containerAtRules;
|
|
215
|
+
this.animations = compiledManifest.animations;
|
|
216
|
+
this.nativeDeclarationFastPathBlockedProperties = compiledManifest.nativeDeclarationFastPathBlockedProperties;
|
|
217
|
+
this.nativeValueNamespaceUtilities = compiledManifest.nativeValueNamespaceUtilities;
|
|
218
|
+
this.keyAliases = compiledManifest.keyAliases;
|
|
219
|
+
}
|
|
220
|
+
applyEmittedGlobalsCounts(emittedGlobals) {
|
|
221
|
+
for (const [name, count] of Object.entries(emittedGlobals.variables || {})){
|
|
222
|
+
if (!count) continue;
|
|
223
|
+
this.themeLayer.tokenCounts.set(name, (this.themeLayer.tokenCounts.get(name) || 0) + count);
|
|
224
|
+
}
|
|
225
|
+
for (const [name, count] of Object.entries(emittedGlobals.animations || {})){
|
|
226
|
+
if (!count) continue;
|
|
227
|
+
this.animationsNonLayer.tokenCounts.set(name, (this.animationsNonLayer.tokenCounts.get(name) || 0) + count);
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
registerEmittedGlobals(emittedGlobals) {
|
|
231
|
+
if (!emittedGlobals) return;
|
|
232
|
+
for (const [name, count] of Object.entries(emittedGlobals.variables || {})){
|
|
233
|
+
if (!count) continue;
|
|
234
|
+
this.emittedGlobals.variables[name] = (this.emittedGlobals.variables[name] || 0) + count;
|
|
235
|
+
}
|
|
236
|
+
for (const [name, count] of Object.entries(emittedGlobals.animations || {})){
|
|
237
|
+
if (!count) continue;
|
|
238
|
+
this.emittedGlobals.animations[name] = (this.emittedGlobals.animations[name] || 0) + count;
|
|
239
|
+
}
|
|
240
|
+
this.applyEmittedGlobalsCounts(emittedGlobals);
|
|
241
|
+
}
|
|
242
|
+
isEmittedGlobalsVariable(name) {
|
|
243
|
+
return Boolean(this.emittedGlobals.variables[name]);
|
|
244
|
+
}
|
|
245
|
+
isEmittedGlobalsAnimation(name) {
|
|
246
|
+
return Boolean(this.emittedGlobals.animations[name]);
|
|
247
|
+
}
|
|
248
|
+
insertStaticVariable(name, visited = new Set()) {
|
|
249
|
+
if (visited.has(name)) return;
|
|
250
|
+
visited.add(name);
|
|
251
|
+
const variable = this.variables.get(name);
|
|
252
|
+
if (!variable || variable.inline) return;
|
|
253
|
+
if (!this.staticVariableTokens.has(name)) {
|
|
254
|
+
if (!this.isEmittedGlobalsVariable(name)) {
|
|
255
|
+
if (!this.themeLayer.get(name)) {
|
|
256
|
+
this.themeLayer.insert(new VariableRule(name, variable, this));
|
|
257
|
+
}
|
|
258
|
+
const count = this.themeLayer.tokenCounts.get(name) || 0;
|
|
259
|
+
this.themeLayer.tokenCounts.set(name, count + 1);
|
|
260
|
+
}
|
|
261
|
+
this.staticVariableTokens.add(name);
|
|
262
|
+
}
|
|
263
|
+
variable.dependencies?.forEach((dependency)=>this.insertStaticVariable(dependency, visited));
|
|
264
|
+
}
|
|
265
|
+
insertStaticAnimation(name) {
|
|
266
|
+
if (this.staticAnimationTokens.has(name)) return;
|
|
267
|
+
const keyframes = this.animations.get(name);
|
|
268
|
+
if (!keyframes) return;
|
|
269
|
+
let rule = this.animationsNonLayer.rules.find((eachRule)=>eachRule.name === name);
|
|
270
|
+
if (!this.isEmittedGlobalsAnimation(name)) {
|
|
271
|
+
if (!rule) {
|
|
272
|
+
rule = new AnimationRule(name, keyframes, this);
|
|
273
|
+
this.animationsNonLayer.insert(rule);
|
|
274
|
+
}
|
|
275
|
+
const count = this.animationsNonLayer.tokenCounts.get(name) || 0;
|
|
276
|
+
this.animationsNonLayer.tokenCounts.set(name, count + 1);
|
|
277
|
+
} else if (!rule) {
|
|
278
|
+
rule = new AnimationRule(name, keyframes, this);
|
|
279
|
+
}
|
|
280
|
+
this.staticAnimationTokens.add(name);
|
|
281
|
+
rule.variableNames?.forEach((variableName)=>this.insertStaticVariable(variableName));
|
|
282
|
+
}
|
|
283
|
+
insertStaticResources() {
|
|
284
|
+
for (const [name, variable] of this.variables){
|
|
285
|
+
if (variable.static) this.insertStaticVariable(name);
|
|
286
|
+
}
|
|
287
|
+
for (const name of this.animations.keys()){
|
|
288
|
+
if (this.manifest.animationOptions?.[name]?.static) this.insertStaticAnimation(name);
|
|
289
|
+
}
|
|
290
|
+
return this;
|
|
291
|
+
}
|
|
292
|
+
resolveVariant(token) {
|
|
293
|
+
return this.variants.get(token);
|
|
294
|
+
}
|
|
295
|
+
parseValue(token, unit = '') {
|
|
296
|
+
return parseValue(token, unit, this.settings.rootSize);
|
|
297
|
+
}
|
|
298
|
+
/**
|
|
299
|
+
* Match check if Master CSS utility
|
|
300
|
+
* @param className
|
|
301
|
+
* @returns css text
|
|
302
|
+
*/ matchesMatcher(className, utility, matcher) {
|
|
303
|
+
switch(matcher.type){
|
|
304
|
+
case 'static':
|
|
305
|
+
return matchesStaticUtility(className, matcher.name);
|
|
306
|
+
case 'key':
|
|
307
|
+
return getKeyedValue(className, matcher.keys) !== undefined;
|
|
308
|
+
case 'variable':
|
|
309
|
+
{
|
|
310
|
+
const value = getKeyedValue(className, matcher.keys);
|
|
311
|
+
if (value === undefined || !utility.variables?.size) return false;
|
|
312
|
+
if (!matchesValueSegmentPolicy(value, matcher)) return false;
|
|
313
|
+
for (const [variableKey, variable] of utility.variables){
|
|
314
|
+
if (value.startsWith(variableKey) && isNameBoundary(value[variableKey.length])) return true;
|
|
315
|
+
const negativeVariableKey = '-' + variableKey;
|
|
316
|
+
if (variableKey[0] !== '-' && variable.type === 'number' && value.startsWith(negativeVariableKey) && isNameBoundary(value[negativeVariableKey.length])) return true;
|
|
317
|
+
}
|
|
318
|
+
return false;
|
|
319
|
+
}
|
|
320
|
+
case 'value':
|
|
321
|
+
{
|
|
322
|
+
const value = getKeyedValue(className, matcher.keys);
|
|
323
|
+
if (value === undefined) return false;
|
|
324
|
+
if (!matchesValueSegmentPolicy(value, matcher)) return false;
|
|
325
|
+
switch(utility.kind){
|
|
326
|
+
case 'color':
|
|
327
|
+
return value[0] === '#' || matchesColorFunctionValue(value) || value.startsWith('currentColor') && isNameBoundary(value[12]) || value.startsWith('transparent') && isNameBoundary(value[11]);
|
|
328
|
+
case 'number':
|
|
329
|
+
return /[\d.]/.test(value[0]) || matchesNumericFunctionValue(value);
|
|
330
|
+
case 'image':
|
|
331
|
+
return matchesImageFunctionValue(value);
|
|
332
|
+
default:
|
|
333
|
+
return false;
|
|
334
|
+
}
|
|
335
|
+
}
|
|
336
|
+
case 'pattern':
|
|
337
|
+
return matcher.values.some((value)=>matchesStaticUtility(className, matcher.prefix + value));
|
|
338
|
+
}
|
|
339
|
+
}
|
|
340
|
+
matchesUtility(className, utility, matcherType) {
|
|
341
|
+
return utility.matchers.some((matcher)=>(!matcherType || matcher.type === matcherType) && this.matchesMatcher(className, utility, matcher));
|
|
342
|
+
}
|
|
343
|
+
matchesExactUtilityDefinition(className, utility) {
|
|
344
|
+
return utility.matchers.some((matcher)=>matcher.type === 'static' && matchesStaticUtility(className, matcher.name));
|
|
345
|
+
}
|
|
346
|
+
hasClassKey(className) {
|
|
347
|
+
const key = getClassKey(className);
|
|
348
|
+
return Boolean(key && !key.startsWith('--'));
|
|
349
|
+
}
|
|
350
|
+
isGroupClassName(className) {
|
|
351
|
+
return className[0] === '{' && className.includes('}');
|
|
352
|
+
}
|
|
353
|
+
getClassKeyAlias(className) {
|
|
354
|
+
const key = getClassKey(className);
|
|
355
|
+
if (!key) return;
|
|
356
|
+
if (key.startsWith('--')) return;
|
|
357
|
+
const canonicalKey = this.keyAliases.get(key);
|
|
358
|
+
if (!canonicalKey) return;
|
|
359
|
+
return {
|
|
360
|
+
canonicalKey,
|
|
361
|
+
indexOfColon: key.length,
|
|
362
|
+
key
|
|
363
|
+
};
|
|
364
|
+
}
|
|
365
|
+
canonicalizeClassName(className, fixedClass) {
|
|
366
|
+
const keyAlias = this.getClassKeyAlias(className);
|
|
367
|
+
if (!keyAlias) return {
|
|
368
|
+
className,
|
|
369
|
+
fixedClass
|
|
370
|
+
};
|
|
371
|
+
return {
|
|
372
|
+
className: keyAlias.canonicalKey + className.slice(keyAlias.indexOfColon),
|
|
373
|
+
fixedClass
|
|
374
|
+
};
|
|
375
|
+
}
|
|
376
|
+
matchResolvedClassName(className) {
|
|
377
|
+
const classKey = getClassKey(className);
|
|
378
|
+
for (const eachUtility of classKey ? this.variableMatcherIndex.get(classKey) || [] : []){
|
|
379
|
+
if (this.matchesUtility(className, eachUtility, 'variable')) return eachUtility;
|
|
380
|
+
}
|
|
381
|
+
for (const eachUtility of classKey ? this.valueMatcherIndex.get(classKey) || [] : []){
|
|
382
|
+
if (this.matchesUtility(className, eachUtility, 'value')) return eachUtility;
|
|
383
|
+
}
|
|
384
|
+
for (const eachUtility of classKey ? this.keyMatcherIndex.get(classKey) || [] : []){
|
|
385
|
+
if (this.matchesUtility(className, eachUtility, 'key')) return eachUtility;
|
|
386
|
+
}
|
|
387
|
+
if (this.arbitraryStaticMatcherIndex) {
|
|
388
|
+
for (const eachUtility of this.arbitraryStaticMatcherIndex.get(getMatchName(className)) || []){
|
|
389
|
+
if (this.matchesUtility(className, eachUtility)) return eachUtility;
|
|
390
|
+
}
|
|
391
|
+
} else {
|
|
392
|
+
for (const eachUtility of this.arbitraryMatcherUtilities){
|
|
393
|
+
if (this.matchesUtility(className, eachUtility)) return eachUtility;
|
|
394
|
+
}
|
|
395
|
+
}
|
|
396
|
+
if (this.patternMatcherIndex) {
|
|
397
|
+
for (const eachUtility of this.patternMatcherIndex.get(getMatchName(className)) || []){
|
|
398
|
+
if (this.matchesUtility(className, eachUtility, 'pattern')) return eachUtility;
|
|
399
|
+
}
|
|
400
|
+
} else {
|
|
401
|
+
for (const eachUtility of this.patternMatcherUtilities){
|
|
402
|
+
if (this.matchesUtility(className, eachUtility, 'pattern')) return eachUtility;
|
|
403
|
+
}
|
|
404
|
+
}
|
|
405
|
+
}
|
|
406
|
+
createGroupUtility(className, fixedClass, mode, branchIndex = 0) {
|
|
407
|
+
if (!this.isGroupClassName(className)) return;
|
|
408
|
+
return this.createRuleWithDefinition(className, builtinGroupUtility, fixedClass, mode, branchIndex);
|
|
409
|
+
}
|
|
410
|
+
createAllGroupUtilities(className, fixedClass, mode) {
|
|
411
|
+
const utility = this.createGroupUtility(className, fixedClass, mode);
|
|
412
|
+
if (!utility?.valid) return [];
|
|
413
|
+
const utilities = [
|
|
414
|
+
utility
|
|
415
|
+
];
|
|
416
|
+
for(let branchIndex = 1; branchIndex < utility.branchCount; branchIndex++){
|
|
417
|
+
const branchUtility = this.createGroupUtility(className, fixedClass, mode, branchIndex);
|
|
418
|
+
if (branchUtility?.valid) utilities.push(branchUtility);
|
|
419
|
+
}
|
|
420
|
+
return utilities;
|
|
421
|
+
}
|
|
422
|
+
matchRawManagedClassName(className) {
|
|
423
|
+
const classKey = getClassKey(className);
|
|
424
|
+
if (!classKey) return;
|
|
425
|
+
for (const eachUtility of this.variableMatcherIndex.get(classKey) || []){
|
|
426
|
+
if (this.matchesUtility(className, eachUtility, 'variable')) return eachUtility;
|
|
427
|
+
}
|
|
428
|
+
for (const eachUtility of this.valueMatcherIndex.get(classKey) || []){
|
|
429
|
+
if (this.matchesUtility(className, eachUtility, 'value')) return eachUtility;
|
|
430
|
+
}
|
|
431
|
+
for (const eachUtility of this.keyMatcherIndex.get(classKey) || []){
|
|
432
|
+
if (this.matchesUtility(className, eachUtility, 'key')) return eachUtility;
|
|
433
|
+
}
|
|
434
|
+
if (this.patternMatcherIndex) {
|
|
435
|
+
for (const eachUtility of this.patternMatcherIndex.get(getMatchName(className)) || []){
|
|
436
|
+
if (this.matchesUtility(className, eachUtility, 'pattern')) return eachUtility;
|
|
437
|
+
}
|
|
438
|
+
} else {
|
|
439
|
+
for (const eachUtility of this.patternMatcherUtilities){
|
|
440
|
+
if (this.matchesUtility(className, eachUtility, 'pattern')) return eachUtility;
|
|
441
|
+
}
|
|
442
|
+
}
|
|
443
|
+
}
|
|
444
|
+
match(className) {
|
|
445
|
+
if (this.isGroupClassName(className)) return builtinGroupUtility;
|
|
446
|
+
if (this.hasClassKey(className)) {
|
|
447
|
+
const rawRegisteredUtility = this.matchRawManagedClassName(className);
|
|
448
|
+
if (rawRegisteredUtility) return rawRegisteredUtility;
|
|
449
|
+
}
|
|
450
|
+
return this.matchResolvedClassName(this.canonicalizeClassName(className).className);
|
|
451
|
+
}
|
|
452
|
+
matchAllResolvedClassName(className) {
|
|
453
|
+
const classKey = getClassKey(className);
|
|
454
|
+
/**
|
|
455
|
+
* 1. variable
|
|
456
|
+
* @example fg:primary bg:blue
|
|
457
|
+
*/ for (const eachUtility of classKey ? this.variableMatcherIndex.get(classKey) || [] : []){
|
|
458
|
+
if (this.matchesUtility(className, eachUtility, 'variable')) return [
|
|
459
|
+
eachUtility
|
|
460
|
+
];
|
|
461
|
+
}
|
|
462
|
+
/**
|
|
463
|
+
* 2. value (ambiguous key with raw color/number/image)
|
|
464
|
+
* @example bg:#fff font:.75rem
|
|
465
|
+
*/ for (const eachUtility of classKey ? this.valueMatcherIndex.get(classKey) || [] : []){
|
|
466
|
+
if (this.matchesUtility(className, eachUtility, 'value')) return [
|
|
467
|
+
eachUtility
|
|
468
|
+
];
|
|
469
|
+
}
|
|
470
|
+
/**
|
|
471
|
+
* 3. full key
|
|
472
|
+
* @example text-align:center color:blue-40
|
|
473
|
+
*/ for (const eachUtility of classKey ? this.keyMatcherIndex.get(classKey) || [] : []){
|
|
474
|
+
if (this.matchesUtility(className, eachUtility, 'key')) return [
|
|
475
|
+
eachUtility
|
|
476
|
+
];
|
|
477
|
+
}
|
|
478
|
+
/**
|
|
479
|
+
* 4. arbitrary
|
|
480
|
+
* @example custom RegExp, utility
|
|
481
|
+
*/ const staticUtilities = [];
|
|
482
|
+
if (this.arbitraryStaticMatcherIndex) {
|
|
483
|
+
for (const eachUtility of this.arbitraryStaticMatcherIndex.get(getMatchName(className)) || []){
|
|
484
|
+
if (this.matchesUtility(className, eachUtility)) staticUtilities.push(eachUtility);
|
|
485
|
+
}
|
|
486
|
+
} else {
|
|
487
|
+
for (const eachUtility of this.arbitraryMatcherUtilities){
|
|
488
|
+
if (!this.matchesUtility(className, eachUtility)) continue;
|
|
489
|
+
if (eachUtility.matchers.some((matcher)=>matcher.type === 'static')) {
|
|
490
|
+
staticUtilities.push(eachUtility);
|
|
491
|
+
continue;
|
|
492
|
+
}
|
|
493
|
+
return [
|
|
494
|
+
eachUtility
|
|
495
|
+
];
|
|
496
|
+
}
|
|
497
|
+
}
|
|
498
|
+
if (staticUtilities.length) return staticUtilities;
|
|
499
|
+
/**
|
|
500
|
+
* 5. enum pattern
|
|
501
|
+
* @example text-center bg-cover
|
|
502
|
+
*/ if (this.patternMatcherIndex) {
|
|
503
|
+
for (const eachUtility of this.patternMatcherIndex.get(getMatchName(className)) || []){
|
|
504
|
+
if (this.matchesUtility(className, eachUtility, 'pattern')) return [
|
|
505
|
+
eachUtility
|
|
506
|
+
];
|
|
507
|
+
}
|
|
508
|
+
} else {
|
|
509
|
+
for (const eachUtility of this.patternMatcherUtilities){
|
|
510
|
+
if (this.matchesUtility(className, eachUtility, 'pattern')) return [
|
|
511
|
+
eachUtility
|
|
512
|
+
];
|
|
513
|
+
}
|
|
514
|
+
}
|
|
515
|
+
return [];
|
|
516
|
+
}
|
|
517
|
+
matchAllRawManagedClassName(className) {
|
|
518
|
+
const classKey = getClassKey(className);
|
|
519
|
+
if (!classKey) return [];
|
|
520
|
+
for (const eachUtility of this.variableMatcherIndex.get(classKey) || []){
|
|
521
|
+
if (this.matchesUtility(className, eachUtility, 'variable')) return [
|
|
522
|
+
eachUtility
|
|
523
|
+
];
|
|
524
|
+
}
|
|
525
|
+
for (const eachUtility of this.valueMatcherIndex.get(classKey) || []){
|
|
526
|
+
if (this.matchesUtility(className, eachUtility, 'value')) return [
|
|
527
|
+
eachUtility
|
|
528
|
+
];
|
|
529
|
+
}
|
|
530
|
+
for (const eachUtility of this.keyMatcherIndex.get(classKey) || []){
|
|
531
|
+
if (this.matchesUtility(className, eachUtility, 'key')) return [
|
|
532
|
+
eachUtility
|
|
533
|
+
];
|
|
534
|
+
}
|
|
535
|
+
if (this.patternMatcherIndex) {
|
|
536
|
+
for (const eachUtility of this.patternMatcherIndex.get(getMatchName(className)) || []){
|
|
537
|
+
if (this.matchesUtility(className, eachUtility, 'pattern')) return [
|
|
538
|
+
eachUtility
|
|
539
|
+
];
|
|
540
|
+
}
|
|
541
|
+
} else {
|
|
542
|
+
for (const eachUtility of this.patternMatcherUtilities){
|
|
543
|
+
if (this.matchesUtility(className, eachUtility, 'pattern')) return [
|
|
544
|
+
eachUtility
|
|
545
|
+
];
|
|
546
|
+
}
|
|
547
|
+
}
|
|
548
|
+
return [];
|
|
549
|
+
}
|
|
550
|
+
matchAll(className) {
|
|
551
|
+
if (this.isGroupClassName(className)) return [
|
|
552
|
+
builtinGroupUtility
|
|
553
|
+
];
|
|
554
|
+
if (this.hasClassKey(className)) {
|
|
555
|
+
const rawRegisteredUtilities = this.matchAllRawManagedClassName(className);
|
|
556
|
+
if (rawRegisteredUtilities.length) return rawRegisteredUtilities;
|
|
557
|
+
}
|
|
558
|
+
return this.matchAllResolvedClassName(this.canonicalizeClassName(className).className);
|
|
559
|
+
}
|
|
560
|
+
parseNativeDeclarationProperty(className) {
|
|
561
|
+
const indexOfColon = className.indexOf(':');
|
|
562
|
+
if (indexOfColon <= 0) return;
|
|
563
|
+
const property = className.slice(0, indexOfColon);
|
|
564
|
+
if (!/^(?:--[-_a-zA-Z0-9]+|-?[_a-zA-Z][-_a-zA-Z0-9]*)$/.test(property)) return;
|
|
565
|
+
return property;
|
|
566
|
+
}
|
|
567
|
+
getNativeDeclarationUtility(property) {
|
|
568
|
+
const cached = this.nativeDeclarationUtilities.get(property);
|
|
569
|
+
if (cached) return cached;
|
|
570
|
+
const utility = {
|
|
571
|
+
id: property,
|
|
572
|
+
name: property,
|
|
573
|
+
type: isNativeCSSShorthandProperty(property) ? UtilityType.Shorthand : UtilityType.Normal,
|
|
574
|
+
order: 0,
|
|
575
|
+
emit: {
|
|
576
|
+
type: 'property',
|
|
577
|
+
property
|
|
578
|
+
},
|
|
579
|
+
matchers: [
|
|
580
|
+
{
|
|
581
|
+
type: 'key',
|
|
582
|
+
keys: [
|
|
583
|
+
property
|
|
584
|
+
]
|
|
585
|
+
}
|
|
586
|
+
]
|
|
587
|
+
};
|
|
588
|
+
this.nativeDeclarationUtilities.set(property, utility);
|
|
589
|
+
return utility;
|
|
590
|
+
}
|
|
591
|
+
matchNativeDeclaration(declaration) {
|
|
592
|
+
if (declaration.property.startsWith('--')) return true;
|
|
593
|
+
const matcher = this.options.nativeDeclarationMatcher;
|
|
594
|
+
if (!matcher) return false;
|
|
595
|
+
const cacheKey = declaration.property + '\0' + declaration.value;
|
|
596
|
+
const cached = this.nativeDeclarationMatches.get(cacheKey);
|
|
597
|
+
if (cached !== undefined) return cached;
|
|
598
|
+
const matched = matcher(declaration);
|
|
599
|
+
this.nativeDeclarationMatches.set(cacheKey, matched);
|
|
600
|
+
return matched;
|
|
601
|
+
}
|
|
602
|
+
isNativeDeclarationUtility(utility) {
|
|
603
|
+
const entries = Object.entries(utility.declarations || {});
|
|
604
|
+
if (entries.length !== 1) return false;
|
|
605
|
+
const [[property, value]] = entries;
|
|
606
|
+
return this.matchNativeDeclaration({
|
|
607
|
+
property,
|
|
608
|
+
value: String(value)
|
|
609
|
+
});
|
|
610
|
+
}
|
|
611
|
+
shouldValidateNativeDeclarationUtility(utility) {
|
|
612
|
+
if (!this.options.nativeDeclarationMatcher) return false;
|
|
613
|
+
return isPureNativeDeclarationUtilityDefinition(utility) && utility.matchers.every((matcher)=>matcher.type === 'key');
|
|
614
|
+
}
|
|
615
|
+
createNativeDeclarationFallback(className, fixedClass, mode, sourceClassName = className) {
|
|
616
|
+
if (!this.options.nativeDeclarationMatcher) return [];
|
|
617
|
+
const property = this.parseNativeDeclarationProperty(className);
|
|
618
|
+
if (!property) return [];
|
|
619
|
+
const registeredUtility = this.getNativeDeclarationUtility(property);
|
|
620
|
+
const utility = this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode);
|
|
621
|
+
if (!utility?.valid || !this.isNativeDeclarationUtility(utility)) return [];
|
|
622
|
+
const utilities = [
|
|
623
|
+
utility
|
|
624
|
+
];
|
|
625
|
+
for(let branchIndex = 1; branchIndex < utility.branchCount; branchIndex++){
|
|
626
|
+
const branchUtility = this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode, branchIndex);
|
|
627
|
+
if (branchUtility?.valid && this.isNativeDeclarationUtility(branchUtility)) utilities.push(branchUtility);
|
|
628
|
+
}
|
|
629
|
+
return utilities;
|
|
630
|
+
}
|
|
631
|
+
createNativeValueNamespaceFallback(className, fixedClass, mode, sourceClassName = className) {
|
|
632
|
+
const property = this.parseNativeDeclarationProperty(className);
|
|
633
|
+
if (!property) return [];
|
|
634
|
+
const registeredUtility = this.nativeValueNamespaceUtilities.get(property);
|
|
635
|
+
if (!registeredUtility) return [];
|
|
636
|
+
const utility = this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode);
|
|
637
|
+
if (!utility?.valid || this.options.nativeDeclarationMatcher && !this.isNativeDeclarationUtility(utility)) return [];
|
|
638
|
+
const utilities = [
|
|
639
|
+
utility
|
|
640
|
+
];
|
|
641
|
+
for(let branchIndex = 1; branchIndex < utility.branchCount; branchIndex++){
|
|
642
|
+
const branchUtility = this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode, branchIndex);
|
|
643
|
+
if (branchUtility?.valid && (!this.options.nativeDeclarationMatcher || this.isNativeDeclarationUtility(branchUtility))) {
|
|
644
|
+
utilities.push(branchUtility);
|
|
645
|
+
}
|
|
646
|
+
}
|
|
647
|
+
return utilities;
|
|
648
|
+
}
|
|
649
|
+
createNativeValueNamespaceFastPath(className, fixedClass, mode, sourceClassName = className) {
|
|
650
|
+
const property = this.parseNativeDeclarationProperty(className);
|
|
651
|
+
if (!property) return [];
|
|
652
|
+
if (this.nativeDeclarationFastPathBlockedProperties.has(property)) return [];
|
|
653
|
+
return this.createNativeValueNamespaceFallback(className, fixedClass, mode, sourceClassName);
|
|
654
|
+
}
|
|
655
|
+
createNativeDeclarationFastPath(className, fixedClass, mode, sourceClassName = className) {
|
|
656
|
+
const property = this.parseNativeDeclarationProperty(className);
|
|
657
|
+
if (!property) return [];
|
|
658
|
+
if (!property.startsWith('--') && this.nativeDeclarationFastPathBlockedProperties.has(property)) return [];
|
|
659
|
+
return this.createNativeDeclarationFallback(className, fixedClass, mode, sourceClassName);
|
|
660
|
+
}
|
|
661
|
+
/**
|
|
662
|
+
* Generate utilities from class name
|
|
663
|
+
* @param className
|
|
664
|
+
* @returns Utility[]
|
|
665
|
+
*/ generate(className, mode) {
|
|
666
|
+
return this.createRules(className, undefined, mode);
|
|
667
|
+
}
|
|
668
|
+
/**
|
|
669
|
+
* Create utility from given class name
|
|
670
|
+
* @param className
|
|
671
|
+
* @returns Utility
|
|
672
|
+
*/ createRule(className, fixedClass, mode) {
|
|
673
|
+
const groupUtility = this.createGroupUtility(className, fixedClass, mode);
|
|
674
|
+
if (groupUtility) return groupUtility;
|
|
675
|
+
const sourceClassName = className;
|
|
676
|
+
if (this.hasClassKey(className)) {
|
|
677
|
+
const rawRegisteredUtility = this.matchRawManagedClassName(className);
|
|
678
|
+
if (rawRegisteredUtility) {
|
|
679
|
+
const utility = this.createRuleWithDefinition(sourceClassName, rawRegisteredUtility, fixedClass, mode);
|
|
680
|
+
if (utility?.valid) return utility;
|
|
681
|
+
}
|
|
682
|
+
}
|
|
683
|
+
const canonicalClass = this.canonicalizeClassName(className, fixedClass);
|
|
684
|
+
className = canonicalClass.className;
|
|
685
|
+
fixedClass = canonicalClass.fixedClass;
|
|
686
|
+
const fastPathNativeValueNamespaceUtilities = this.createNativeValueNamespaceFastPath(className, fixedClass, mode, sourceClassName);
|
|
687
|
+
if (fastPathNativeValueNamespaceUtilities.length) return fastPathNativeValueNamespaceUtilities[0];
|
|
688
|
+
const fastPathNativeUtilities = this.createNativeDeclarationFastPath(className, fixedClass, mode, sourceClassName);
|
|
689
|
+
if (fastPathNativeUtilities.length) return fastPathNativeUtilities[0];
|
|
690
|
+
const registeredUtility = this.matchResolvedClassName(className);
|
|
691
|
+
if (registeredUtility && this.matchesExactUtilityDefinition(className, registeredUtility)) {
|
|
692
|
+
const nativeValueNamespaceUtilities = this.createNativeValueNamespaceFallback(className, fixedClass, mode, sourceClassName);
|
|
693
|
+
if (nativeValueNamespaceUtilities.length) return nativeValueNamespaceUtilities[0];
|
|
694
|
+
const nativeUtilities = this.createNativeDeclarationFallback(className, fixedClass, mode, sourceClassName);
|
|
695
|
+
if (nativeUtilities.length) return nativeUtilities[0];
|
|
696
|
+
}
|
|
697
|
+
if (registeredUtility) return this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode);
|
|
698
|
+
return this.createNativeValueNamespaceFallback(className, fixedClass, mode, sourceClassName)[0] || this.createNativeDeclarationFallback(className, fixedClass, mode, sourceClassName)[0];
|
|
699
|
+
}
|
|
700
|
+
createRules(className, fixedClass, mode) {
|
|
701
|
+
const groupUtilities = this.createAllGroupUtilities(className, fixedClass, mode);
|
|
702
|
+
if (groupUtilities.length) return groupUtilities;
|
|
703
|
+
const sourceClassName = className;
|
|
704
|
+
if (this.hasClassKey(className)) {
|
|
705
|
+
const rawRegisteredUtilities = this.matchAllRawManagedClassName(className);
|
|
706
|
+
const rawUtilities = [];
|
|
707
|
+
for (const registeredUtility of rawRegisteredUtilities){
|
|
708
|
+
const utility = this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode);
|
|
709
|
+
if (utility && utility.valid) {
|
|
710
|
+
rawUtilities.push(utility);
|
|
711
|
+
for(let branchIndex = 1; branchIndex < utility.branchCount; branchIndex++){
|
|
712
|
+
const branchUtility = this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode, branchIndex);
|
|
713
|
+
if (branchUtility?.valid) rawUtilities.push(branchUtility);
|
|
714
|
+
}
|
|
715
|
+
}
|
|
716
|
+
}
|
|
717
|
+
if (rawUtilities.length) return rawUtilities;
|
|
718
|
+
}
|
|
719
|
+
const canonicalClass = this.canonicalizeClassName(className, fixedClass);
|
|
720
|
+
className = canonicalClass.className;
|
|
721
|
+
fixedClass = canonicalClass.fixedClass;
|
|
722
|
+
const fastPathNativeValueNamespaceUtilities = this.createNativeValueNamespaceFastPath(className, fixedClass, mode, sourceClassName);
|
|
723
|
+
if (fastPathNativeValueNamespaceUtilities.length) return fastPathNativeValueNamespaceUtilities;
|
|
724
|
+
const fastPathNativeUtilities = this.createNativeDeclarationFastPath(className, fixedClass, mode, sourceClassName);
|
|
725
|
+
if (fastPathNativeUtilities.length) return fastPathNativeUtilities;
|
|
726
|
+
const registeredUtilities = this.matchAllResolvedClassName(className);
|
|
727
|
+
if (registeredUtilities.length && registeredUtilities.every((utility)=>this.matchesExactUtilityDefinition(className, utility))) {
|
|
728
|
+
const nativeValueNamespaceUtilities = this.createNativeValueNamespaceFallback(className, fixedClass, mode, sourceClassName);
|
|
729
|
+
if (nativeValueNamespaceUtilities.length) return nativeValueNamespaceUtilities;
|
|
730
|
+
const nativeUtilities = this.createNativeDeclarationFallback(className, fixedClass, mode, sourceClassName);
|
|
731
|
+
if (nativeUtilities.length) return nativeUtilities;
|
|
732
|
+
}
|
|
733
|
+
const utilities = [];
|
|
734
|
+
for (const registeredUtility of registeredUtilities){
|
|
735
|
+
const utility = this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode);
|
|
736
|
+
if (utility && utility.valid) {
|
|
737
|
+
utilities.push(utility);
|
|
738
|
+
for(let branchIndex = 1; branchIndex < utility.branchCount; branchIndex++){
|
|
739
|
+
const branchUtility = this.createRuleWithDefinition(sourceClassName, registeredUtility, fixedClass, mode, branchIndex);
|
|
740
|
+
if (branchUtility?.valid) utilities.push(branchUtility);
|
|
741
|
+
}
|
|
742
|
+
}
|
|
743
|
+
}
|
|
744
|
+
if (utilities.length) return utilities;
|
|
745
|
+
const nativeValueNamespaceUtilities = this.createNativeValueNamespaceFallback(className, fixedClass, mode, sourceClassName);
|
|
746
|
+
return nativeValueNamespaceUtilities.length ? nativeValueNamespaceUtilities : this.createNativeDeclarationFallback(className, fixedClass, mode, sourceClassName);
|
|
747
|
+
}
|
|
748
|
+
createRuleWithDefinition(className, registeredUtility, fixedClass, mode, branchIndex = 0) {
|
|
749
|
+
const candidate = new Utility(className, this, registeredUtility, fixedClass, mode, branchIndex);
|
|
750
|
+
if (candidate.valid && this.shouldValidateNativeDeclarationUtility(registeredUtility) && !this.isNativeDeclarationUtility(candidate)) return;
|
|
751
|
+
for (const layer of this.getUtilityLayers()){
|
|
752
|
+
const rule = layer.get(candidate.key);
|
|
753
|
+
const utility = rule instanceof Utility && rule.registeredUtility === registeredUtility ? rule : undefined;
|
|
754
|
+
if (utility) return utility;
|
|
755
|
+
}
|
|
756
|
+
return candidate;
|
|
757
|
+
}
|
|
758
|
+
/**
|
|
759
|
+
* Create utility from given selector text
|
|
760
|
+
* @param selectorText
|
|
761
|
+
*/ createRulesFromSelectorText(selectorText, layerName) {
|
|
762
|
+
const selectorTextSplits = selectorText.split(' ');
|
|
763
|
+
const stopChars = /[.#\[!\*>+~:,\s]/;
|
|
764
|
+
for(let i = 0; i < selectorTextSplits.length; i++){
|
|
765
|
+
const eachField = selectorTextSplits[i];
|
|
766
|
+
const modeSelector = this.getModeSelector(eachField);
|
|
767
|
+
if (i === 0 && eachField === modeSelector || (i === 0 || i === 1) && eachField === this.settings.scope) continue;
|
|
768
|
+
if (eachField.startsWith('.')) {
|
|
769
|
+
const eachFieldName = eachField.slice(1);
|
|
770
|
+
let className = '';
|
|
771
|
+
let l = 0;
|
|
772
|
+
while(l < eachFieldName.length){
|
|
773
|
+
const char = eachFieldName[l];
|
|
774
|
+
const nextChar = eachFieldName[l + 1];
|
|
775
|
+
if (char === '\\' && nextChar) {
|
|
776
|
+
className += nextChar;
|
|
777
|
+
l += 2;
|
|
778
|
+
continue;
|
|
779
|
+
}
|
|
780
|
+
if (stopChars.test(char)) break;
|
|
781
|
+
className += char;
|
|
782
|
+
l++;
|
|
783
|
+
}
|
|
784
|
+
const utilities = this.generate(className).filter((utility)=>!layerName || utility.layerName === layerName);
|
|
785
|
+
if (utilities.length) return utilities;
|
|
786
|
+
}
|
|
787
|
+
}
|
|
788
|
+
}
|
|
789
|
+
/**
|
|
790
|
+
* 根據蒐集到的所有 DOM class 重新 create
|
|
791
|
+
*/ refresh(manifest = this.manifest) {
|
|
792
|
+
this.reset();
|
|
793
|
+
this.loadManifest(manifest);
|
|
794
|
+
this.applyEmittedGlobalsCounts(this.emittedGlobals);
|
|
795
|
+
this.insertStaticResources();
|
|
796
|
+
return this;
|
|
797
|
+
}
|
|
798
|
+
reset() {
|
|
799
|
+
this.classUtilities.clear();
|
|
800
|
+
this.staticVariableTokens.clear();
|
|
801
|
+
this.staticAnimationTokens.clear();
|
|
802
|
+
this.baseLayer.reset();
|
|
803
|
+
this.themeLayer.reset();
|
|
804
|
+
this.defaultsLayer.reset();
|
|
805
|
+
this.componentsLayer.reset();
|
|
806
|
+
this.utilitiesLayer.reset();
|
|
807
|
+
this.animationsNonLayer.reset();
|
|
808
|
+
return this;
|
|
809
|
+
}
|
|
810
|
+
destroy() {
|
|
811
|
+
this.reset();
|
|
812
|
+
return this;
|
|
813
|
+
}
|
|
814
|
+
add(...classNames) {
|
|
815
|
+
for (const className of classNames){
|
|
816
|
+
const rules = this.classUtilities.get(className);
|
|
817
|
+
if (rules) continue;
|
|
818
|
+
const newRules = this.generate(className);
|
|
819
|
+
if (newRules.length) {
|
|
820
|
+
newRules.forEach((eachUtility)=>eachUtility.layer.insert(eachUtility));
|
|
821
|
+
this.classUtilities.set(className, newRules);
|
|
822
|
+
}
|
|
823
|
+
}
|
|
824
|
+
return this;
|
|
825
|
+
}
|
|
826
|
+
remove(...classNames) {
|
|
827
|
+
/**
|
|
828
|
+
* class name 從 DOM tree 中被移除,
|
|
829
|
+
* 匹配並刪除對應的 rule
|
|
830
|
+
*/ for (const className of classNames){
|
|
831
|
+
const rules = this.classUtilities.get(className);
|
|
832
|
+
if (rules) {
|
|
833
|
+
rules.forEach((rule)=>rule.layer.delete(rule.key));
|
|
834
|
+
this.classUtilities.delete(className);
|
|
835
|
+
}
|
|
836
|
+
}
|
|
837
|
+
}
|
|
838
|
+
getModeSelector(modeName) {
|
|
839
|
+
switch(this.settings.modeTrigger){
|
|
840
|
+
case 'class':
|
|
841
|
+
return '.' + modeName;
|
|
842
|
+
case 'host':
|
|
843
|
+
return ':host(.' + modeName + ')';
|
|
844
|
+
}
|
|
845
|
+
}
|
|
846
|
+
}
|
|
847
|
+
|
|
848
|
+
export { MasterCSS as default };
|