@nativescript/core 8.8.0-alpha.2 → 8.8.0-next-06-28-2024-9718658121
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/css/parser.d.ts +0 -38
- package/css/parser.js +0 -108
- package/css/parser.js.map +1 -1
- package/css/system-classes.d.ts +0 -1
- package/css/system-classes.js +0 -1
- package/css/system-classes.js.map +1 -1
- package/package.json +2 -1
- package/ui/action-bar/index.ios.js +1 -1
- package/ui/action-bar/index.ios.js.map +1 -1
- package/ui/core/view-base/index.d.ts +7 -0
- package/ui/core/view-base/index.js +11 -2
- package/ui/core/view-base/index.js.map +1 -1
- package/ui/image/image-common.d.ts +3 -11
- package/ui/image/image-common.js +5 -3
- package/ui/image/image-common.js.map +1 -1
- package/ui/image/index.d.ts +1 -1
- package/ui/image/index.ios.js +12 -9
- package/ui/image/index.ios.js.map +1 -1
- package/ui/image/symbol-effects-common.d.ts +36 -0
- package/ui/image/symbol-effects-common.js +35 -0
- package/ui/image/symbol-effects-common.js.map +1 -0
- package/ui/image/symbol-effects.android.d.ts +4 -0
- package/ui/image/symbol-effects.android.js +8 -0
- package/ui/image/symbol-effects.android.js.map +1 -0
- package/ui/image/symbol-effects.d.ts +13 -0
- package/ui/image/symbol-effects.ios.d.ts +2 -0
- package/ui/image/symbol-effects.ios.js +93 -0
- package/ui/image/symbol-effects.ios.js.map +1 -0
- package/ui/index.d.ts +1 -1
- package/ui/index.js +1 -1
- package/ui/index.js.map +1 -1
- package/ui/styling/css-selector.d.ts +63 -23
- package/ui/styling/css-selector.js +372 -114
- package/ui/styling/css-selector.js.map +1 -1
- package/ui/styling/style-properties.js +1 -1
- package/ui/styling/style-properties.js.map +1 -1
- package/ui/styling/style-scope.js +7 -13
- package/ui/styling/style-scope.js.map +1 -1
|
@@ -1,8 +1,27 @@
|
|
|
1
|
+
import { parse as convertToCSSWhatSelector } from 'css-what';
|
|
1
2
|
import '../../globals';
|
|
2
3
|
import { isCssVariable } from '../core/properties';
|
|
3
4
|
import { isNullOrUndefined } from '../../utils/types';
|
|
4
|
-
|
|
5
|
-
|
|
5
|
+
var Combinator;
|
|
6
|
+
(function (Combinator) {
|
|
7
|
+
Combinator["descendant"] = " ";
|
|
8
|
+
Combinator["child"] = ">";
|
|
9
|
+
Combinator["adjacent"] = "+";
|
|
10
|
+
Combinator["sibling"] = "~";
|
|
11
|
+
// Not supported
|
|
12
|
+
Combinator["parent"] = "<";
|
|
13
|
+
Combinator["column-combinator"] = "||";
|
|
14
|
+
})(Combinator || (Combinator = {}));
|
|
15
|
+
var AttributeSelectorOperator;
|
|
16
|
+
(function (AttributeSelectorOperator) {
|
|
17
|
+
AttributeSelectorOperator["exists"] = "";
|
|
18
|
+
AttributeSelectorOperator["equals"] = "=";
|
|
19
|
+
AttributeSelectorOperator["start"] = "^=";
|
|
20
|
+
AttributeSelectorOperator["end"] = "$=";
|
|
21
|
+
AttributeSelectorOperator["any"] = "*=";
|
|
22
|
+
AttributeSelectorOperator["element"] = "~=";
|
|
23
|
+
AttributeSelectorOperator["hyphen"] = "|=";
|
|
24
|
+
})(AttributeSelectorOperator || (AttributeSelectorOperator = {}));
|
|
6
25
|
var Match;
|
|
7
26
|
(function (Match) {
|
|
8
27
|
/**
|
|
@@ -14,7 +33,22 @@ var Match;
|
|
|
14
33
|
*/
|
|
15
34
|
Match.Static = false;
|
|
16
35
|
})(Match || (Match = {}));
|
|
17
|
-
function
|
|
36
|
+
function eachNodePreviousGeneralSibling(node, callback) {
|
|
37
|
+
if (!node.parent || !node.parent.getChildIndex || !node.parent.getChildAt || !node.parent.getChildrenCount) {
|
|
38
|
+
return;
|
|
39
|
+
}
|
|
40
|
+
const nodeIndex = node.parent.getChildIndex(node);
|
|
41
|
+
if (nodeIndex === 0) {
|
|
42
|
+
return;
|
|
43
|
+
}
|
|
44
|
+
const count = node.parent.getChildrenCount();
|
|
45
|
+
let retVal = true;
|
|
46
|
+
for (let i = nodeIndex - 1; i >= 0 && retVal; i--) {
|
|
47
|
+
const sibling = node.parent.getChildAt(i);
|
|
48
|
+
retVal = callback(sibling);
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
function getNodePreviousDirectSibling(node) {
|
|
18
52
|
if (!node.parent || !node.parent.getChildIndex || !node.parent.getChildAt) {
|
|
19
53
|
return null;
|
|
20
54
|
}
|
|
@@ -33,7 +67,19 @@ function SelectorProperties(specificity, rarity, dynamic = false) {
|
|
|
33
67
|
return cls;
|
|
34
68
|
};
|
|
35
69
|
}
|
|
36
|
-
|
|
70
|
+
function FunctionalPseudoClassProperties(specificity, rarity, pseudoSelectorListType) {
|
|
71
|
+
return (cls) => {
|
|
72
|
+
cls.prototype.specificity = specificity;
|
|
73
|
+
cls.prototype.rarity = rarity;
|
|
74
|
+
cls.prototype.combinator = undefined;
|
|
75
|
+
cls.prototype.dynamic = false;
|
|
76
|
+
cls.prototype.pseudoSelectorListType = pseudoSelectorListType;
|
|
77
|
+
return cls;
|
|
78
|
+
};
|
|
79
|
+
}
|
|
80
|
+
export class SelectorBase {
|
|
81
|
+
}
|
|
82
|
+
let SelectorCore = class SelectorCore extends SelectorBase {
|
|
37
83
|
lookupSort(sorter, base) {
|
|
38
84
|
sorter.sortAsUniversal(base || this);
|
|
39
85
|
}
|
|
@@ -70,7 +116,7 @@ let InvalidSelector = class InvalidSelector extends SimpleSelector {
|
|
|
70
116
|
this.e = e;
|
|
71
117
|
}
|
|
72
118
|
toString() {
|
|
73
|
-
return
|
|
119
|
+
return `<${this.e}>`;
|
|
74
120
|
}
|
|
75
121
|
match(node) {
|
|
76
122
|
return false;
|
|
@@ -159,52 +205,55 @@ ClassSelector = __decorate([
|
|
|
159
205
|
], ClassSelector);
|
|
160
206
|
export { ClassSelector };
|
|
161
207
|
let AttributeSelector = class AttributeSelector extends SimpleSelector {
|
|
162
|
-
constructor(attribute, test, value) {
|
|
208
|
+
constructor(attribute, test, value, ignoreCase) {
|
|
163
209
|
super();
|
|
164
210
|
this.attribute = attribute;
|
|
165
211
|
this.test = test;
|
|
166
212
|
this.value = value;
|
|
167
|
-
|
|
168
|
-
// HasAttribute
|
|
169
|
-
this.match = (node) => !isNullOrUndefined(node[attribute]);
|
|
170
|
-
return;
|
|
171
|
-
}
|
|
172
|
-
if (!value) {
|
|
173
|
-
this.match = (node) => false;
|
|
174
|
-
}
|
|
175
|
-
this.match = (node) => {
|
|
176
|
-
const attr = node[attribute] + '';
|
|
177
|
-
if (test === '=') {
|
|
178
|
-
// Equals
|
|
179
|
-
return attr === value;
|
|
180
|
-
}
|
|
181
|
-
if (test === '^=') {
|
|
182
|
-
// PrefixMatch
|
|
183
|
-
return attr.startsWith(value);
|
|
184
|
-
}
|
|
185
|
-
if (test === '$=') {
|
|
186
|
-
// SuffixMatch
|
|
187
|
-
return attr.endsWith(value);
|
|
188
|
-
}
|
|
189
|
-
if (test === '*=') {
|
|
190
|
-
// SubstringMatch
|
|
191
|
-
return attr.indexOf(value) !== -1;
|
|
192
|
-
}
|
|
193
|
-
if (test === '~=') {
|
|
194
|
-
// Includes
|
|
195
|
-
const words = attr.split(' ');
|
|
196
|
-
return words && words.indexOf(value) !== -1;
|
|
197
|
-
}
|
|
198
|
-
if (test === '|=') {
|
|
199
|
-
// DashMatch
|
|
200
|
-
return attr === value || attr.startsWith(value + '-');
|
|
201
|
-
}
|
|
202
|
-
};
|
|
213
|
+
this.ignoreCase = ignoreCase;
|
|
203
214
|
}
|
|
204
215
|
toString() {
|
|
205
|
-
return `[${this.attribute}${wrap(this.test)}${
|
|
216
|
+
return `[${this.attribute}${wrap(AttributeSelectorOperator[this.test] ?? this.test)}${this.value || ''}]${wrap(this.combinator)}`;
|
|
206
217
|
}
|
|
207
218
|
match(node) {
|
|
219
|
+
let attr = node[this.attribute];
|
|
220
|
+
if (this.test === 'exists') {
|
|
221
|
+
return !isNullOrUndefined(attr);
|
|
222
|
+
}
|
|
223
|
+
if (!this.value) {
|
|
224
|
+
return false;
|
|
225
|
+
}
|
|
226
|
+
// Now, convert value to string
|
|
227
|
+
attr += '';
|
|
228
|
+
if (this.ignoreCase) {
|
|
229
|
+
attr = attr.toLowerCase();
|
|
230
|
+
this.value = this.value.toLowerCase();
|
|
231
|
+
}
|
|
232
|
+
// =
|
|
233
|
+
if (this.test === 'equals') {
|
|
234
|
+
return attr === this.value;
|
|
235
|
+
}
|
|
236
|
+
// ^=
|
|
237
|
+
if (this.test === 'start') {
|
|
238
|
+
return attr.startsWith(this.value);
|
|
239
|
+
}
|
|
240
|
+
// $=
|
|
241
|
+
if (this.test === 'end') {
|
|
242
|
+
return attr.endsWith(this.value);
|
|
243
|
+
}
|
|
244
|
+
// *=
|
|
245
|
+
if (this.test === 'any') {
|
|
246
|
+
return attr.indexOf(this.value) !== -1;
|
|
247
|
+
}
|
|
248
|
+
// ~=
|
|
249
|
+
if (this.test === 'element') {
|
|
250
|
+
const words = attr.split(' ');
|
|
251
|
+
return words && words.indexOf(this.value) !== -1;
|
|
252
|
+
}
|
|
253
|
+
// |=
|
|
254
|
+
if (this.test === 'hyphen') {
|
|
255
|
+
return attr === this.value || attr.startsWith(this.value + '-');
|
|
256
|
+
}
|
|
208
257
|
return false;
|
|
209
258
|
}
|
|
210
259
|
mayMatch(node) {
|
|
@@ -216,7 +265,7 @@ let AttributeSelector = class AttributeSelector extends SimpleSelector {
|
|
|
216
265
|
};
|
|
217
266
|
AttributeSelector = __decorate([
|
|
218
267
|
SelectorProperties(10 /* Specificity.Attribute */, 0 /* Rarity.Attribute */, Match.Dynamic),
|
|
219
|
-
__metadata("design:paramtypes", [String, String, String])
|
|
268
|
+
__metadata("design:paramtypes", [String, String, String, Boolean])
|
|
220
269
|
], AttributeSelector);
|
|
221
270
|
export { AttributeSelector };
|
|
222
271
|
let PseudoClassSelector = class PseudoClassSelector extends SimpleSelector {
|
|
@@ -242,12 +291,100 @@ PseudoClassSelector = __decorate([
|
|
|
242
291
|
__metadata("design:paramtypes", [String])
|
|
243
292
|
], PseudoClassSelector);
|
|
244
293
|
export { PseudoClassSelector };
|
|
294
|
+
export class FunctionalPseudoClassSelector extends PseudoClassSelector {
|
|
295
|
+
constructor(cssPseudoClass, dataType) {
|
|
296
|
+
super(cssPseudoClass);
|
|
297
|
+
const selectors = [];
|
|
298
|
+
const needsHighestSpecificity = this.specificity === -1 /* Specificity.SelectorListHighest */;
|
|
299
|
+
let specificity = 0;
|
|
300
|
+
if (Array.isArray(dataType)) {
|
|
301
|
+
for (const asts of dataType) {
|
|
302
|
+
const selector = createSelectorFromAst(asts);
|
|
303
|
+
if (selector instanceof InvalidSelector) {
|
|
304
|
+
// Only forgiving selector list can ignore invalid selectors
|
|
305
|
+
if (this.selectorListType !== 1 /* PseudoClassSelectorList.Forgiving */) {
|
|
306
|
+
selectors.splice(0);
|
|
307
|
+
specificity = 0;
|
|
308
|
+
break;
|
|
309
|
+
}
|
|
310
|
+
continue;
|
|
311
|
+
}
|
|
312
|
+
// The specificity of some pseudo-classes is replaced by the specificity of the most specific selector in its comma-separated argument of selectors
|
|
313
|
+
if (needsHighestSpecificity && selector.specificity > specificity) {
|
|
314
|
+
specificity = selector.specificity;
|
|
315
|
+
}
|
|
316
|
+
selectors.push(selector);
|
|
317
|
+
}
|
|
318
|
+
}
|
|
319
|
+
this.selectors = selectors;
|
|
320
|
+
this.specificity = specificity;
|
|
321
|
+
// Functional pseudo-classes become dynamic based on selectors in selector list
|
|
322
|
+
this.dynamic = this.selectors.some((sel) => sel.dynamic);
|
|
323
|
+
}
|
|
324
|
+
toString() {
|
|
325
|
+
return `:${this.cssPseudoClass}(${this.selectors.join(', ')})${wrap(this.combinator)}`;
|
|
326
|
+
}
|
|
327
|
+
match(node) {
|
|
328
|
+
return false;
|
|
329
|
+
}
|
|
330
|
+
mayMatch(node) {
|
|
331
|
+
return true;
|
|
332
|
+
}
|
|
333
|
+
trackChanges(node, map) {
|
|
334
|
+
this.selectors.forEach((sel) => sel.trackChanges(node, map));
|
|
335
|
+
}
|
|
336
|
+
}
|
|
337
|
+
let NotFunctionalPseudoClassSelector = class NotFunctionalPseudoClassSelector extends FunctionalPseudoClassSelector {
|
|
338
|
+
match(node) {
|
|
339
|
+
return !this.selectors.some((sel) => sel.match(node));
|
|
340
|
+
}
|
|
341
|
+
};
|
|
342
|
+
NotFunctionalPseudoClassSelector = __decorate([
|
|
343
|
+
FunctionalPseudoClassProperties(-1 /* Specificity.SelectorListHighest */, 0 /* Rarity.PseudoClass */, 0 /* PseudoClassSelectorList.Regular */)
|
|
344
|
+
], NotFunctionalPseudoClassSelector);
|
|
345
|
+
export { NotFunctionalPseudoClassSelector };
|
|
346
|
+
let IsFunctionalPseudoClassSelector = class IsFunctionalPseudoClassSelector extends FunctionalPseudoClassSelector {
|
|
347
|
+
match(node) {
|
|
348
|
+
return this.selectors.some((sel) => sel.match(node));
|
|
349
|
+
}
|
|
350
|
+
lookupSort(sorter, base) {
|
|
351
|
+
// A faster lookup can be performed when selector list contains just a single selector
|
|
352
|
+
if (this.selectors.length === 1) {
|
|
353
|
+
this.selectors[0].lookupSort(sorter, base || this);
|
|
354
|
+
}
|
|
355
|
+
else {
|
|
356
|
+
super.lookupSort(sorter, base || this);
|
|
357
|
+
}
|
|
358
|
+
}
|
|
359
|
+
};
|
|
360
|
+
IsFunctionalPseudoClassSelector = __decorate([
|
|
361
|
+
FunctionalPseudoClassProperties(-1 /* Specificity.SelectorListHighest */, 0 /* Rarity.PseudoClass */, 1 /* PseudoClassSelectorList.Forgiving */)
|
|
362
|
+
], IsFunctionalPseudoClassSelector);
|
|
363
|
+
export { IsFunctionalPseudoClassSelector };
|
|
364
|
+
let WhereFunctionalPseudoClassSelector = class WhereFunctionalPseudoClassSelector extends FunctionalPseudoClassSelector {
|
|
365
|
+
match(node) {
|
|
366
|
+
return this.selectors.some((sel) => sel.match(node));
|
|
367
|
+
}
|
|
368
|
+
lookupSort(sorter, base) {
|
|
369
|
+
// A faster lookup can be performed when selector list contains just a single selector
|
|
370
|
+
if (this.selectors.length === 1) {
|
|
371
|
+
this.selectors[0].lookupSort(sorter, base || this);
|
|
372
|
+
}
|
|
373
|
+
else {
|
|
374
|
+
super.lookupSort(sorter, base || this);
|
|
375
|
+
}
|
|
376
|
+
}
|
|
377
|
+
};
|
|
378
|
+
WhereFunctionalPseudoClassSelector = __decorate([
|
|
379
|
+
FunctionalPseudoClassProperties(0 /* Specificity.Zero */, 0 /* Rarity.PseudoClass */, 1 /* PseudoClassSelectorList.Forgiving */)
|
|
380
|
+
], WhereFunctionalPseudoClassSelector);
|
|
381
|
+
export { WhereFunctionalPseudoClassSelector };
|
|
245
382
|
export class SimpleSelectorSequence extends SimpleSelector {
|
|
246
383
|
constructor(selectors) {
|
|
247
384
|
super();
|
|
248
385
|
this.selectors = selectors;
|
|
249
386
|
this.specificity = selectors.reduce((sum, sel) => sel.specificity + sum, 0);
|
|
250
|
-
this.head =
|
|
387
|
+
this.head = selectors.reduce((prev, curr) => (!prev || curr.rarity > prev.rarity ? curr : prev), null);
|
|
251
388
|
this.dynamic = selectors.some((sel) => sel.dynamic);
|
|
252
389
|
}
|
|
253
390
|
toString() {
|
|
@@ -266,34 +403,41 @@ export class SimpleSelectorSequence extends SimpleSelector {
|
|
|
266
403
|
this.head.lookupSort(sorter, base || this);
|
|
267
404
|
}
|
|
268
405
|
}
|
|
269
|
-
export class
|
|
406
|
+
export class ComplexSelector extends SelectorCore {
|
|
270
407
|
constructor(selectors) {
|
|
271
408
|
super();
|
|
272
409
|
this.selectors = selectors;
|
|
273
|
-
|
|
274
|
-
let
|
|
275
|
-
let lastGroup;
|
|
410
|
+
let siblingsToGroup;
|
|
411
|
+
let currentGroup;
|
|
276
412
|
const groups = [];
|
|
277
413
|
this.specificity = 0;
|
|
278
414
|
this.dynamic = false;
|
|
279
|
-
for (let i = selectors.length - 1; i
|
|
415
|
+
for (let i = selectors.length - 1; i >= 0; i--) {
|
|
280
416
|
const sel = selectors[i];
|
|
281
|
-
|
|
282
|
-
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
417
|
+
switch (sel.combinator) {
|
|
418
|
+
case undefined:
|
|
419
|
+
case Combinator.descendant:
|
|
420
|
+
siblingsToGroup = [];
|
|
421
|
+
currentGroup = [siblingsToGroup];
|
|
422
|
+
groups.push(currentGroup);
|
|
423
|
+
break;
|
|
424
|
+
case Combinator.child:
|
|
425
|
+
siblingsToGroup = [];
|
|
426
|
+
currentGroup.push(siblingsToGroup);
|
|
427
|
+
break;
|
|
428
|
+
case Combinator.adjacent:
|
|
429
|
+
case Combinator.sibling:
|
|
430
|
+
break;
|
|
431
|
+
default:
|
|
432
|
+
throw new Error(`Unsupported combinator "${sel.combinator}" for selector ${sel}.`);
|
|
289
433
|
}
|
|
290
434
|
this.specificity += sel.specificity;
|
|
291
435
|
if (sel.dynamic) {
|
|
292
436
|
this.dynamic = true;
|
|
293
437
|
}
|
|
294
|
-
|
|
438
|
+
siblingsToGroup.push(sel);
|
|
295
439
|
}
|
|
296
|
-
this.groups = groups.map((g) => new Selector.ChildGroup(g.map((
|
|
440
|
+
this.groups = groups.map((g) => new Selector.ChildGroup(g.map((selectors) => (selectors.length > 1 ? new Selector.SiblingGroup(selectors) : selectors[0]))));
|
|
297
441
|
this.last = selectors[selectors.length - 1];
|
|
298
442
|
}
|
|
299
443
|
toString() {
|
|
@@ -302,13 +446,13 @@ export class Selector extends SelectorCore {
|
|
|
302
446
|
match(node) {
|
|
303
447
|
return this.groups.every((group, i) => {
|
|
304
448
|
if (i === 0) {
|
|
305
|
-
node = group.
|
|
449
|
+
node = group.getMatchingNode(node, true);
|
|
306
450
|
return !!node;
|
|
307
451
|
}
|
|
308
452
|
else {
|
|
309
453
|
let ancestor = node;
|
|
310
454
|
while ((ancestor = ancestor.parent ?? ancestor._modalParent)) {
|
|
311
|
-
if ((node = group.
|
|
455
|
+
if ((node = group.getMatchingNode(ancestor, true))) {
|
|
312
456
|
return true;
|
|
313
457
|
}
|
|
314
458
|
}
|
|
@@ -316,8 +460,14 @@ export class Selector extends SelectorCore {
|
|
|
316
460
|
}
|
|
317
461
|
});
|
|
318
462
|
}
|
|
463
|
+
mayMatch(node) {
|
|
464
|
+
return false;
|
|
465
|
+
}
|
|
466
|
+
trackChanges(node, map) {
|
|
467
|
+
this.selectors.forEach((sel) => sel.trackChanges(node, map));
|
|
468
|
+
}
|
|
319
469
|
lookupSort(sorter, base) {
|
|
320
|
-
this.last.lookupSort(sorter, this);
|
|
470
|
+
this.last.lookupSort(sorter, base || this);
|
|
321
471
|
}
|
|
322
472
|
accumulateChanges(node, map) {
|
|
323
473
|
if (!this.dynamic) {
|
|
@@ -326,7 +476,7 @@ export class Selector extends SelectorCore {
|
|
|
326
476
|
const bounds = [];
|
|
327
477
|
const mayMatch = this.groups.every((group, i) => {
|
|
328
478
|
if (i === 0) {
|
|
329
|
-
const nextNode = group.
|
|
479
|
+
const nextNode = group.getMatchingNode(node, false);
|
|
330
480
|
bounds.push({ left: node, right: node });
|
|
331
481
|
node = nextNode;
|
|
332
482
|
return !!node;
|
|
@@ -334,7 +484,7 @@ export class Selector extends SelectorCore {
|
|
|
334
484
|
else {
|
|
335
485
|
let ancestor = node;
|
|
336
486
|
while ((ancestor = ancestor.parent)) {
|
|
337
|
-
const nextNode = group.
|
|
487
|
+
const nextNode = group.getMatchingNode(ancestor, false);
|
|
338
488
|
if (nextNode) {
|
|
339
489
|
bounds.push({ left: ancestor, right: null });
|
|
340
490
|
node = nextNode;
|
|
@@ -367,37 +517,112 @@ export class Selector extends SelectorCore {
|
|
|
367
517
|
return mayMatch;
|
|
368
518
|
}
|
|
369
519
|
}
|
|
520
|
+
export var Selector;
|
|
370
521
|
(function (Selector) {
|
|
371
522
|
// Non-spec. Selector sequences are grouped by ancestor then by child combinators for easier backtracking.
|
|
372
|
-
class ChildGroup {
|
|
523
|
+
class ChildGroup extends SelectorBase {
|
|
373
524
|
constructor(selectors) {
|
|
525
|
+
super();
|
|
374
526
|
this.selectors = selectors;
|
|
375
527
|
this.dynamic = selectors.some((sel) => sel.dynamic);
|
|
376
528
|
}
|
|
529
|
+
getMatchingNode(node, strict) {
|
|
530
|
+
const funcName = strict ? 'match' : 'mayMatch';
|
|
531
|
+
return this.selectors.every((sel, i) => (node = i === 0 ? node : node.parent) && sel[funcName](node)) ? node : null;
|
|
532
|
+
}
|
|
377
533
|
match(node) {
|
|
378
|
-
return this.
|
|
534
|
+
return this.getMatchingNode(node, true) != null;
|
|
379
535
|
}
|
|
380
536
|
mayMatch(node) {
|
|
381
|
-
return this.
|
|
537
|
+
return this.getMatchingNode(node, false) != null;
|
|
382
538
|
}
|
|
383
539
|
trackChanges(node, map) {
|
|
384
|
-
this.selectors.forEach((sel, i) =>
|
|
540
|
+
this.selectors.forEach((sel, i) => {
|
|
541
|
+
if (i === 0) {
|
|
542
|
+
node && sel.trackChanges(node, map);
|
|
543
|
+
}
|
|
544
|
+
else {
|
|
545
|
+
node = node.parent;
|
|
546
|
+
if (node && sel.mayMatch(node)) {
|
|
547
|
+
sel.trackChanges(node, map);
|
|
548
|
+
}
|
|
549
|
+
}
|
|
550
|
+
});
|
|
385
551
|
}
|
|
386
552
|
}
|
|
387
553
|
Selector.ChildGroup = ChildGroup;
|
|
388
|
-
class SiblingGroup {
|
|
554
|
+
class SiblingGroup extends SelectorBase {
|
|
389
555
|
constructor(selectors) {
|
|
556
|
+
super();
|
|
390
557
|
this.selectors = selectors;
|
|
391
558
|
this.dynamic = selectors.some((sel) => sel.dynamic);
|
|
392
559
|
}
|
|
393
560
|
match(node) {
|
|
394
|
-
return this.selectors.every((sel, i) =>
|
|
561
|
+
return this.selectors.every((sel, i) => {
|
|
562
|
+
if (i === 0) {
|
|
563
|
+
return node && sel.match(node);
|
|
564
|
+
}
|
|
565
|
+
if (sel.combinator === Combinator.adjacent) {
|
|
566
|
+
node = getNodePreviousDirectSibling(node);
|
|
567
|
+
return node && sel.match(node);
|
|
568
|
+
}
|
|
569
|
+
// Sibling combinator
|
|
570
|
+
let isMatching = false;
|
|
571
|
+
eachNodePreviousGeneralSibling(node, (sibling) => {
|
|
572
|
+
isMatching = sel.match(sibling);
|
|
573
|
+
return !isMatching;
|
|
574
|
+
});
|
|
575
|
+
return isMatching;
|
|
576
|
+
});
|
|
395
577
|
}
|
|
396
578
|
mayMatch(node) {
|
|
397
|
-
return this.selectors.every((sel, i) =>
|
|
579
|
+
return this.selectors.every((sel, i) => {
|
|
580
|
+
if (i === 0) {
|
|
581
|
+
return node && sel.mayMatch(node);
|
|
582
|
+
}
|
|
583
|
+
if (sel.combinator === Combinator.adjacent) {
|
|
584
|
+
node = getNodePreviousDirectSibling(node);
|
|
585
|
+
return node && sel.mayMatch(node);
|
|
586
|
+
}
|
|
587
|
+
// Sibling combinator
|
|
588
|
+
let isMatching = false;
|
|
589
|
+
eachNodePreviousGeneralSibling(node, (sibling) => {
|
|
590
|
+
isMatching = sel.mayMatch(sibling);
|
|
591
|
+
return !isMatching;
|
|
592
|
+
});
|
|
593
|
+
return isMatching;
|
|
594
|
+
});
|
|
398
595
|
}
|
|
399
596
|
trackChanges(node, map) {
|
|
400
|
-
this.selectors.forEach((sel, i) =>
|
|
597
|
+
this.selectors.forEach((sel, i) => {
|
|
598
|
+
if (i === 0) {
|
|
599
|
+
if (node) {
|
|
600
|
+
sel.trackChanges(node, map);
|
|
601
|
+
}
|
|
602
|
+
}
|
|
603
|
+
else {
|
|
604
|
+
if (sel.combinator === Combinator.adjacent) {
|
|
605
|
+
node = getNodePreviousDirectSibling(node);
|
|
606
|
+
if (node && sel.mayMatch(node)) {
|
|
607
|
+
sel.trackChanges(node, map);
|
|
608
|
+
}
|
|
609
|
+
}
|
|
610
|
+
else {
|
|
611
|
+
// Sibling combinator
|
|
612
|
+
let matchingSibling;
|
|
613
|
+
eachNodePreviousGeneralSibling(node, (sibling) => {
|
|
614
|
+
const isMatching = sel.mayMatch(sibling);
|
|
615
|
+
if (isMatching) {
|
|
616
|
+
matchingSibling = sibling;
|
|
617
|
+
}
|
|
618
|
+
return !isMatching;
|
|
619
|
+
});
|
|
620
|
+
if (matchingSibling) {
|
|
621
|
+
sel.trackChanges(matchingSibling, map);
|
|
622
|
+
}
|
|
623
|
+
}
|
|
624
|
+
}
|
|
625
|
+
});
|
|
401
626
|
}
|
|
402
627
|
}
|
|
403
628
|
Selector.SiblingGroup = SiblingGroup;
|
|
@@ -426,65 +651,101 @@ function createDeclaration(decl) {
|
|
|
426
651
|
return { property: isCssVariable(decl.property) ? decl.property : decl.property.toLowerCase(), value: decl.value };
|
|
427
652
|
}
|
|
428
653
|
function createSimpleSelectorFromAst(ast) {
|
|
429
|
-
if (ast.type === '
|
|
430
|
-
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
|
|
435
|
-
|
|
436
|
-
return new
|
|
654
|
+
if (ast.type === 'attribute') {
|
|
655
|
+
if (ast.name === 'class') {
|
|
656
|
+
return new ClassSelector(ast.value);
|
|
657
|
+
}
|
|
658
|
+
if (ast.name === 'id') {
|
|
659
|
+
return new IdSelector(ast.value);
|
|
660
|
+
}
|
|
661
|
+
return new AttributeSelector(ast.name, ast.action, ast.value, !!ast.ignoreCase);
|
|
437
662
|
}
|
|
438
|
-
if (ast.type === '
|
|
439
|
-
return new
|
|
663
|
+
if (ast.type === 'tag') {
|
|
664
|
+
return new TypeSelector(ast.name.replace('-', '').toLowerCase());
|
|
440
665
|
}
|
|
441
|
-
if (ast.type === '
|
|
442
|
-
|
|
666
|
+
if (ast.type === 'pseudo') {
|
|
667
|
+
if (ast.name === 'is') {
|
|
668
|
+
return new IsFunctionalPseudoClassSelector(ast.name, ast.data);
|
|
669
|
+
}
|
|
670
|
+
if (ast.name === 'where') {
|
|
671
|
+
return new WhereFunctionalPseudoClassSelector(ast.name, ast.data);
|
|
672
|
+
}
|
|
673
|
+
if (ast.name === 'not') {
|
|
674
|
+
return new NotFunctionalPseudoClassSelector(ast.name, ast.data);
|
|
675
|
+
}
|
|
676
|
+
return new PseudoClassSelector(ast.name);
|
|
443
677
|
}
|
|
444
|
-
if (ast.type === '
|
|
678
|
+
if (ast.type === 'universal') {
|
|
445
679
|
return new UniversalSelector();
|
|
446
680
|
}
|
|
681
|
+
return new InvalidSelector(new Error(ast.type));
|
|
447
682
|
}
|
|
448
|
-
function createSimpleSelectorSequenceFromAst(
|
|
449
|
-
if (
|
|
683
|
+
function createSimpleSelectorSequenceFromAst(asts) {
|
|
684
|
+
if (asts.length === 0) {
|
|
450
685
|
return new InvalidSelector(new Error('Empty simple selector sequence.'));
|
|
451
686
|
}
|
|
452
|
-
|
|
453
|
-
return createSimpleSelectorFromAst(
|
|
687
|
+
if (asts.length === 1) {
|
|
688
|
+
return createSimpleSelectorFromAst(asts[0]);
|
|
454
689
|
}
|
|
455
|
-
|
|
456
|
-
|
|
690
|
+
const sequenceSelectors = [];
|
|
691
|
+
for (const ast of asts) {
|
|
692
|
+
const selector = createSimpleSelectorFromAst(ast);
|
|
693
|
+
if (selector instanceof InvalidSelector) {
|
|
694
|
+
return selector;
|
|
695
|
+
}
|
|
696
|
+
sequenceSelectors.push(selector);
|
|
457
697
|
}
|
|
698
|
+
return new SimpleSelectorSequence(sequenceSelectors);
|
|
458
699
|
}
|
|
459
|
-
function createSelectorFromAst(
|
|
460
|
-
|
|
700
|
+
function createSelectorFromAst(asts) {
|
|
701
|
+
let result;
|
|
702
|
+
if (asts.length === 0) {
|
|
461
703
|
return new InvalidSelector(new Error('Empty selector.'));
|
|
462
704
|
}
|
|
463
|
-
|
|
464
|
-
return
|
|
465
|
-
}
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
705
|
+
if (asts.length === 1) {
|
|
706
|
+
return createSimpleSelectorFromAst(asts[0]);
|
|
707
|
+
}
|
|
708
|
+
const simpleSelectorSequences = [];
|
|
709
|
+
let sequenceAsts = [];
|
|
710
|
+
let combinatorCount = 0;
|
|
711
|
+
for (const ast of asts) {
|
|
712
|
+
const combinator = Combinator[ast.type];
|
|
713
|
+
// Combinator means the end of a sequence
|
|
714
|
+
if (combinator != null) {
|
|
715
|
+
const selector = createSimpleSelectorSequenceFromAst(sequenceAsts);
|
|
716
|
+
if (selector instanceof InvalidSelector) {
|
|
717
|
+
return selector;
|
|
718
|
+
}
|
|
719
|
+
selector.combinator = combinator;
|
|
720
|
+
simpleSelectorSequences.push(selector);
|
|
721
|
+
combinatorCount++;
|
|
722
|
+
// Cleanup stored selectors for the new sequence to take place
|
|
723
|
+
sequenceAsts = [];
|
|
724
|
+
}
|
|
725
|
+
else {
|
|
726
|
+
sequenceAsts.push(ast);
|
|
727
|
+
}
|
|
728
|
+
}
|
|
729
|
+
if (combinatorCount > 0) {
|
|
730
|
+
// Create a sequence using the remaining selectors after the last combinator
|
|
731
|
+
if (sequenceAsts.length) {
|
|
732
|
+
const selector = createSimpleSelectorSequenceFromAst(sequenceAsts);
|
|
733
|
+
if (selector instanceof InvalidSelector) {
|
|
734
|
+
return selector;
|
|
475
735
|
}
|
|
476
|
-
simpleSelectorSequences.push(
|
|
736
|
+
simpleSelectorSequences.push(selector);
|
|
477
737
|
}
|
|
478
|
-
return new
|
|
738
|
+
return new ComplexSelector(simpleSelectorSequences);
|
|
479
739
|
}
|
|
740
|
+
return createSimpleSelectorSequenceFromAst(sequenceAsts);
|
|
480
741
|
}
|
|
481
742
|
export function createSelector(sel) {
|
|
482
743
|
try {
|
|
483
|
-
const
|
|
484
|
-
if (!
|
|
744
|
+
const result = convertToCSSWhatSelector(sel);
|
|
745
|
+
if (!result?.length) {
|
|
485
746
|
return new InvalidSelector(new Error('Empty selector'));
|
|
486
747
|
}
|
|
487
|
-
return createSelectorFromAst(
|
|
748
|
+
return createSelectorFromAst(result[0]);
|
|
488
749
|
}
|
|
489
750
|
catch (e) {
|
|
490
751
|
return new InvalidSelector(e);
|
|
@@ -544,9 +805,6 @@ export class SelectorsMatch {
|
|
|
544
805
|
this.changeMap = new Map();
|
|
545
806
|
}
|
|
546
807
|
addAttribute(node, attribute) {
|
|
547
|
-
if (CSSUtils.IgnoredCssDynamicAttributeTracking.has(attribute)) {
|
|
548
|
-
return;
|
|
549
|
-
}
|
|
550
808
|
const deps = this.properties(node);
|
|
551
809
|
if (!deps.attributes) {
|
|
552
810
|
deps.attributes = new Set();
|