@tbela99/css-parser 0.3.0 → 0.4.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/{LICENSE → LICENSE.md} +1 -1
- package/README.md +191 -80
- package/dist/config.json.js +20 -1
- package/dist/index-umd-web.js +3210 -1352
- package/dist/index.cjs +3211 -1353
- package/dist/index.d.ts +910 -0
- package/dist/lib/ast/expand.js +1 -1
- package/dist/lib/ast/features/calc.js +1 -2
- package/dist/lib/ast/features/inlinecssvariables.js +1 -1
- package/dist/lib/ast/features/shorthand.js +1 -1
- package/dist/lib/ast/math/expression.js +38 -3
- package/dist/lib/ast/math/math.js +2 -2
- package/dist/lib/ast/minify.js +0 -1
- package/dist/lib/ast/types.js +1 -0
- package/dist/lib/ast/utils/minifyfeature.js +4 -3
- package/dist/lib/parser/declaration/list.js +1 -1
- package/dist/lib/parser/declaration/map.js +129 -26
- package/dist/lib/parser/declaration/set.js +1 -1
- package/dist/lib/parser/parse.js +325 -303
- package/dist/lib/parser/tokenize.js +220 -223
- package/dist/lib/parser/utils/declaration.js +1 -1
- package/dist/lib/parser/utils/syntax.js +159 -23
- package/dist/lib/parser/utils/type.js +2 -2
- package/dist/lib/renderer/color/a98rgb.js +64 -0
- package/dist/lib/renderer/color/color.js +521 -0
- package/dist/lib/renderer/color/colormix.js +337 -0
- package/dist/lib/renderer/color/hex.js +92 -0
- package/dist/lib/renderer/color/hsl.js +118 -0
- package/dist/lib/renderer/color/hsv.js +20 -0
- package/dist/lib/renderer/color/hwb.js +101 -0
- package/dist/lib/renderer/color/lab.js +136 -0
- package/dist/lib/renderer/color/lch.js +79 -0
- package/dist/lib/renderer/color/oklab.js +121 -0
- package/dist/lib/renderer/color/oklch.js +65 -0
- package/dist/lib/renderer/color/p3.js +57 -0
- package/dist/lib/renderer/color/prophotorgb.js +56 -0
- package/dist/lib/renderer/color/rec2020.js +70 -0
- package/dist/lib/renderer/color/relativecolor.js +152 -0
- package/dist/lib/renderer/color/rgb.js +44 -0
- package/dist/lib/renderer/color/srgb.js +261 -0
- package/dist/lib/renderer/color/utils/components.js +20 -0
- package/dist/lib/renderer/color/utils/constants.js +191 -0
- package/dist/lib/renderer/color/utils/matrix.js +35 -0
- package/dist/lib/renderer/color/xyz.js +64 -0
- package/dist/lib/renderer/color/xyzd50.js +33 -0
- package/dist/lib/renderer/render.js +61 -32
- package/dist/node/index.js +1 -1
- package/dist/node/load.js +1 -1
- package/dist/web/index.js +1 -1
- package/package.json +15 -14
- package/quickjs.sh +1 -0
- package/dist/lib/ast/features/utils/math.js +0 -95
- package/dist/lib/iterable/set.js +0 -48
- package/dist/lib/iterable/weakmap.js +0 -53
- package/dist/lib/renderer/utils/calccolor.js +0 -238
- package/dist/lib/renderer/utils/color.js +0 -371
- package/dist/lib/renderer/utils/hex.js +0 -124
- package/dist/lib/renderer/utils/hsl.js +0 -49
- package/dist/lib/renderer/utils/hsv.js +0 -15
- package/dist/lib/renderer/utils/hwb.js +0 -50
- package/dist/lib/renderer/utils/rgb.js +0 -66
package/dist/lib/ast/expand.js
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { splitRule, combinators } from './minify.js';
|
|
2
2
|
import { parseString } from '../parser/parse.js';
|
|
3
3
|
import { renderToken } from '../renderer/render.js';
|
|
4
|
-
import '../renderer/utils/color.js';
|
|
5
4
|
import { EnumToken } from './types.js';
|
|
6
5
|
import { walkValues } from './walk.js';
|
|
6
|
+
import '../renderer/color/utils/constants.js';
|
|
7
7
|
|
|
8
8
|
function expand(ast) {
|
|
9
9
|
//
|
|
@@ -21,7 +21,7 @@ class ComputeCalcExpressionFeature extends MinifyFeature {
|
|
|
21
21
|
}
|
|
22
22
|
run(ast) {
|
|
23
23
|
if (!('chi' in ast)) {
|
|
24
|
-
return
|
|
24
|
+
return;
|
|
25
25
|
}
|
|
26
26
|
// @ts-ignore
|
|
27
27
|
for (const node of ast.chi) {
|
|
@@ -58,7 +58,6 @@ class ComputeCalcExpressionFeature extends MinifyFeature {
|
|
|
58
58
|
}
|
|
59
59
|
}
|
|
60
60
|
}
|
|
61
|
-
return ast;
|
|
62
61
|
}
|
|
63
62
|
}
|
|
64
63
|
|
|
@@ -45,7 +45,7 @@ class InlineCssVariablesFeature extends MinifyFeature {
|
|
|
45
45
|
if (!('variableScope' in context)) {
|
|
46
46
|
context.variableScope = new Map;
|
|
47
47
|
}
|
|
48
|
-
const isRoot = parent.typ == EnumToken.StyleSheetNodeType && ast.typ == EnumToken.RuleNodeType &&
|
|
48
|
+
const isRoot = parent.typ == EnumToken.StyleSheetNodeType && ast.typ == EnumToken.RuleNodeType && [':root', 'html'].includes(ast.sel);
|
|
49
49
|
const variableScope = context.variableScope;
|
|
50
50
|
// @ts-ignore
|
|
51
51
|
for (const node of ast.chi) {
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { PropertyList } from '../../parser/declaration/list.js';
|
|
2
|
-
import '../../renderer/utils/color.js';
|
|
3
2
|
import { EnumToken } from '../types.js';
|
|
4
3
|
import '../minify.js';
|
|
5
4
|
import '../../parser/parse.js';
|
|
5
|
+
import '../../renderer/color/utils/constants.js';
|
|
6
6
|
import '../../renderer/sourcemap/lib/encode.js';
|
|
7
7
|
import { MinifyFeature } from '../utils/minifyfeature.js';
|
|
8
8
|
|
|
@@ -72,10 +72,41 @@ function doEvaluate(l, r, op) {
|
|
|
72
72
|
return defaultReturn;
|
|
73
73
|
}
|
|
74
74
|
}
|
|
75
|
-
|
|
75
|
+
else if (op == EnumToken.Mul &&
|
|
76
|
+
![EnumToken.NumberTokenType, EnumToken.PercentageTokenType].includes(l.typ) &&
|
|
77
|
+
![EnumToken.NumberTokenType, EnumToken.PercentageTokenType].includes(r.typ)) {
|
|
78
|
+
return defaultReturn;
|
|
79
|
+
}
|
|
80
|
+
const typ = l.typ == EnumToken.NumberTokenType ? r.typ : (r.typ == EnumToken.NumberTokenType ? l.typ : (l.typ == EnumToken.PercentageTokenType ? r.typ : l.typ));
|
|
81
|
+
// @ts-ignore
|
|
82
|
+
let v1 = typeof l.val == 'string' ? +l.val : l.val;
|
|
76
83
|
// @ts-ignore
|
|
77
|
-
|
|
78
|
-
|
|
84
|
+
let v2 = typeof r.val == 'string' ? +r.val : r.val;
|
|
85
|
+
if (op == EnumToken.Mul) {
|
|
86
|
+
if (l.typ != EnumToken.NumberTokenType && r.typ != EnumToken.NumberTokenType) {
|
|
87
|
+
if (typeof v1 == 'number' && l.typ == EnumToken.PercentageTokenType) {
|
|
88
|
+
v1 = {
|
|
89
|
+
typ: EnumToken.FractionTokenType,
|
|
90
|
+
l: { typ: EnumToken.NumberTokenType, val: String(v1) },
|
|
91
|
+
r: { typ: EnumToken.NumberTokenType, val: '100' }
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
else if (typeof v2 == 'number' && r.typ == EnumToken.PercentageTokenType) {
|
|
95
|
+
v2 = {
|
|
96
|
+
typ: EnumToken.FractionTokenType,
|
|
97
|
+
l: { typ: EnumToken.NumberTokenType, val: String(v2) },
|
|
98
|
+
r: { typ: EnumToken.NumberTokenType, val: '100' }
|
|
99
|
+
};
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
// @ts-ignore
|
|
104
|
+
const val = compute(v1, v2, op);
|
|
105
|
+
return {
|
|
106
|
+
...(l.typ == EnumToken.NumberTokenType ? r : l),
|
|
107
|
+
typ,
|
|
108
|
+
val: typeof val == 'number' ? reduceNumber(val) : val
|
|
109
|
+
};
|
|
79
110
|
}
|
|
80
111
|
/**
|
|
81
112
|
* convert BinaryExpression into an array
|
|
@@ -166,6 +197,10 @@ function factor(tokens, ops) {
|
|
|
166
197
|
return [factorToken(tokens[0])];
|
|
167
198
|
}
|
|
168
199
|
for (let i = 0; i < tokens.length; i++) {
|
|
200
|
+
if (tokens[i].typ == EnumToken.ListToken) {
|
|
201
|
+
// @ts-ignore
|
|
202
|
+
tokens.splice(i, 1, ...tokens[i].chi);
|
|
203
|
+
}
|
|
169
204
|
isOp = opList.includes(tokens[i].typ);
|
|
170
205
|
if (isOp ||
|
|
171
206
|
// @ts-ignore
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { EnumToken } from '../types.js';
|
|
2
2
|
import { reduceNumber } from '../../renderer/render.js';
|
|
3
3
|
|
|
4
|
-
|
|
4
|
+
function gcd(x, y) {
|
|
5
5
|
x = Math.abs(x);
|
|
6
6
|
y = Math.abs(y);
|
|
7
7
|
let t;
|
|
@@ -14,7 +14,7 @@ const gcd = (x, y) => {
|
|
|
14
14
|
x = t;
|
|
15
15
|
}
|
|
16
16
|
return x;
|
|
17
|
-
}
|
|
17
|
+
}
|
|
18
18
|
function compute(a, b, op) {
|
|
19
19
|
if (typeof a == 'number' && typeof b == 'number') {
|
|
20
20
|
switch (op) {
|
package/dist/lib/ast/minify.js
CHANGED
package/dist/lib/ast/types.js
CHANGED
|
@@ -78,6 +78,7 @@ var EnumToken;
|
|
|
78
78
|
/* aliases */
|
|
79
79
|
EnumToken[EnumToken["Time"] = 25] = "Time";
|
|
80
80
|
EnumToken[EnumToken["Iden"] = 7] = "Iden";
|
|
81
|
+
EnumToken[EnumToken["EOF"] = 47] = "EOF";
|
|
81
82
|
EnumToken[EnumToken["Hash"] = 28] = "Hash";
|
|
82
83
|
EnumToken[EnumToken["Flex"] = 57] = "Flex";
|
|
83
84
|
EnumToken[EnumToken["Angle"] = 24] = "Angle";
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { PropertySet } from './set.js';
|
|
2
|
-
import '../../renderer/utils/color.js';
|
|
3
2
|
import { EnumToken } from '../../ast/types.js';
|
|
4
3
|
import '../../ast/minify.js';
|
|
5
4
|
import { parseString } from '../parse.js';
|
|
5
|
+
import '../../renderer/color/utils/constants.js';
|
|
6
6
|
import '../../renderer/sourcemap/lib/encode.js';
|
|
7
7
|
import { getConfig } from '../utils/config.js';
|
|
8
8
|
import { PropertyMap } from './map.js';
|
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { eq } from '../utils/eq.js';
|
|
2
2
|
import { renderToken } from '../../renderer/render.js';
|
|
3
|
-
import '../../renderer/utils/color.js';
|
|
4
3
|
import { EnumToken } from '../../ast/types.js';
|
|
5
4
|
import '../../ast/minify.js';
|
|
6
5
|
import { parseString } from '../parse.js';
|
|
6
|
+
import '../../renderer/color/utils/constants.js';
|
|
7
7
|
import { getConfig } from '../utils/config.js';
|
|
8
8
|
import { matchType } from '../utils/type.js';
|
|
9
9
|
import { PropertySet } from './set.js';
|
|
@@ -22,12 +22,10 @@ class PropertyMap {
|
|
|
22
22
|
this.pattern = config.pattern.split(/\s/);
|
|
23
23
|
}
|
|
24
24
|
add(declaration) {
|
|
25
|
-
for (const val of declaration.val) {
|
|
26
|
-
Object.defineProperty(val, 'propertyName', { enumerable: false, writable: true, value: declaration.nam });
|
|
27
|
-
}
|
|
28
25
|
if (declaration.nam == this.config.shorthand) {
|
|
29
26
|
this.declarations = new Map;
|
|
30
27
|
this.declarations.set(declaration.nam, declaration);
|
|
28
|
+
this.matchTypes(declaration);
|
|
31
29
|
}
|
|
32
30
|
else {
|
|
33
31
|
const separator = this.config.separator != null ? {
|
|
@@ -165,6 +163,55 @@ class PropertyMap {
|
|
|
165
163
|
}
|
|
166
164
|
return this;
|
|
167
165
|
}
|
|
166
|
+
matchTypes(declaration) {
|
|
167
|
+
const patterns = this.pattern.slice();
|
|
168
|
+
const values = [...declaration.val];
|
|
169
|
+
let i;
|
|
170
|
+
let j;
|
|
171
|
+
const map = new Map;
|
|
172
|
+
for (i = 0; i < patterns.length; i++) {
|
|
173
|
+
for (j = 0; j < values.length; j++) {
|
|
174
|
+
if (!map.has(patterns[i])) {
|
|
175
|
+
// @ts-ignore
|
|
176
|
+
map.set(patterns[i], this.config.properties?.[patterns[i]]?.constraints?.mapping?.max ?? 1);
|
|
177
|
+
}
|
|
178
|
+
let count = map.get(patterns[i]);
|
|
179
|
+
if (count > 0 && matchType(values[j], this.config.properties[patterns[i]])) {
|
|
180
|
+
Object.defineProperty(values[j], 'propertyName', {
|
|
181
|
+
enumerable: false,
|
|
182
|
+
writable: true,
|
|
183
|
+
value: patterns[i]
|
|
184
|
+
});
|
|
185
|
+
map.set(patterns[i], --count);
|
|
186
|
+
values.splice(j--, 1);
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
if (this.config.set != null) {
|
|
191
|
+
for (const [key, val] of Object.entries(this.config.set)) {
|
|
192
|
+
if (map.has(key)) {
|
|
193
|
+
for (const v of val) {
|
|
194
|
+
// missing
|
|
195
|
+
if (map.get(v) == 1) {
|
|
196
|
+
let i = declaration.val.length;
|
|
197
|
+
while (i--) {
|
|
198
|
+
// @ts-ignore
|
|
199
|
+
if (declaration.val[i].propertyName == key) {
|
|
200
|
+
const val = { ...declaration.val[i] };
|
|
201
|
+
Object.defineProperty(val, 'propertyName', {
|
|
202
|
+
enumerable: false,
|
|
203
|
+
writable: true,
|
|
204
|
+
value: v
|
|
205
|
+
});
|
|
206
|
+
declaration.val.splice(i, 0, val, { typ: EnumToken.WhitespaceTokenType });
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
}
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
}
|
|
214
|
+
}
|
|
168
215
|
[Symbol.iterator]() {
|
|
169
216
|
let iterable;
|
|
170
217
|
let requiredCount = 0;
|
|
@@ -195,34 +242,60 @@ class PropertyMap {
|
|
|
195
242
|
if (isShorthand && this.declarations.has(this.config.shorthand)) {
|
|
196
243
|
const cache = new Map();
|
|
197
244
|
const removeDefaults = (declaration) => {
|
|
198
|
-
let
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
245
|
+
let i;
|
|
246
|
+
let t;
|
|
247
|
+
let map = new Map();
|
|
248
|
+
let value = [];
|
|
249
|
+
let values = [];
|
|
250
|
+
// @ts-ignore
|
|
251
|
+
let typ = (EnumToken[this.config.separator?.typ] ?? EnumToken.CommaTokenType);
|
|
252
|
+
let separator = this.config.separator ? renderToken(this.config.separator) : ',';
|
|
253
|
+
this.matchTypes(declaration);
|
|
254
|
+
values.push(value);
|
|
255
|
+
for (i = 0; i < declaration.val.length; i++) {
|
|
256
|
+
t = declaration.val[i];
|
|
206
257
|
if (!cache.has(t)) {
|
|
207
258
|
cache.set(t, renderToken(t, { minify: true }));
|
|
208
259
|
}
|
|
209
|
-
|
|
260
|
+
if (t.typ == typ && separator == cache.get(t)) {
|
|
261
|
+
this.removeDefaults(map, value);
|
|
262
|
+
value = [];
|
|
263
|
+
values.push(value);
|
|
264
|
+
map.clear();
|
|
265
|
+
continue;
|
|
266
|
+
}
|
|
267
|
+
value.push(t);
|
|
210
268
|
// @ts-ignore
|
|
211
|
-
if (
|
|
269
|
+
if ('propertyName' in t) {
|
|
212
270
|
// @ts-ignore
|
|
213
|
-
|
|
214
|
-
|
|
271
|
+
if (!map.has(t.propertyName)) {
|
|
272
|
+
// @ts-ignore
|
|
273
|
+
map.set(t.propertyName, { t: [t], value: [cache.get(t)] });
|
|
274
|
+
}
|
|
275
|
+
else {
|
|
276
|
+
// @ts-ignore
|
|
277
|
+
const v = map.get(t.propertyName);
|
|
278
|
+
v.t.push(t);
|
|
279
|
+
v.value.push(cache.get(t));
|
|
280
|
+
}
|
|
281
|
+
}
|
|
282
|
+
}
|
|
283
|
+
this.removeDefaults(map, value);
|
|
284
|
+
declaration.val = values.reduce((acc, curr) => {
|
|
285
|
+
for (const cr of curr) {
|
|
286
|
+
if (cr.typ == EnumToken.WhitespaceTokenType && acc.at(-1)?.typ == cr.typ) {
|
|
287
|
+
continue;
|
|
288
|
+
}
|
|
289
|
+
acc.push(cr);
|
|
215
290
|
}
|
|
216
|
-
return
|
|
217
|
-
})
|
|
218
|
-
|
|
219
|
-
})
|
|
220
|
-
.filter((val, index, array) => !(index > 0 &&
|
|
221
|
-
val.typ == EnumToken.WhitespaceTokenType &&
|
|
222
|
-
array[index - 1].typ == EnumToken.WhitespaceTokenType));
|
|
223
|
-
if (declaration.val.at(-1)?.typ == EnumToken.WhitespaceTokenType) {
|
|
291
|
+
return acc;
|
|
292
|
+
}, []);
|
|
293
|
+
while (declaration.val.at(-1)?.typ == EnumToken.WhitespaceTokenType) {
|
|
224
294
|
declaration.val.pop();
|
|
225
295
|
}
|
|
296
|
+
while (declaration.val.at(0)?.typ == EnumToken.WhitespaceTokenType) {
|
|
297
|
+
declaration.val.shift();
|
|
298
|
+
}
|
|
226
299
|
return declaration;
|
|
227
300
|
};
|
|
228
301
|
const values = [...this.declarations.values()].reduce((acc, curr) => {
|
|
@@ -322,12 +395,12 @@ class PropertyMap {
|
|
|
322
395
|
return acc;
|
|
323
396
|
}, []);
|
|
324
397
|
count++;
|
|
325
|
-
if (!isShorthand || Object.entries(this.config.properties).some(entry => {
|
|
398
|
+
if (!isShorthand || Object.entries(this.config.properties).some((entry) => {
|
|
326
399
|
// missing required property
|
|
327
400
|
return entry[1].required && !(entry[0] in tokens);
|
|
328
401
|
}) ||
|
|
329
402
|
// @ts-ignore
|
|
330
|
-
!Object.values(tokens).every(v => v.filter(t => t.typ != EnumToken.CommentTokenType).length == count)) {
|
|
403
|
+
!Object.values(tokens).every((v) => v.filter((t) => t.typ != EnumToken.CommentTokenType).length == count)) {
|
|
331
404
|
// @ts-ignore
|
|
332
405
|
iterable = this.declarations.values();
|
|
333
406
|
}
|
|
@@ -482,6 +555,36 @@ class PropertyMap {
|
|
|
482
555
|
}
|
|
483
556
|
};
|
|
484
557
|
}
|
|
558
|
+
removeDefaults(map, value) {
|
|
559
|
+
for (const [key, val] of map) {
|
|
560
|
+
const config = this.config.properties[key];
|
|
561
|
+
if (config == null) {
|
|
562
|
+
continue;
|
|
563
|
+
}
|
|
564
|
+
const v = val.value.join(' ');
|
|
565
|
+
if (config.default.includes(v) || (value.length == 1 && this.config.default.includes(v))) {
|
|
566
|
+
for (const token of value) {
|
|
567
|
+
if (val.t.includes(token)) {
|
|
568
|
+
let index = value.indexOf(token);
|
|
569
|
+
value.splice(index, 1);
|
|
570
|
+
if (config.prefix != null) {
|
|
571
|
+
while (index-- > 0) {
|
|
572
|
+
if (value[index].typ == EnumToken.WhitespaceTokenType) {
|
|
573
|
+
continue;
|
|
574
|
+
}
|
|
575
|
+
if (value[index].typ == EnumToken[config.prefix.typ] &&
|
|
576
|
+
// @ts-ignore
|
|
577
|
+
value[index].val == config.prefix.val) {
|
|
578
|
+
value.splice(index, 1);
|
|
579
|
+
break;
|
|
580
|
+
}
|
|
581
|
+
}
|
|
582
|
+
}
|
|
583
|
+
}
|
|
584
|
+
}
|
|
585
|
+
}
|
|
586
|
+
}
|
|
587
|
+
}
|
|
485
588
|
}
|
|
486
589
|
|
|
487
590
|
export { PropertyMap };
|
|
@@ -3,7 +3,7 @@ import { isLength } from '../utils/syntax.js';
|
|
|
3
3
|
import { EnumToken } from '../../ast/types.js';
|
|
4
4
|
import '../../ast/minify.js';
|
|
5
5
|
import '../parse.js';
|
|
6
|
-
import '../../renderer/utils/
|
|
6
|
+
import '../../renderer/color/utils/constants.js';
|
|
7
7
|
import '../../renderer/sourcemap/lib/encode.js';
|
|
8
8
|
|
|
9
9
|
function dedup(values) {
|