Changeset 286890 in webkit


Ignore:
Timestamp:
Dec 10, 2021 5:08:04 PM (7 months ago)
Author:
Razvan Caliman
Message:

Web Inspector: Add CSS variable names to property name completion list
https://bugs.webkit.org/show_bug.cgi?id=233372
<rdar://83205968>

Reviewed by Devin Rousso.

Add the list of applicable CSS variables to the list of CSS property name completions.

WI.CSSPropertyNameCompletions is a long-lived object that holds all supported property names.
It doesn't need to change over time in a Web Inspector session. But the list of applicable
CSS variables depends on the selected node.

To avoid thrashing the long list of values in WI.CSSPropertyNameCompletions we don't proactively collect
CSS variables. Instead, we introduce a flag to indicate that the list of CSS variables may
be stale whenever the inspected node changes. Only when completions are requested do we check
this flag and augment the list of CSS property names with the latest list of CSS variables.

  • UserInterface/Models/CSSCompletions.js:

(WI.CSSCompletions.prototype.replaceValues):
Allow a sub-class to replace the list of values in one go.
If a WI.CSSQueryController was used, reset it and provide it the new list of values.

  • UserInterface/Models/CSSPropertyNameCompletions.js:

(WI.CSSPropertyNameCompletions):
(WI.CSSPropertyNameCompletions.prototype.executeQuery):
(WI.CSSPropertyNameCompletions.prototype.startsWith):
(WI.CSSPropertyNameCompletions.prototype._updateValuesWithLatestCSSVariablesIfNeeded):
Holding a copy of the original list of CSS property names in order to create a new list
agumented with variables on demand.

(WI.CSSPropertyNameCompletions.prototype.addValues):
Warn when trying to add new property values which would overwrite the cached and sorted list of CSS property names.

(WI.CSSPropertyNameCompletions.prototype._handleInspectedNodeChanged):
Consider changing of the inspected node as an indicator that the list of variables is stale.
That may not necessarily be true for web pages with all CSS variables declared on :root or <html>,
but iterating over them to verify is needlessly expensive especially if completions were not even requested.

(WI.CSSPropertyNameCompletions.prototype._handleNodesStylesNeedsRefresh):
Consider any change to the styles of the inspected node as a potential change to the list of applicable variables.

(WI.CSSPropertyNameCompletions):

Location:
trunk/Source/WebInspectorUI
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/WebInspectorUI/ChangeLog

    r286887 r286890  
     12021-12-10  Razvan Caliman  <rcaliman@apple.com>
     2
     3        Web Inspector: Add CSS variable names to property name completion list
     4        https://bugs.webkit.org/show_bug.cgi?id=233372
     5        <rdar://83205968>
     6
     7        Reviewed by Devin Rousso.
     8
     9        Add the list of applicable CSS variables to the list of CSS property name completions.
     10
     11        `WI.CSSPropertyNameCompletions` is a long-lived object that holds all supported property names.
     12        It doesn't need to change over time in a Web Inspector session. But the list of applicable
     13        CSS variables depends on the selected node.
     14
     15        To avoid thrashing the long list of values in `WI.CSSPropertyNameCompletions` we don't proactively collect
     16        CSS variables. Instead, we introduce a flag to indicate that the list of CSS variables may
     17        be stale whenever the inspected node changes. Only when completions are requested do we check
     18        this flag and augment the list of CSS property names with the latest list of CSS variables.
     19
     20        * UserInterface/Models/CSSCompletions.js:
     21        (WI.CSSCompletions.prototype.replaceValues):
     22        Allow a sub-class to replace the list of values in one go.
     23        If a `WI.CSSQueryController` was used, reset it and provide it the new list of values.
     24
     25        * UserInterface/Models/CSSPropertyNameCompletions.js:
     26        (WI.CSSPropertyNameCompletions):
     27        (WI.CSSPropertyNameCompletions.prototype.executeQuery):
     28        (WI.CSSPropertyNameCompletions.prototype.startsWith):
     29        (WI.CSSPropertyNameCompletions.prototype._updateValuesWithLatestCSSVariablesIfNeeded):
     30        Holding a copy of the original list of CSS property names in order to create a new list
     31        agumented with variables on demand.
     32
     33        (WI.CSSPropertyNameCompletions.prototype.addValues):
     34        Warn when trying to add new property values which would overwrite the cached and sorted list of CSS property names.
     35
     36        (WI.CSSPropertyNameCompletions.prototype._handleInspectedNodeChanged):
     37        Consider changing of the inspected node as an indicator that the list of variables is stale.
     38        That may not necessarily be true for web pages with all CSS variables declared on :root or <html>,
     39        but iterating over them to verify is needlessly expensive especially if completions were not even requested.
     40
     41        (WI.CSSPropertyNameCompletions.prototype._handleNodesStylesNeedsRefresh):
     42        Consider any change to the styles of the inspected node as a potential change to the list of applicable variables.
     43
     44        (WI.CSSPropertyNameCompletions):
     45
    1462021-12-10  BJ Burg  <bburg@apple.com>
    247
  • trunk/Source/WebInspectorUI/UserInterface/Models/CSSCompletions.js

    r286844 r286890  
    172172        return results;
    173173    }
     174
     175    // Protected
     176
     177    replaceValues(values)
     178    {
     179        console.assert(Array.isArray(values), values);
     180        console.assert(typeof values[0] === "string", "Expect an array of string values", values);
     181
     182        this._values = values;
     183        this._values.sort();
     184
     185        this._queryController?.reset();
     186        this._queryController?.addValues(values);
     187    }
     188
     189    // Private
    174190
    175191    _firstIndexOfPrefix(prefix)
  • trunk/Source/WebInspectorUI/UserInterface/Models/CSSPropertyNameCompletions.js

    r286844 r286890  
    4141
    4242        super(values, options);
     43
     44        this._cachedSortedPropertyNames = this.values.slice();
     45        this._needsVariablesFromInspectedNode = true;
     46
     47        WI.domManager.addEventListener(WI.DOMManager.Event.InspectedNodeChanged, this._handleInspectedNodeChanged, this);
    4348    }
    4449
     
    4954        return this.values.includes(name);
    5055    }
     56
     57    executeQuery(query)
     58    {
     59        this._updateValuesWithLatestCSSVariablesIfNeeded();
     60
     61        return super.executeQuery(query);
     62    }
     63
     64    startsWith(prefix)
     65    {
     66        this._updateValuesWithLatestCSSVariablesIfNeeded();
     67
     68        return super.startsWith(prefix);
     69    }
     70
     71    addValues()
     72    {
     73        console.assert(false, "Adding values will overwrite the list of supported CSS property names.");
     74    }
     75
     76    // Private
     77
     78    _updateValuesWithLatestCSSVariablesIfNeeded()
     79    {
     80        if (!this._needsVariablesFromInspectedNode)
     81            return;
     82
     83        // An inspected node is not guaranteed to exist when unit testing.
     84        if (!WI.domManager.inspectedNode) {
     85            this._needsVariablesFromInspectedNode = false;
     86            return;
     87        }
     88
     89        let nodeStyles = WI.cssManager.stylesForNode(WI.domManager.inspectedNode);
     90        nodeStyles.addEventListener(WI.DOMNodeStyles.Event.NeedsRefresh, this._handleNodesStylesNeedsRefresh, this);
     91
     92        let values = Array.from(nodeStyles.allCSSVariables);
     93        values.pushAll(this._cachedSortedPropertyNames);
     94        this.replaceValues(values);
     95
     96        this._needsVariablesFromInspectedNode = false;
     97    }
     98
     99    _handleInspectedNodeChanged(event)
     100    {
     101        if (this._needsVariablesFromInspectedNode || !event.data.lastInspectedNode)
     102            return;
     103
     104        this._needsVariablesFromInspectedNode = true;
     105
     106        let nodeStyles = WI.cssManager.stylesForNode(event.data.lastInspectedNode);
     107        nodeStyles.removeEventListener(WI.DOMNodeStyles.Event.NeedsRefresh, this._handleNodesStylesNeedsRefresh, this);
     108    }
     109
     110    _handleNodesStylesNeedsRefresh(event)
     111    {
     112        this._needsVariablesFromInspectedNode = true;
     113    }
    51114};
Note: See TracChangeset for help on using the changeset viewer.