Web Inspector: Convert TreeElement classes to ES6
[WebKit-https.git] / Source / WebInspectorUI / UserInterface / Views / TreeOutlineDataGridSynchronizer.js
1 /*
2  * Copyright (C) 2013, 2015 Apple Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
14  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
15  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
17  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
18  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
19  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
20  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
21  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
22  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
23  * THE POSSIBILITY OF SUCH DAMAGE.
24  */
25
26 WebInspector.TreeOutlineDataGridSynchronizer = class TreeOutlineDataGridSynchronizer extends WebInspector.Object
27 {
28     constructor(treeOutline, dataGrid, delegate)
29     {
30         super();
31
32         this._treeOutline = treeOutline;
33         this._dataGrid = dataGrid;
34         this._delegate = delegate || null;
35         this._enabled = true;
36
37         this._treeOutline.element.parentNode.addEventListener("scroll", this._treeOutlineScrolled.bind(this));
38         this._dataGrid.scrollContainer.addEventListener("scroll", this._dataGridScrolled.bind(this));
39
40         this._treeOutline.__dataGridNode = this._dataGrid;
41
42         this._dataGrid.addEventListener(WebInspector.DataGrid.Event.ExpandedNode, this._dataGridNodeExpanded, this);
43         this._dataGrid.addEventListener(WebInspector.DataGrid.Event.CollapsedNode, this._dataGridNodeCollapsed, this);
44         this._dataGrid.addEventListener(WebInspector.DataGrid.Event.SelectedNodeChanged, this._dataGridNodeSelected, this);
45
46         // FIXME: This is a hack. TreeOutline should just dispatch events via WebInspector.Object.
47         var existingOnAdd = treeOutline.onadd;
48         var existingOnRemove = treeOutline.onremove;
49         var existingOnExpand = treeOutline.onexpand;
50         var existingOnCollapse = treeOutline.oncollapse;
51         var existingOnHidden = treeOutline.onhidden;
52         var existingOnSelect = treeOutline.onselect;
53
54         treeOutline.onadd = function(element) {
55             this._treeElementAdded(element);
56             if (existingOnAdd)
57                 existingOnAdd.call(treeOutline, element);
58         }.bind(this);
59
60         treeOutline.onremove = function(element) {
61             this._treeElementRemoved(element);
62             if (existingOnRemove)
63                 existingOnRemove.call(treeOutline, element);
64         }.bind(this);
65
66         treeOutline.onexpand = function(element) {
67             this._treeElementExpanded(element);
68             if (existingOnExpand)
69                 existingOnExpand.call(treeOutline, element);
70         }.bind(this);
71
72         treeOutline.oncollapse = function(element) {
73             this._treeElementCollapsed(element);
74             if (existingOnCollapse)
75                 existingOnCollapse.call(treeOutline, element);
76         }.bind(this);
77
78         treeOutline.onhidden = function(element, hidden) {
79             this._treeElementHiddenChanged(element, hidden);
80             if (existingOnHidden)
81                 existingOnHidden.call(treeOutline, element, hidden);
82         }.bind(this);
83
84         treeOutline.onselect = function(element, selectedByUser) {
85             this._treeElementSelected(element, selectedByUser);
86             if (existingOnSelect)
87                 existingOnSelect.call(treeOutline, element, selectedByUser);
88         }.bind(this);
89     }
90
91     // Public
92
93     get treeOutline()
94     {
95         return this._treeOutline;
96     }
97
98     get dataGrid()
99     {
100         return this._dataGrid;
101     }
102
103     get delegate()
104     {
105         return this._delegate;
106     }
107
108     get enabled()
109     {
110         return this._enabled;
111     }
112
113     set enabled(x)
114     {
115         this._enabled = x || false;
116     }
117
118     associate(treeElement, dataGridNode)
119     {
120         console.assert(treeElement);
121         console.assert(dataGridNode);
122
123         treeElement.__dataGridNode = dataGridNode;
124         dataGridNode.__treeElement = treeElement;
125     }
126
127     synchronize()
128     {
129         this._dataGrid.scrollContainer.scrollTop = this._treeOutline.element.parentNode.scrollTop;
130         if (this._treeOutline.selectedTreeElement)
131             this._treeOutline.selectedTreeElement.__dataGridNode.select(true);
132         else if (this._dataGrid.selectedNode)
133             this._dataGrid.selectedNode.deselect(true);
134     }
135
136     treeElementForDataGridNode(dataGridNode)
137     {
138         return dataGridNode.__treeElement || null;
139     }
140
141     dataGridNodeForTreeElement(treeElement)
142     {
143         if (treeElement.__dataGridNode)
144             return treeElement.__dataGridNode;
145
146         if (typeof this._delegate.dataGridNodeForTreeElement === "function") {
147             var dataGridNode = this._delegate.dataGridNodeForTreeElement(treeElement);
148             if (dataGridNode)
149                 this.associate(treeElement, dataGridNode);
150             return dataGridNode;
151         }
152
153         return null;
154     }
155
156     // Private
157
158     _treeOutlineScrolled(event)
159     {
160         if (!this._enabled)
161             return;
162
163         if (this._ignoreNextTreeOutlineScrollEvent) {
164             delete this._ignoreNextTreeOutlineScrollEvent;
165             return;
166         }
167
168         this._ignoreNextDataGridScrollEvent = true;
169         this._dataGrid.scrollContainer.scrollTop = this._treeOutline.element.parentNode.scrollTop;
170     }
171
172     _dataGridScrolled(event)
173     {
174         if (!this._enabled)
175             return;
176
177         if (this._ignoreNextDataGridScrollEvent) {
178             delete this._ignoreNextDataGridScrollEvent;
179             return;
180         }
181
182         this._ignoreNextTreeOutlineScrollEvent = true;
183         this._treeOutline.element.parentNode.scrollTop = this._dataGrid.scrollContainer.scrollTop;
184     }
185
186     _dataGridNodeSelected(event)
187     {
188         if (!this._enabled)
189             return;
190
191         var dataGridNode = this._dataGrid.selectedNode;
192         if (dataGridNode)
193             dataGridNode.__treeElement.select(true, true, true, true);
194     }
195
196     _dataGridNodeExpanded(event)
197     {
198         if (!this._enabled)
199             return;
200
201         var dataGridNode = event.data.dataGridNode;
202         console.assert(dataGridNode);
203
204         if (!dataGridNode.__treeElement.expanded)
205             dataGridNode.__treeElement.expand();
206     }
207
208     _dataGridNodeCollapsed(event)
209     {
210         if (!this._enabled)
211             return;
212
213         var dataGridNode = event.data.dataGridNode;
214         console.assert(dataGridNode);
215
216         if (dataGridNode.__treeElement.expanded)
217             dataGridNode.__treeElement.collapse();
218     }
219
220     _treeElementSelected(treeElement, selectedByUser)
221     {
222         if (!this._enabled)
223             return;
224
225         var dataGridNode = treeElement.__dataGridNode;
226         console.assert(dataGridNode);
227
228         dataGridNode.select(true);
229     }
230
231     _treeElementAdded(treeElement)
232     {
233         if (!this._enabled)
234             return;
235
236         var dataGridNode = this.dataGridNodeForTreeElement(treeElement);
237         console.assert(dataGridNode);
238
239         var parentDataGridNode = treeElement.parent.__dataGridNode;
240         console.assert(dataGridNode);
241
242         var childIndex = treeElement.parent.children.indexOf(treeElement);
243         console.assert(childIndex !== -1);
244
245         parentDataGridNode.insertChild(dataGridNode, childIndex);
246     }
247
248     _treeElementRemoved(treeElement)
249     {
250         if (!this._enabled)
251             return;
252
253         var dataGridNode = treeElement.__dataGridNode;
254         console.assert(dataGridNode);
255
256         if (dataGridNode.parent)
257             dataGridNode.parent.removeChild(dataGridNode);
258     }
259
260     _treeElementExpanded(treeElement)
261     {
262         if (!this._enabled)
263             return;
264
265         var dataGridNode = treeElement.__dataGridNode;
266         console.assert(dataGridNode);
267
268         if (!dataGridNode.expanded)
269             dataGridNode.expand();
270     }
271
272     _treeElementCollapsed(treeElement)
273     {
274         if (!this._enabled)
275             return;
276
277         var dataGridNode = treeElement.__dataGridNode;
278         console.assert(dataGridNode);
279
280         if (dataGridNode.expanded)
281             dataGridNode.collapse();
282     }
283
284     _treeElementHiddenChanged(treeElement, hidden)
285     {
286         if (!this._enabled)
287             return;
288
289         var dataGridNode = treeElement.__dataGridNode;
290         console.assert(dataGridNode);
291
292         dataGridNode.element.classList.toggle("hidden", hidden);
293     }
294 };