@@ -16,148 +16,112 @@ async function _update() {
1616
1717async function _updateSelectedNode ( selectedNode ) {
1818 const issueListEl = document . querySelector ( "#selected ul" ) ;
19+ issueListEl . innerHTML = "" ;
1920
20- if ( ! _isValidElement ( selectedNode ) ) {
21- _render ( [ ] , issueListEl ) ;
22- return ;
23- }
24-
25- const issues = [ ] ;
26-
27- const { actorID, attributes, nodeName } = selectedNode ;
28- issues . push (
29- ..._webcompat . getHTMLElementIssues ( nodeName , attributes , _targetBrowsers ) ) ;
30-
31- const declarationBlocks =
32- await browser . experiments . inspectedNode . getStyle ( actorID , true ) ;
33- for ( const declarations of declarationBlocks ) {
34- issues . push (
35- ..._webcompat . getCSSDeclarationBlockIssues ( declarations , _targetBrowsers ) ) ;
36- }
37-
38- _render ( issues , issueListEl ) ;
21+ _asyncRenderNodes ( 0 , [ selectedNode ] , true , issueListEl , [ ] ) . then ( ( ) => {
22+ if ( ! issueListEl . querySelector ( "li" ) ) {
23+ _renderNoIssue ( issueListEl ) ;
24+ }
25+ } ) ;
3926}
4027
4128async function _updateSubtree ( selectedNode ) {
4229 const subtreeEl = document . getElementById ( "subtree" ) ;
4330 const issueListEl = subtreeEl . querySelector ( "ul" ) ;
4431
45- if ( ! _isValidElement ( selectedNode ) ) {
46- _render ( [ ] , issueListEl ) ;
47- return ;
48- }
49-
50- const issues = [ ] ;
51-
5232 subtreeEl . classList . add ( "processing" ) ;
5333 const progressEl = subtreeEl . querySelector ( "aside label" ) ;
5434
5535 progressEl . textContent = "Getting all descendants of the selected node" ;
5636 const nodesInSubtree = await browser . experiments . inspectedNode . getNodesInSubtree ( ) ;
5737
58- progressEl . textContent = "Getting web compatibility issues for HTML element" ;
59- for ( const node of nodesInSubtree ) {
60- if ( ! _isValidElement ( node ) ) {
61- continue
38+ progressEl . textContent = "Getting web compatibility issues" ;
39+ issueListEl . innerHTML = "" ;
40+ _asyncRenderNodes ( 0 , nodesInSubtree , false , issueListEl , [ ] ) . then ( ( ) => {
41+ subtreeEl . classList . remove ( "processing" ) ;
42+ if ( ! issueListEl . querySelector ( "li" ) ) {
43+ _renderNoIssue ( issueListEl ) ;
6244 }
45+ } ) ;
46+ }
6347
64- const { attributes, nodeName } = node ;
65- issues . push (
66- ...
67- _webcompat . getHTMLElementIssues ( nodeName , attributes , _targetBrowsers )
68- . map ( issue => {
69- issue . node = node ;
70- return issue ;
71- } )
72- )
48+ async function _asyncRenderNodes ( index , nodes , skipPseudo , listEl , groupsCache ) {
49+ const node = nodes [ index ] ;
50+ if ( ! node ) {
51+ return ;
7352 }
7453
75- progressEl . textContent = "Getting web compatibility issues for CSS styles" ;
76- for ( const node of nodesInSubtree ) {
77- if ( ! _isValidElement ( node ) ) {
78- continue
79- }
54+ if ( _isValidElement ( node ) ) {
55+ const { actorID , attributes , nodeName } = node ;
56+ const htmlIssues =
57+ _webcompat . getHTMLElementIssues ( nodeName , attributes , _targetBrowsers ) ;
58+ _appendIssues ( htmlIssues , node , listEl , groupsCache ) ;
8059
8160 const declarationBlocks =
82- await browser . experiments . inspectedNode . getStyle ( node . actorID , false ) ;
61+ await browser . experiments . inspectedNode . getStyle ( actorID , skipPseudo ) ;
8362 for ( const declarations of declarationBlocks ) {
84- issues . push (
85- ...
86- _webcompat . getCSSDeclarationBlockIssues ( declarations , _targetBrowsers )
87- . map ( issue => {
88- issue . node = node ;
89- return issue ;
90- } )
91- ) ;
63+ const cssIssues =
64+ _webcompat . getCSSDeclarationBlockIssues ( declarations , _targetBrowsers ) ;
65+ _appendIssues ( cssIssues , node , listEl , groupsCache ) ;
9266 }
9367 }
9468
95- progressEl . textContent = "Grouping all issues" ;
96- const issueGroups = _groupIssues ( issues ) ;
97-
98- progressEl . textContent = "Rendering all issues" ;
99- _render ( issueGroups , issueListEl ) ;
100-
101- subtreeEl . classList . remove ( "processing" ) ;
69+ await _asyncRenderNodes ( index + 1 , nodes , skipPseudo , listEl , groupsCache ) ;
10270}
10371
104- /**
105- * Group by the issue cause.
106- * @param {Array } issues
107- * The issue list which WebCompat library returns. Also the issue in the list
108- * assume to contain the node information additionaly.
109- * @return {Array }
110- * Array of issues grouped. The issue has `nodes` attribute which contains the
111- * node informations where caused the issue.
112- */
113- function _groupIssues ( issues ) {
114- const issueGroups = [ ] ;
72+ function _isValidElement ( { nodeType, isCustomElement } ) {
73+ return nodeType === Node . ELEMENT_NODE && ! isCustomElement ;
74+ }
11575
76+ function _appendIssues ( issues , node , listEl , issueGroups ) {
11677 for ( const issue of issues ) {
117- let issueGroup = issueGroups . find ( i => {
118- return i . type === issue . type &&
119- i . property === issue . property &&
120- i . element === issue . element &&
121- i . attribute === issue . attribute &&
122- i . value === issue . value ;
123- } ) ;
124-
125- if ( ! issueGroup ) {
126- issueGroup = Object . assign ( { } , issue , { nodes : [ ] , node : undefined } ) ;
127- issueGroups . push ( issueGroup ) ;
128- }
129-
130- const isNodeContainedInGroup = issueGroup . nodes . some ( n => {
131- return n . nodeName === issue . node . nodeName &&
132- n . nodeType === issue . node . nodeType &&
133- n . id === issue . node . id &&
134- n . className === issue . node . className ;
135- } ) ;
78+ _appendIssue ( issue , node , listEl , issueGroups ) ;
79+ }
80+ }
13681
137- if ( ! isNodeContainedInGroup ) {
138- issueGroup . nodes . push ( issue . node ) ;
139- }
82+ function _appendIssue ( issue , node , listEl , issueGroups ) {
83+ let issueGroup = issueGroups . find ( i => {
84+ return i . type === issue . type &&
85+ i . property === issue . property &&
86+ i . element === issue . element &&
87+ i . attribute === issue . attribute &&
88+ i . value === issue . value ;
89+ } ) ;
90+
91+ if ( ! issueGroup ) {
92+ issueGroup = Object . assign ( { } , issue , { nodes : [ ] } ) ;
93+ issueGroups . push ( issueGroup ) ;
14094 }
14195
142- return issueGroups ;
143- }
96+ const isNodeContainedInGroup = issueGroup . nodes . some ( n => {
97+ return n . nodeName === node . nodeName &&
98+ n . nodeType === node . nodeType &&
99+ n . id === node . id &&
100+ n . className === node . className ;
101+ } ) ;
102+
103+ if ( ! isNodeContainedInGroup ) {
104+ issueGroup . nodes . push ( node ) ;
105+
106+ if ( issueGroup . view ) {
107+ // Remove occurrences element in order to update occurrences only.
108+ issueGroup . view . querySelector ( ".occurrences" ) . remove ( ) ;
109+ } else {
110+ // Append new view for this issue.
111+ const view = _renderIssue ( issueGroup ) ;
112+ listEl . appendChild ( view ) ;
113+ issueGroup . view = view ;
114+ }
144115
145- function _isValidElement ( { nodeType , isCustomElement } ) {
146- return nodeType === Node . ELEMENT_NODE && ! isCustomElement ;
116+ issueGroup . view . append ( _renderOccurrences ( issueGroup . nodes ) ) ;
117+ }
147118}
148119
149- function _render ( issues , issueListEl ) {
150- issueListEl . innerHTML = "" ;
151120
152- if ( ! issues . length ) {
153- const noIssueEl = document . createElement ( "li" ) ;
154- noIssueEl . textContent = "No issues" ;
155- issueListEl . appendChild ( noIssueEl ) ;
156- } else {
157- for ( const issue of issues ) {
158- issueListEl . appendChild ( _renderIssue ( issue ) ) ;
159- }
160- }
121+ function _renderNoIssue ( listEl ) {
122+ const noIssueEl = document . createElement ( "li" ) ;
123+ noIssueEl . textContent = "No issues" ;
124+ listEl . appendChild ( noIssueEl ) ;
161125}
162126
163127function _renderIssue ( issue ) {
@@ -168,15 +132,10 @@ function _renderIssue(issue) {
168132 issueEl . appendChild ( predicateEl ) ;
169133
170134 issueEl . classList . add ( ( issue . deprecated ? "warning" : "information" ) ) ;
171-
172- if ( issue . nodes ) {
173- issueEl . append ( _renderOccurrences ( issue ) ) ;
174- }
175-
176135 return issueEl ;
177136}
178137
179- function _renderOccurrences ( { nodes } ) {
138+ function _renderOccurrences ( nodes ) {
180139 const occurrencesEl = document . createElement ( "section" ) ;
181140 occurrencesEl . classList . add ( "occurrences" ) ;
182141
0 commit comments