Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(8)

Side by Side Diff: third_party/WebKit/Source/devtools/front_end/ui/Widget.js

Issue 2157363006: DevTools: keep widgets in widget hierarchy upon hide, split attach/detach cycle from show/hide. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: lcean Created 4 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « third_party/WebKit/Source/devtools/front_end/ui/TabbedPane.js ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2008 Apple Inc. All Rights Reserved. 2 * Copyright (C) 2008 Apple Inc. All Rights Reserved.
3 * Copyright (C) 2011 Google Inc. All Rights Reserved. 3 * Copyright (C) 2011 Google Inc. All Rights Reserved.
4 * 4 *
5 * Redistribution and use in source and binary forms, with or without 5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions 6 * modification, are permitted provided that the following conditions
7 * are met: 7 * are met:
8 * 1. Redistributions of source code must retain the above copyright 8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright 10 * 2. Redistributions in binary form must reproduce the above copyright
(...skipping 23 matching lines...) Expand all
34 this.contentElement = createElementWithClass("div", "widget"); 34 this.contentElement = createElementWithClass("div", "widget");
35 if (isWebComponent) { 35 if (isWebComponent) {
36 this.element = createElementWithClass("div", "vbox flex-auto"); 36 this.element = createElementWithClass("div", "vbox flex-auto");
37 this._shadowRoot = WebInspector.createShadowRootWithCoreStyles(this.elem ent); 37 this._shadowRoot = WebInspector.createShadowRootWithCoreStyles(this.elem ent);
38 this._shadowRoot.appendChild(this.contentElement); 38 this._shadowRoot.appendChild(this.contentElement);
39 } else { 39 } else {
40 this.element = this.contentElement; 40 this.element = this.contentElement;
41 } 41 }
42 this._isWebComponent = isWebComponent; 42 this._isWebComponent = isWebComponent;
43 this.element.__widget = this; 43 this.element.__widget = this;
44 this._visible = true; 44 this._visible = false;
45 this._isRoot = false; 45 this._isRoot = false;
46 this._isShowing = false; 46 this._isShowing = false;
47 this._children = []; 47 this._children = [];
48 this._hideOnDetach = false; 48 this._hideOnDetach = false;
49 this._notificationDepth = 0; 49 this._notificationDepth = 0;
50 } 50 }
51 51
52 WebInspector.Widget.prototype = { 52 WebInspector.Widget.prototype = {
53 markAsRoot: function() 53 markAsRoot: function()
54 { 54 {
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
112 */ 112 */
113 _inNotification: function() 113 _inNotification: function()
114 { 114 {
115 return !!this._notificationDepth || (this._parentWidget && this._parentW idget._inNotification()); 115 return !!this._notificationDepth || (this._parentWidget && this._parentW idget._inNotification());
116 }, 116 },
117 117
118 _parentIsShowing: function() 118 _parentIsShowing: function()
119 { 119 {
120 if (this._isRoot) 120 if (this._isRoot)
121 return true; 121 return true;
122 return this._parentWidget && this._parentWidget.isShowing(); 122 return !!this._parentWidget && this._parentWidget.isShowing();
123 }, 123 },
124 124
125 /** 125 /**
126 * @param {function(this:WebInspector.Widget)} method 126 * @param {function(this:WebInspector.Widget)} method
127 */ 127 */
128 _callOnVisibleChildren: function(method) 128 _callOnVisibleChildren: function(method)
129 { 129 {
130 var copy = this._children.slice(); 130 var copy = this._children.slice();
131 for (var i = 0; i < copy.length; ++i) { 131 for (var i = 0; i < copy.length; ++i) {
132 if (copy[i]._parentWidget === this && copy[i]._visible) 132 if (copy[i]._parentWidget === this && copy[i]._visible)
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
203 onLayout: function() 203 onLayout: function()
204 { 204 {
205 }, 205 },
206 206
207 /** 207 /**
208 * @param {?Element} parentElement 208 * @param {?Element} parentElement
209 * @param {?Element=} insertBefore 209 * @param {?Element=} insertBefore
210 */ 210 */
211 show: function(parentElement, insertBefore) 211 show: function(parentElement, insertBefore)
212 { 212 {
213 this.attach(parentElement, insertBefore);
214 this.showWidget();
215 },
216
217 /**
218 * @param {?Element} parentElement
dgozman 2016/07/20 23:48:22 !Element
pfeldman 2016/07/20 23:57:52 Done.
219 * @param {?Element=} insertBefore
220 */
221 attach: function(parentElement, insertBefore)
dgozman 2016/07/20 23:48:22 Let's move the parameters to showWidget instead!
pfeldman 2016/07/20 23:57:52 Acknowledged.
222 {
213 WebInspector.Widget.__assert(parentElement, "Attempt to attach widget wi th no parent element"); 223 WebInspector.Widget.__assert(parentElement, "Attempt to attach widget wi th no parent element");
214 224
215 // Update widget hierarchy. 225 // Update widget hierarchy.
216 if (this.element.parentElement !== parentElement) { 226 var currentParent = parentElement;
217 if (this.element.parentElement) 227 while (currentParent && !currentParent.__widget)
218 this.detach(); 228 currentParent = currentParent.parentElementOrShadowHost();
229 var newParentWidget = currentParent ? currentParent.__widget : null;
219 230
220 var currentParent = parentElement; 231 if (this._parentWidget && newParentWidget !== this._parentWidget) {
221 while (currentParent && !currentParent.__widget) 232 // Reparent.
222 currentParent = currentParent.parentElementOrShadowHost(); 233 this.detach();
223
224 if (currentParent) {
225 this._parentWidget = currentParent.__widget;
226 this._parentWidget._children.push(this);
227 this._isRoot = false;
228 } else
229 WebInspector.Widget.__assert(this._isRoot, "Attempt to attach wi dget to orphan node");
230 } else if (this._visible) {
231 return;
232 } 234 }
233 235
236 if (newParentWidget) {
237 if (this._parentWidget !== newParentWidget) {
238 this._parentWidget = newParentWidget;
239 this._parentWidget._children.push(this);
240 }
241 this._isRoot = false;
242 } else {
243 WebInspector.Widget.__assert(this._isRoot, "Attempt to attach widget to orphan node");
244 }
245
246 this._parentElement = parentElement;
247 this._insertBeforeElement = insertBefore;
248 },
249
250 showWidget: function()
251 {
252 WebInspector.Widget.__assert(this._parentElement, "Attempt to show detac hed widget");
253 if (this._visible)
254 return;
234 this._visible = true; 255 this._visible = true;
235 256
236 if (this._parentIsShowing()) 257 if (this._parentIsShowing())
237 this._processWillShow(); 258 this._processWillShow();
238 259
239 this.element.classList.remove("hidden"); 260 this.element.classList.remove("hidden");
240 261
241 // Reparent 262 // Reparent
242 if (this.element.parentElement !== parentElement) { 263 if (this.element.parentElement !== this._parentElement) {
243 WebInspector.Widget._incrementWidgetCounter(parentElement, this.elem ent); 264 WebInspector.Widget._incrementWidgetCounter(this._parentElement, thi s.element);
244 if (insertBefore) 265 if (this._insertBeforeElement)
245 WebInspector.Widget._originalInsertBefore.call(parentElement, th is.element, insertBefore); 266 WebInspector.Widget._originalInsertBefore.call(this._parentEleme nt, this.element, this._insertBeforeElement);
246 else 267 else
247 WebInspector.Widget._originalAppendChild.call(parentElement, thi s.element); 268 WebInspector.Widget._originalAppendChild.call(this._parentElemen t, this.element);
248 } 269 }
249 270
250 if (this._parentIsShowing()) 271 if (this._parentIsShowing())
251 this._processWasShown(); 272 this._processWasShown();
252 273
253 if (this._parentWidget && this._hasNonZeroConstraints()) 274 if (this._parentWidget && this._hasNonZeroConstraints())
254 this._parentWidget.invalidateConstraints(); 275 this._parentWidget.invalidateConstraints();
255 else 276 else
256 this._processOnResize(); 277 this._processOnResize();
257 }, 278 },
258 279
280 hideWidget: function()
281 {
282 this._hideWidget();
283 },
284
259 /** 285 /**
260 * @param {boolean=} overrideHideOnDetach 286 * @param {boolean=} overrideHideOnDetach
287 * @return {boolean}
dgozman 2016/07/20 23:48:22 Remove the return value.
pfeldman 2016/07/20 23:57:52 Done.
261 */ 288 */
262 detach: function(overrideHideOnDetach) 289 _hideWidget: function(overrideHideOnDetach)
263 { 290 {
264 var parentElement = this.element.parentElement; 291 WebInspector.Widget.__assert(this._parentElement, "Attempt to hide detac hed widget");
265 if (!parentElement) 292 if (!this._visible)
266 return; 293 return false;
294 this._visible = false;
295 var parentElement = this._parentElement;
267 296
268 if (this._parentIsShowing()) 297 if (this._parentIsShowing())
269 this._processWillHide(); 298 this._processWillHide();
270 299
271 if (!overrideHideOnDetach && this.shouldHideOnDetach()) { 300 if (!overrideHideOnDetach && this.shouldHideOnDetach()) {
272 this.element.classList.add("hidden"); 301 this.element.classList.add("hidden");
273 this._visible = false;
274 if (this._parentIsShowing()) 302 if (this._parentIsShowing())
275 this._processWasHidden(); 303 this._processWasHidden();
276 if (this._parentWidget && this._hasNonZeroConstraints()) 304 if (this._parentWidget && this._hasNonZeroConstraints())
277 this._parentWidget.invalidateConstraints(); 305 this._parentWidget.invalidateConstraints();
278 return; 306 return true;
279 } 307 }
280 308
281 // Force legal removal 309 // Force legal removal
282 WebInspector.Widget._decrementWidgetCounter(parentElement, this.element) ; 310 WebInspector.Widget._decrementWidgetCounter(parentElement, this.element) ;
283 WebInspector.Widget._originalRemoveChild.call(parentElement, this.elemen t); 311 WebInspector.Widget._originalRemoveChild.call(parentElement, this.elemen t);
284 312
285 this._visible = false;
286 if (this._parentIsShowing()) 313 if (this._parentIsShowing())
287 this._processWasHidden(); 314 this._processWasHidden();
315 return true;
316 },
317
318 detach: function()
319 {
320 if (!this._parentWidget)
321 return;
322 var wasShown = this._hideWidget(true);
323 if (!wasShown)
324 return;
288 325
289 // Update widget hierarchy. 326 // Update widget hierarchy.
290 if (this._parentWidget) { 327 if (this._parentWidget) {
291 var childIndex = this._parentWidget._children.indexOf(this); 328 var childIndex = this._parentWidget._children.indexOf(this);
292 WebInspector.Widget.__assert(childIndex >= 0, "Attempt to remove non -child widget"); 329 WebInspector.Widget.__assert(childIndex >= 0, "Attempt to remove non -child widget");
293 this._parentWidget._children.splice(childIndex, 1); 330 this._parentWidget._children.splice(childIndex, 1);
294 this._parentWidget.childWasDetached(this); 331 this._parentWidget.childWasDetached(this);
295 var parent = this._parentWidget; 332 var parent = this._parentWidget;
296 this._parentWidget = null; 333 this._parentWidget = null;
334 this._parentElement = null;
335 this._insertBeforeElement = null;
297 if (this._hasNonZeroConstraints()) 336 if (this._hasNonZeroConstraints())
298 parent.invalidateConstraints(); 337 parent.invalidateConstraints();
dgozman 2016/07/20 23:48:22 This should be in hide.
pfeldman 2016/07/20 23:57:52 Done.
299 } else 338 } else {
300 WebInspector.Widget.__assert(this._isRoot, "Removing non-root widget from DOM"); 339 WebInspector.Widget.__assert(this._isRoot, "Removing non-root widget from DOM");
340 }
301 }, 341 },
302 342
303 detachChildWidgets: function() 343 detachChildWidgets: function()
304 { 344 {
305 var children = this._children.slice(); 345 var children = this._children.slice();
306 for (var i = 0; i < children.length; ++i) 346 for (var i = 0; i < children.length; ++i)
307 children[i].detach(); 347 children[i].detach();
308 }, 348 },
309 349
310 /** 350 /**
(...skipping 441 matching lines...) Expand 10 before | Expand all | Expand 10 after
752 { 792 {
753 WebInspector.Widget.__assert(!child.__widgetCounter && !child.__widget, "Att empt to remove element containing widget via regular DOM operation"); 793 WebInspector.Widget.__assert(!child.__widgetCounter && !child.__widget, "Att empt to remove element containing widget via regular DOM operation");
754 return WebInspector.Widget._originalRemoveChild.call(this, child); 794 return WebInspector.Widget._originalRemoveChild.call(this, child);
755 } 795 }
756 796
757 Element.prototype.removeChildren = function() 797 Element.prototype.removeChildren = function()
758 { 798 {
759 WebInspector.Widget.__assert(!this.__widgetCounter, "Attempt to remove eleme nt containing widget via regular DOM operation"); 799 WebInspector.Widget.__assert(!this.__widgetCounter, "Attempt to remove eleme nt containing widget via regular DOM operation");
760 WebInspector.Widget._originalRemoveChildren.call(this); 800 WebInspector.Widget._originalRemoveChildren.call(this);
761 } 801 }
OLDNEW
« no previous file with comments | « third_party/WebKit/Source/devtools/front_end/ui/TabbedPane.js ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698