chrome-devtools-frontend 1.0.1008562 → 1.0.1009019
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/.vscode/devtools-workspace-launch.json +1 -1
- package/config/gni/devtools_grd_files.gni +0 -1
- package/front_end/core/sdk/Target.ts +2 -2
- package/front_end/legacy_test_runner/elements_test_runner/ElementsTestRunner.js +8 -8
- package/front_end/models/logs/NetworkLog.ts +18 -8
- package/front_end/models/source_map_scopes/NamesResolver.ts +7 -2
- package/front_end/panels/elements/ComputedStyleWidget.ts +190 -221
- package/front_end/panels/elements/ElementsTreeElement.ts +101 -90
- package/front_end/panels/elements/StylePropertyTreeElement.ts +1 -1
- package/front_end/panels/elements/components/ComputedStyleProperty.ts +14 -2
- package/front_end/panels/elements/components/ComputedStyleTrace.ts +4 -1
- package/front_end/panels/elements/components/computedStyleProperty.css +15 -6
- package/front_end/panels/elements/components/computedStyleTrace.css +12 -1
- package/front_end/panels/elements/computedStyleSidebarPane.css +0 -5
- package/front_end/panels/network/NetworkSearchScope.ts +1 -1
- package/front_end/ui/components/docs/computed_style_property/basic.ts +12 -10
- package/front_end/ui/components/docs/computed_style_property/traceable.ts +13 -10
- package/front_end/ui/legacy/components/data_grid/DataGrid.ts +3 -5
- package/package.json +1 -1
- package/front_end/panels/elements/computedStyleWidgetTree.css +0 -66
@@ -38,9 +38,9 @@ import * as SDK from '../../core/sdk/sdk.js';
|
|
38
38
|
import * as InlineEditor from '../../ui/legacy/components/inline_editor/inline_editor.js';
|
39
39
|
import * as Components from '../../ui/legacy/components/utils/utils.js';
|
40
40
|
import * as UI from '../../ui/legacy/legacy.js';
|
41
|
+
|
41
42
|
import * as ElementsComponents from './components/components.js';
|
42
43
|
import computedStyleSidebarPaneStyles from './computedStyleSidebarPane.css.js';
|
43
|
-
import computedStyleWidgetTreeStyles from './computedStyleWidgetTree.css.js';
|
44
44
|
|
45
45
|
import type {ComputedStyle} from './ComputedStyleModel.js';
|
46
46
|
import {ComputedStyleModel, Events} from './ComputedStyleModel.js';
|
@@ -49,7 +49,9 @@ import {PlatformFontsWidget} from './PlatformFontsWidget.js';
|
|
49
49
|
import type {Category} from './PropertyNameCategories.js';
|
50
50
|
import {categorizePropertyName, DefaultCategoryOrder} from './PropertyNameCategories.js';
|
51
51
|
import {StylePropertiesSection} from './StylePropertiesSection.js';
|
52
|
-
import {
|
52
|
+
import {StylesSidebarPane, StylesSidebarPropertyRenderer} from './StylesSidebarPane.js';
|
53
|
+
import * as TreeOutline from '../../ui/components/tree_outline/tree_outline.js';
|
54
|
+
import * as LitHtml from '../../ui/lit-html/lit-html.js';
|
53
55
|
|
54
56
|
const UIStrings = {
|
55
57
|
/**
|
@@ -92,23 +94,24 @@ const UIStrings = {
|
|
92
94
|
const str_ = i18n.i18n.registerUIStrings('panels/elements/ComputedStyleWidget.ts', UIStrings);
|
93
95
|
const i18nString = i18n.i18n.getLocalizedString.bind(undefined, str_);
|
94
96
|
|
95
|
-
const createPropertyElement =
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
const renderer = new StylesSidebarPropertyRenderer(null, node, propertyName, propertyValue);
|
100
|
-
renderer.setColorHandler(processColor);
|
97
|
+
const createPropertyElement =
|
98
|
+
(node: SDK.DOMModel.DOMNode, propertyName: string, propertyValue: string, traceable: boolean, inherited: boolean,
|
99
|
+
onNavigateToSource: ((event?: Event) => void)): ElementsComponents.ComputedStyleProperty.ComputedStyleProperty => {
|
100
|
+
const propertyElement = new ElementsComponents.ComputedStyleProperty.ComputedStyleProperty();
|
101
101
|
|
102
|
-
|
103
|
-
|
104
|
-
propertyElement.appendChild(propertyNameElement);
|
102
|
+
const renderer = new StylesSidebarPropertyRenderer(null, node, propertyName, propertyValue);
|
103
|
+
renderer.setColorHandler(processColor);
|
105
104
|
|
106
|
-
|
107
|
-
|
108
|
-
|
105
|
+
propertyElement.data = {
|
106
|
+
propertyNameRenderer: renderer.renderName.bind(renderer),
|
107
|
+
propertyValueRenderer: renderer.renderValue.bind(renderer),
|
108
|
+
traceable,
|
109
|
+
inherited,
|
110
|
+
onNavigateToSource,
|
111
|
+
};
|
109
112
|
|
110
|
-
|
111
|
-
};
|
113
|
+
return propertyElement;
|
114
|
+
};
|
112
115
|
|
113
116
|
const createTraceElement =
|
114
117
|
(node: SDK.DOMModel.DOMNode, property: SDK.CSSProperty.CSSProperty, isPropertyOverloaded: boolean,
|
@@ -123,16 +126,15 @@ const createTraceElement =
|
|
123
126
|
trace.appendChild(valueElement);
|
124
127
|
|
125
128
|
const rule = (property.ownerStyle.parentRule as SDK.CSSRule.CSSStyleRule | null);
|
129
|
+
let ruleOriginNode;
|
126
130
|
if (rule) {
|
127
|
-
|
128
|
-
linkSpan.appendChild(StylePropertiesSection.createRuleOriginNode(matchedStyles, linkifier, rule));
|
129
|
-
linkSpan.slot = 'trace-link';
|
130
|
-
trace.appendChild(linkSpan);
|
131
|
+
ruleOriginNode = StylePropertiesSection.createRuleOriginNode(matchedStyles, linkifier, rule);
|
131
132
|
}
|
132
133
|
trace.data = {
|
133
134
|
selector: rule ? rule.selectorText() : 'element.style',
|
134
135
|
active: !isPropertyOverloaded,
|
135
|
-
onNavigateToSource:
|
136
|
+
onNavigateToSource: navigateToSource.bind(null, property),
|
137
|
+
ruleOriginNode,
|
136
138
|
};
|
137
139
|
|
138
140
|
return trace;
|
@@ -154,7 +156,10 @@ const processColor = (text: string): Node => {
|
|
154
156
|
return swatch;
|
155
157
|
};
|
156
158
|
|
157
|
-
const navigateToSource = (cssProperty: SDK.CSSProperty.CSSProperty, event
|
159
|
+
const navigateToSource = (cssProperty: SDK.CSSProperty.CSSProperty, event?: Event): void => {
|
160
|
+
if (!event) {
|
161
|
+
return;
|
162
|
+
}
|
158
163
|
void Common.Revealer.reveal(cssProperty);
|
159
164
|
event.consume(true);
|
160
165
|
};
|
@@ -171,6 +176,20 @@ const propertySorter = (propA: string, propB: string): number => {
|
|
171
176
|
return Platform.StringUtilities.compare(canonicalA, canonicalB);
|
172
177
|
};
|
173
178
|
|
179
|
+
type ComputedStyleData = {
|
180
|
+
tag: 'property',
|
181
|
+
propertyName: string,
|
182
|
+
propertyValue: string,
|
183
|
+
inherited: boolean,
|
184
|
+
}|{
|
185
|
+
tag: 'traceElement',
|
186
|
+
property: SDK.CSSProperty.CSSProperty,
|
187
|
+
rule: SDK.CSSRule.CSSRule | null,
|
188
|
+
}|{
|
189
|
+
tag: 'category',
|
190
|
+
name: string,
|
191
|
+
};
|
192
|
+
|
174
193
|
export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
175
194
|
private computedStyleModel: ComputedStyleModel;
|
176
195
|
private readonly showInheritedComputedStylePropertiesSetting: Common.Settings.Setting<boolean>;
|
@@ -178,17 +197,11 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
178
197
|
input: Element;
|
179
198
|
private filterRegex: RegExp|null;
|
180
199
|
private readonly noMatchesElement: HTMLElement;
|
181
|
-
private propertiesOutline: UI.TreeOutline.TreeOutlineInShadow;
|
182
|
-
private readonly propertyByTreeElement: WeakMap<UI.TreeOutline.TreeElement, {
|
183
|
-
name: string,
|
184
|
-
value: string,
|
185
|
-
}>;
|
186
|
-
private readonly categoryByTreeElement: WeakMap<UI.TreeOutline.TreeElement, Category>;
|
187
|
-
private readonly expandedProperties: Set<string>;
|
188
|
-
private readonly expandedGroups: Set<Category>;
|
189
200
|
private readonly linkifier: Components.Linkifier.Linkifier;
|
190
201
|
private readonly imagePreviewPopover: ImagePreviewPopover;
|
191
|
-
|
202
|
+
|
203
|
+
#computedStylesTree = new TreeOutline.TreeOutline.TreeOutline<ComputedStyleData>();
|
204
|
+
#treeData?: TreeOutline.TreeOutline.TreeOutlineData<ComputedStyleData>;
|
192
205
|
|
193
206
|
constructor() {
|
194
207
|
super(true);
|
@@ -223,20 +236,7 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
223
236
|
this.noMatchesElement = this.contentElement.createChild('div', 'gray-info-message');
|
224
237
|
this.noMatchesElement.textContent = i18nString(UIStrings.noMatchingProperty);
|
225
238
|
|
226
|
-
this.
|
227
|
-
this.propertiesOutline.hideOverflow();
|
228
|
-
this.propertiesOutline.setShowSelectionOnKeyboardFocus(true);
|
229
|
-
this.propertiesOutline.setFocusable(true);
|
230
|
-
this.propertiesOutline.element.classList.add('monospace', 'computed-properties');
|
231
|
-
this.propertiesOutline.addEventListener(UI.TreeOutline.Events.ElementExpanded, this.onTreeElementToggled, this);
|
232
|
-
this.propertiesOutline.addEventListener(UI.TreeOutline.Events.ElementCollapsed, this.onTreeElementToggled, this);
|
233
|
-
this.contentElement.appendChild(this.propertiesOutline.element);
|
234
|
-
|
235
|
-
this.propertyByTreeElement = new WeakMap();
|
236
|
-
this.categoryByTreeElement = new WeakMap();
|
237
|
-
|
238
|
-
this.expandedProperties = new Set();
|
239
|
-
this.expandedGroups = new Set(DefaultCategoryOrder);
|
239
|
+
this.contentElement.appendChild(this.#computedStylesTree);
|
240
240
|
|
241
241
|
this.linkifier = new Components.Linkifier.Linkifier(_maxLinkLength);
|
242
242
|
|
@@ -251,13 +251,12 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
251
251
|
const fontsWidget = new PlatformFontsWidget(this.computedStyleModel);
|
252
252
|
fontsWidget.show(this.contentElement);
|
253
253
|
|
254
|
-
this.idleCallbackManager = new IdleCallbackManager();
|
255
254
|
Common.Settings.Settings.instance().moduleSetting('colorFormat').addChangeListener(this.update.bind(this));
|
256
255
|
}
|
257
256
|
|
258
257
|
onResize(): void {
|
259
258
|
const isNarrow = this.contentElement.offsetWidth < 260;
|
260
|
-
this.
|
259
|
+
this.#computedStylesTree.classList.toggle('computed-narrow', isNarrow);
|
261
260
|
}
|
262
261
|
|
263
262
|
private showInheritedComputedStyleChanged(): void {
|
@@ -265,25 +264,22 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
265
264
|
}
|
266
265
|
|
267
266
|
update(): void {
|
268
|
-
if (this.idleCallbackManager) {
|
269
|
-
this.idleCallbackManager.discard();
|
270
|
-
}
|
271
|
-
this.idleCallbackManager = new IdleCallbackManager();
|
272
267
|
super.update();
|
273
268
|
}
|
274
269
|
|
275
270
|
wasShown(): void {
|
276
271
|
super.wasShown();
|
277
272
|
this.registerCSSFiles([computedStyleSidebarPaneStyles]);
|
278
|
-
this.propertiesOutline.registerCSSFiles([computedStyleWidgetTreeStyles]);
|
279
273
|
}
|
280
274
|
|
281
275
|
async doUpdate(): Promise<void> {
|
282
276
|
const [nodeStyles, matchedStyles] =
|
283
277
|
await Promise.all([this.computedStyleModel.fetchComputedStyle(), this.fetchMatchedCascade()]);
|
278
|
+
if (!nodeStyles || !matchedStyles) {
|
279
|
+
this.noMatchesElement.classList.remove('hidden');
|
280
|
+
return;
|
281
|
+
}
|
284
282
|
const shouldGroupComputedStyles = this.groupComputedStylesSetting.get();
|
285
|
-
this.propertiesOutline.contentElement.classList.toggle('grouped-list', shouldGroupComputedStyles);
|
286
|
-
this.propertiesOutline.contentElement.classList.toggle('alphabetical-list', !shouldGroupComputedStyles);
|
287
283
|
if (shouldGroupComputedStyles) {
|
288
284
|
await this.rebuildGroupedList(nodeStyles, matchedStyles);
|
289
285
|
} else {
|
@@ -310,15 +306,12 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
310
306
|
}
|
311
307
|
}
|
312
308
|
|
313
|
-
private async rebuildAlphabeticalList(
|
314
|
-
|
315
|
-
const hadFocus = this.propertiesOutline.element.hasFocus();
|
309
|
+
private async rebuildAlphabeticalList(nodeStyle: ComputedStyle, matchedStyles: SDK.CSSMatchedStyles.CSSMatchedStyles):
|
310
|
+
Promise<void> {
|
316
311
|
this.imagePreviewPopover.hide();
|
317
|
-
this.propertiesOutline.removeChildren();
|
318
312
|
this.linkifier.reset();
|
319
313
|
const cssModel = this.computedStyleModel.cssModel();
|
320
|
-
if (!
|
321
|
-
this.noMatchesElement.classList.remove('hidden');
|
314
|
+
if (!cssModel) {
|
322
315
|
return;
|
323
316
|
}
|
324
317
|
|
@@ -329,8 +322,7 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
329
322
|
const propertyTraces = this.computePropertyTraces(matchedStyles);
|
330
323
|
const nonInheritedProperties = this.computeNonInheritedProperties(matchedStyles);
|
331
324
|
const showInherited = this.showInheritedComputedStylePropertiesSetting.get();
|
332
|
-
const
|
333
|
-
// filter and preprocess properties to line up in the computed style queue
|
325
|
+
const tree: TreeOutline.TreeOutlineUtils.TreeNode<ComputedStyleData>[] = [];
|
334
326
|
for (const propertyName of uniqueProperties) {
|
335
327
|
const propertyValue = nodeStyle.computedStyle.get(propertyName) || '';
|
336
328
|
const canonicalName = SDK.CSSMetadata.cssMetadata().canonicalPropertyName(propertyName);
|
@@ -344,45 +336,21 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
344
336
|
if (propertyName !== canonicalName && propertyValue === nodeStyle.computedStyle.get(canonicalName)) {
|
345
337
|
continue;
|
346
338
|
}
|
347
|
-
|
339
|
+
tree.push(this.buildTreeNode(propertyTraces, propertyName, propertyValue, isInherited));
|
348
340
|
}
|
349
341
|
|
350
|
-
this.
|
351
|
-
|
352
|
-
|
353
|
-
|
354
|
-
|
355
|
-
|
356
|
-
|
357
|
-
const batchSize = 20;
|
358
|
-
const timeoutInterval = 100;
|
359
|
-
let timeout = 100;
|
360
|
-
while (computedStyleQueue.length > 0) {
|
361
|
-
const currentBatch = computedStyleQueue.splice(0, batchSize);
|
362
|
-
|
363
|
-
this.idleCallbackManager.schedule(() => {
|
364
|
-
for (const {propertyName, propertyValue, isInherited} of currentBatch) {
|
365
|
-
const treeElement = this.buildPropertyTreeElement(
|
366
|
-
propertyTraces, node, (matchedStyles as SDK.CSSMatchedStyles.CSSMatchedStyles), propertyName,
|
367
|
-
propertyValue, isInherited, hadFocus);
|
368
|
-
this.propertiesOutline.appendChild(treeElement);
|
369
|
-
}
|
370
|
-
|
371
|
-
this.filterAlphabeticalList();
|
372
|
-
}, timeout);
|
373
|
-
|
374
|
-
timeout += timeoutInterval;
|
375
|
-
}
|
376
|
-
|
377
|
-
await this.idleCallbackManager.awaitDone();
|
378
|
-
this.propertiesOutline.contentElement.classList.remove('render-flash');
|
342
|
+
const defaultRenderer = this.createTreeNodeRenderer(propertyTraces, node, matchedStyles);
|
343
|
+
this.#treeData = {
|
344
|
+
tree,
|
345
|
+
compact: true,
|
346
|
+
defaultRenderer,
|
347
|
+
};
|
348
|
+
this.filterAlphabeticalList();
|
379
349
|
}
|
380
350
|
|
381
351
|
private async rebuildGroupedList(
|
382
352
|
nodeStyle: ComputedStyle|null, matchedStyles: SDK.CSSMatchedStyles.CSSMatchedStyles|null): Promise<void> {
|
383
|
-
const hadFocus = this.propertiesOutline.element.hasFocus();
|
384
353
|
this.imagePreviewPopover.hide();
|
385
|
-
this.propertiesOutline.removeChildren();
|
386
354
|
this.linkifier.reset();
|
387
355
|
const cssModel = this.computedStyleModel.cssModel();
|
388
356
|
if (!nodeStyle || !matchedStyles || !cssModel) {
|
@@ -395,8 +363,9 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
395
363
|
const nonInheritedProperties = this.computeNonInheritedProperties(matchedStyles);
|
396
364
|
const showInherited = this.showInheritedComputedStylePropertiesSetting.get();
|
397
365
|
|
398
|
-
const propertiesByCategory = new Map<Category,
|
366
|
+
const propertiesByCategory = new Map<Category, string[]>();
|
399
367
|
|
368
|
+
const tree: TreeOutline.TreeOutlineUtils.TreeNode<ComputedStyleData>[] = [];
|
400
369
|
for (const [propertyName, propertyValue] of nodeStyle.computedStyle) {
|
401
370
|
const canonicalName = SDK.CSSMetadata.cssMetadata().canonicalPropertyName(propertyName);
|
402
371
|
const isInherited = !nonInheritedProperties.has(canonicalName);
|
@@ -412,115 +381,109 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
412
381
|
|
413
382
|
const categories = categorizePropertyName(propertyName);
|
414
383
|
for (const category of categories) {
|
415
|
-
const treeElement = this.buildPropertyTreeElement(
|
416
|
-
propertyTraces, node, matchedStyles, propertyName, propertyValue, isInherited, hadFocus);
|
417
384
|
if (!propertiesByCategory.has(category)) {
|
418
385
|
propertiesByCategory.set(category, []);
|
419
386
|
}
|
420
|
-
|
421
|
-
// @ts-expect-error
|
422
|
-
propertiesByCategory.get(category).push(treeElement);
|
387
|
+
propertiesByCategory.get(category)?.push(propertyName);
|
423
388
|
}
|
424
389
|
}
|
425
390
|
|
391
|
+
this.#computedStylesTree.removeChildren();
|
426
392
|
for (const category of DefaultCategoryOrder) {
|
427
393
|
const properties = propertiesByCategory.get(category);
|
428
394
|
if (properties && properties.length > 0) {
|
429
|
-
const
|
430
|
-
|
431
|
-
|
432
|
-
|
433
|
-
|
434
|
-
|
435
|
-
for (const property of properties) {
|
436
|
-
group.appendChild(property);
|
395
|
+
const propertyNodes: TreeOutline.TreeOutlineUtils.TreeNode<ComputedStyleData>[] = [];
|
396
|
+
for (const propertyName of properties) {
|
397
|
+
const propertyValue = nodeStyle.computedStyle.get(propertyName) || '';
|
398
|
+
const canonicalName = SDK.CSSMetadata.cssMetadata().canonicalPropertyName(propertyName);
|
399
|
+
const isInherited = !nonInheritedProperties.has(canonicalName);
|
400
|
+
propertyNodes.push(this.buildTreeNode(propertyTraces, propertyName, propertyValue, isInherited));
|
437
401
|
}
|
438
|
-
|
439
|
-
this.propertiesOutline.appendChild(group);
|
440
|
-
if (this.expandedGroups.has(category)) {
|
441
|
-
group.expand();
|
442
|
-
}
|
443
|
-
|
444
|
-
this.categoryByTreeElement.set(group, category);
|
402
|
+
tree.push({id: category, treeNodeData: {tag: 'category', name: category}, children: async () => propertyNodes});
|
445
403
|
}
|
446
404
|
}
|
405
|
+
const defaultRenderer = this.createTreeNodeRenderer(propertyTraces, node, matchedStyles);
|
406
|
+
this.#treeData = {
|
407
|
+
tree,
|
408
|
+
compact: true,
|
409
|
+
defaultRenderer,
|
410
|
+
};
|
411
|
+
return this.filterGroupLists();
|
412
|
+
}
|
447
413
|
|
448
|
-
|
414
|
+
private buildTraceNode(property: SDK.CSSProperty.CSSProperty):
|
415
|
+
TreeOutline.TreeOutlineUtils.TreeNode<ComputedStyleData> {
|
416
|
+
const rule = property.ownerStyle.parentRule as SDK.CSSRule.CSSStyleRule;
|
417
|
+
return {
|
418
|
+
treeNodeData: {
|
419
|
+
tag: 'traceElement',
|
420
|
+
property,
|
421
|
+
rule,
|
422
|
+
},
|
423
|
+
id: rule.origin + ': ' + rule.styleSheetId + property.range,
|
424
|
+
};
|
449
425
|
}
|
450
426
|
|
451
|
-
private
|
452
|
-
|
453
|
-
|
454
|
-
|
455
|
-
|
456
|
-
|
457
|
-
|
458
|
-
|
459
|
-
|
427
|
+
private createTreeNodeRenderer(
|
428
|
+
propertyTraces: Map<string, SDK.CSSProperty.CSSProperty[]>,
|
429
|
+
domNode: SDK.DOMModel.DOMNode,
|
430
|
+
matchedStyles: SDK.CSSMatchedStyles.CSSMatchedStyles,
|
431
|
+
):
|
432
|
+
(node: TreeOutline.TreeOutlineUtils.TreeNode<ComputedStyleData>,
|
433
|
+
state: {isExpanded: boolean}) => LitHtml.TemplateResult {
|
434
|
+
return node => {
|
435
|
+
const data = node.treeNodeData;
|
436
|
+
let navigate: (arg0?: Event) => void = () => {};
|
437
|
+
if (data.tag === 'property') {
|
438
|
+
const trace = propertyTraces.get(data.propertyName);
|
439
|
+
const activeProperty = trace?.find(
|
440
|
+
property => matchedStyles.propertyState(property) === SDK.CSSMatchedStyles.PropertyState.Active);
|
441
|
+
if (activeProperty) {
|
442
|
+
navigate = navigateToSource.bind(this, activeProperty);
|
443
|
+
}
|
444
|
+
const propertyElement = createPropertyElement(
|
445
|
+
domNode, data.propertyName, data.propertyValue, propertyTraces.has(data.propertyName), data.inherited,
|
446
|
+
navigate);
|
447
|
+
if (activeProperty) {
|
448
|
+
propertyElement.addEventListener(
|
449
|
+
'contextmenu', this.handleContextMenuEvent.bind(this, matchedStyles, activeProperty));
|
450
|
+
}
|
451
|
+
return LitHtml.html`${propertyElement}`;
|
460
452
|
}
|
461
|
-
|
453
|
+
if (data.tag === 'traceElement') {
|
454
|
+
const isPropertyOverloaded =
|
455
|
+
matchedStyles.propertyState(data.property) === SDK.CSSMatchedStyles.PropertyState.Overloaded;
|
456
|
+
const traceElement =
|
457
|
+
createTraceElement(domNode, data.property, isPropertyOverloaded, matchedStyles, this.linkifier);
|
458
|
+
traceElement.addEventListener(
|
459
|
+
'contextmenu', this.handleContextMenuEvent.bind(this, matchedStyles, data.property));
|
460
|
+
return LitHtml.html`${traceElement}`;
|
461
|
+
}
|
462
|
+
return LitHtml.html`<span style="cursor: text; color: var(--color-text-secondary);">${data.name}</span>`;
|
463
|
+
};
|
462
464
|
}
|
463
465
|
|
464
|
-
private
|
465
|
-
propertyTraces: Map<string, SDK.CSSProperty.CSSProperty[]>,
|
466
|
-
|
467
|
-
|
468
|
-
|
469
|
-
|
470
|
-
|
471
|
-
if (trace) {
|
472
|
-
const activeProperty =
|
473
|
-
this.renderPropertyTrace((matchedStyles as SDK.CSSMatchedStyles.CSSMatchedStyles), node, treeElement, trace);
|
474
|
-
treeElement.setExpandable(true);
|
475
|
-
treeElement.listItemElement.addEventListener('click', event => {
|
476
|
-
treeElement.expanded ? treeElement.collapse() : treeElement.expand();
|
477
|
-
event.consume();
|
478
|
-
}, false);
|
479
|
-
navigate = (navigateToSource.bind(this, activeProperty) as (arg0?: Event|undefined) => void);
|
480
|
-
}
|
481
|
-
|
482
|
-
const propertyElement = createPropertyElement(node, propertyName, propertyValue);
|
483
|
-
propertyElement.data = {
|
484
|
-
traceable: propertyTraces.has(propertyName),
|
466
|
+
private buildTreeNode(
|
467
|
+
propertyTraces: Map<string, SDK.CSSProperty.CSSProperty[]>, propertyName: string, propertyValue: string,
|
468
|
+
isInherited: boolean): TreeOutline.TreeOutlineUtils.TreeNode<ComputedStyleData> {
|
469
|
+
const treeNodeData: ComputedStyleData = {
|
470
|
+
tag: 'property',
|
471
|
+
propertyName,
|
472
|
+
propertyValue,
|
485
473
|
inherited: isInherited,
|
486
|
-
onNavigateToSource: navigate,
|
487
474
|
};
|
488
|
-
|
489
|
-
|
490
|
-
|
491
|
-
|
492
|
-
|
493
|
-
|
494
|
-
|
495
|
-
if (this.expandedProperties.has(propertyName)) {
|
496
|
-
treeElement.expand();
|
497
|
-
}
|
498
|
-
|
499
|
-
return treeElement;
|
500
|
-
}
|
501
|
-
|
502
|
-
private renderPropertyTrace(
|
503
|
-
matchedStyles: SDK.CSSMatchedStyles.CSSMatchedStyles, node: SDK.DOMModel.DOMNode,
|
504
|
-
rootTreeElement: UI.TreeOutline.TreeElement,
|
505
|
-
tracedProperties: SDK.CSSProperty.CSSProperty[]): SDK.CSSProperty.CSSProperty {
|
506
|
-
let activeProperty: SDK.CSSProperty.CSSProperty|null = null;
|
507
|
-
for (const property of tracedProperties) {
|
508
|
-
const isPropertyOverloaded =
|
509
|
-
matchedStyles.propertyState(property) === SDK.CSSMatchedStyles.PropertyState.Overloaded;
|
510
|
-
if (!isPropertyOverloaded) {
|
511
|
-
activeProperty = property;
|
512
|
-
rootTreeElement.listItemElement.addEventListener(
|
513
|
-
'contextmenu', this.handleContextMenuEvent.bind(this, matchedStyles, property));
|
514
|
-
}
|
515
|
-
const trace = createTraceElement(node, property, isPropertyOverloaded, matchedStyles, this.linkifier);
|
516
|
-
const traceTreeElement = new UI.TreeOutline.TreeElement();
|
517
|
-
traceTreeElement.title = trace;
|
518
|
-
traceTreeElement.listItemElement.addEventListener(
|
519
|
-
'contextmenu', this.handleContextMenuEvent.bind(this, matchedStyles, property));
|
520
|
-
rootTreeElement.appendChild(traceTreeElement);
|
475
|
+
const trace = propertyTraces.get(propertyName);
|
476
|
+
if (!trace) {
|
477
|
+
return {
|
478
|
+
treeNodeData,
|
479
|
+
id: propertyName,
|
480
|
+
};
|
521
481
|
}
|
522
|
-
|
523
|
-
|
482
|
+
return {
|
483
|
+
treeNodeData,
|
484
|
+
id: propertyName,
|
485
|
+
children: async () => trace.map(this.buildTraceNode),
|
486
|
+
};
|
524
487
|
}
|
525
488
|
|
526
489
|
private handleContextMenuEvent(
|
@@ -575,56 +538,62 @@ export class ComputedStyleWidget extends UI.ThrottledWidget.ThrottledWidget {
|
|
575
538
|
return result;
|
576
539
|
}
|
577
540
|
|
578
|
-
filterComputedStyles(this: ComputedStyleWidget, regex: RegExp|null): void {
|
541
|
+
async filterComputedStyles(this: ComputedStyleWidget, regex: RegExp|null): Promise<void> {
|
579
542
|
this.filterRegex = regex;
|
580
543
|
if (this.groupComputedStylesSetting.get()) {
|
581
|
-
this.filterGroupLists();
|
582
|
-
} else {
|
583
|
-
this.filterAlphabeticalList();
|
544
|
+
return this.filterGroupLists();
|
584
545
|
}
|
546
|
+
return this.filterAlphabeticalList();
|
585
547
|
}
|
586
548
|
|
587
|
-
private
|
549
|
+
private nodeFilter(node: TreeOutline.TreeOutlineUtils.TreeNode<ComputedStyleData>): boolean {
|
588
550
|
const regex = this.filterRegex;
|
589
|
-
const
|
590
|
-
|
591
|
-
|
592
|
-
|
593
|
-
if (!property) {
|
594
|
-
continue;
|
595
|
-
}
|
596
|
-
const matched = !regex || regex.test(property.name) || regex.test(property.value);
|
597
|
-
child.hidden = !matched;
|
598
|
-
hasMatch = hasMatch || matched;
|
551
|
+
const data = node.treeNodeData;
|
552
|
+
if (data.tag === 'property') {
|
553
|
+
const matched = !regex || regex.test(data.propertyName) || regex.test(data.propertyValue);
|
554
|
+
return matched;
|
599
555
|
}
|
600
|
-
|
556
|
+
return true;
|
601
557
|
}
|
602
558
|
|
603
|
-
private
|
604
|
-
|
605
|
-
|
606
|
-
|
607
|
-
|
608
|
-
|
609
|
-
|
610
|
-
|
611
|
-
|
612
|
-
|
613
|
-
|
614
|
-
|
615
|
-
|
616
|
-
|
617
|
-
|
618
|
-
|
619
|
-
|
559
|
+
private filterAlphabeticalList(): void {
|
560
|
+
if (!this.#treeData) {
|
561
|
+
return;
|
562
|
+
}
|
563
|
+
const tree = this.#treeData.tree.filter(this.nodeFilter.bind(this));
|
564
|
+
this.#computedStylesTree.data = {
|
565
|
+
tree,
|
566
|
+
defaultRenderer: this.#treeData.defaultRenderer,
|
567
|
+
compact: this.#treeData.compact,
|
568
|
+
};
|
569
|
+
this.noMatchesElement.classList.toggle('hidden', Boolean(tree.length));
|
570
|
+
}
|
571
|
+
|
572
|
+
private async filterGroupLists(): Promise<void> {
|
573
|
+
if (!this.#treeData) {
|
574
|
+
return;
|
575
|
+
}
|
576
|
+
const tree: TreeOutline.TreeOutlineUtils.TreeNode<ComputedStyleData>[] = [];
|
577
|
+
for (const group of this.#treeData.tree) {
|
578
|
+
const data = group.treeNodeData;
|
579
|
+
if (data.tag !== 'category' || !group.children) {
|
580
|
+
continue;
|
581
|
+
}
|
582
|
+
const properties = await group.children();
|
583
|
+
const filteredChildren = properties.filter(this.nodeFilter.bind(this));
|
584
|
+
if (filteredChildren.length) {
|
585
|
+
tree.push(
|
586
|
+
{id: data.name, treeNodeData: {tag: 'category', name: data.name}, children: async () => filteredChildren});
|
620
587
|
}
|
621
|
-
group.hidden = !hasGroupMatch;
|
622
|
-
// the first visible group won't have a divider before the group title
|
623
|
-
group.listItemElement.classList.toggle('first-group', hasGroupMatch && !foundFirstGroup);
|
624
|
-
foundFirstGroup = foundFirstGroup || hasGroupMatch;
|
625
588
|
}
|
626
589
|
|
627
|
-
this.
|
590
|
+
this.#computedStylesTree.data = {
|
591
|
+
tree,
|
592
|
+
defaultRenderer: this.#treeData.defaultRenderer,
|
593
|
+
compact: this.#treeData.compact,
|
594
|
+
};
|
595
|
+
await this.#computedStylesTree.expandRecursively(0);
|
596
|
+
this.noMatchesElement.classList.toggle('hidden', Boolean(tree.length));
|
628
597
|
}
|
629
598
|
}
|
630
599
|
|