Changeset 201171 in webkit
- Timestamp:
- May 19, 2016, 10:58:16 AM (9 years ago)
- Location:
- trunk/Source
- Files:
-
- 11 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WebInspectorUI/ChangeLog
r201126 r201171 1 2016-05-19 Brian Burg <bburg@apple.com> 2 3 Web Inspector: timelines should not update via requestAnimationFrame unless Web Inspector is visible 4 https://bugs.webkit.org/show_bug.cgi?id=157897 5 <rdar://problem/26330802> 6 7 Reviewed by Timothy Hatcher. 8 9 The timelines overview tries to animate using requestAnimationFrame, even if the 10 inspector frontend is not really visible. When it does this, requestAnimationFrame 11 simply stalls out until the inspector becomes visible. If a recording is started 12 while the inspector is not visible, then when it is shown again, the timeline will 13 start to animate from 0s instead of the current time. This happens because the 14 requestAnimationFrame was requested when the current time actually was 0, and it 15 finally executes some time later, when the current time is no longer accurate. 16 Since the timelines animate by calculating time elapsed since the previous frame 17 rather than using event timestamps, there is no way for the timelines to skip forward 18 in their animations in scenarios where the current time becomes arbitrarily skewed. 19 20 To fix this, consider the visibility state of the frontend as reported by the UIProcess. 21 Fire a global notification when visibility state changes, and start or stop updating 22 the current time as the frontend becomes visible or not shown. 23 24 This does not affect most other uses of requestAnimationFrame, which are used as 25 timers to call updateLayout at an appropriate time. The timelines case is different 26 because the current time is fixed prior to requesting an animation frame, and 27 later animation frames are only triggered by earlier requests, so there's nothing to 28 coalesce. 29 30 * UserInterface/Base/Main.js: 31 (WebInspector.loaded): Initialize WebInspector.visible. 32 33 * UserInterface/Base/Object.js: Add new event. 34 35 * UserInterface/Protocol/InspectorFrontendAPI.js: 36 (InspectorFrontendAPI.setIsVisible): Added. 37 38 * UserInterface/Test/Test.js: 39 (WebInspector.updateVisibilityState): Add a stub. 40 41 * UserInterface/Views/TimelineRecordingContentView.js: 42 (WebInspector.TimelineRecordingContentView): 43 (WebInspector.TimelineRecordingContentView.prototype._inspectorVisibilityStateChanged): 44 If visibility state changes while capturing, then start or stop updating the 45 current time as appropriate. Otherwise, refresh the timelines with updated 46 times so that they know about the recording's updated start/current/end time. 47 48 (WebInspector.TimelineRecordingContentView.prototype._startUpdatingCurrentTime): 49 Bail out if the Web Inspector frontend is not visible to the user and won't be 50 able to service requestAnimationFrames immediately. 51 1 52 2016-05-18 Timothy Hatcher <timothy@apple.com> 2 53 -
trunk/Source/WebInspectorUI/UserInterface/Base/Main.js
r200332 r201171 177 177 }; 178 178 179 this.visible = false; 180 179 181 this._windowKeydownListeners = []; 180 182 }; … … 712 714 }; 713 715 716 WebInspector.updateVisibilityState = function(visible) 717 { 718 this.visible = visible; 719 this.notifications.dispatchEventToListeners(WebInspector.Notification.VisibilityStateDidChange); 720 } 721 714 722 WebInspector.handlePossibleLinkClick = function(event, frame, alwaysOpenExternally) 715 723 { -
trunk/Source/WebInspectorUI/UserInterface/Base/Object.js
r195581 r201171 217 217 TabTypesChanged: "tab-types-changed", 218 218 DebugUIEnabledDidChange: "debug-ui-enabled-did-change", 219 VisibilityStateDidChange: "visibility-state-did-change", 219 220 }; -
trunk/Source/WebInspectorUI/UserInterface/Protocol/InspectorFrontendAPI.js
r201101 r201171 67 67 { 68 68 WebInspector.updateDockedState(side); 69 }, 70 71 setIsVisible: function(visible) 72 { 73 WebInspector.updateVisibilityState(visible); 69 74 }, 70 75 -
trunk/Source/WebInspectorUI/UserInterface/Test/Test.js
r197827 r201171 96 96 WebInspector.updateDockedState = () => {}; 97 97 WebInspector.updateDockingAvailability = () => {}; 98 WebInspector.updateVisibilityState = () => {}; 98 99 99 100 window.InspectorTest = new FrontendTestHarness(); -
trunk/Source/WebInspectorUI/UserInterface/Views/TimelineRecordingContentView.js
r201082 r201171 92 92 WebInspector.TimelineView.addEventListener(WebInspector.TimelineView.Event.RecordWasFiltered, this._recordWasFiltered, this); 93 93 94 WebInspector.notifications.addEventListener(WebInspector.Notification.VisibilityStateDidChange, this._inspectorVisibilityStateChanged, this); 95 94 96 for (let instrument of this._recording.instruments) 95 97 this._instrumentAdded(instrument); … … 342 344 } 343 345 346 _inspectorVisibilityStateChanged() 347 { 348 if (WebInspector.timelineManager.activeRecording !== this._recording) 349 return; 350 351 // Stop updating since the results won't be rendered anyway. 352 if (!WebInspector.visible && this._updating) { 353 this._stopUpdatingCurrentTime(); 354 return; 355 } 356 357 // Nothing else to do if the current time was not being updated. 358 if (!WebInspector.visible) 359 return; 360 361 let {startTime, endTime} = this.representedObject; 362 if (!WebInspector.timelineManager.isCapturing()) { 363 // Force the overview to render data from the entire recording. 364 // This is necessary if the recording was started when the inspector was not 365 // visible because the views were never updated with currentTime/endTime. 366 this._updateTimes(startTime, endTime, endTime); 367 return; 368 } 369 370 this._startUpdatingCurrentTime(endTime); 371 } 372 344 373 _update(timestamp) 345 374 { … … 402 431 return; 403 432 404 if (typeof startTime === "number") 433 // Don't update the current time if the Inspector is not visible, as the requestAnimationFrames won't work. 434 if (!WebInspector.visible) 435 return; 436 437 if (typeof startTime === "number" && !isNaN(this._currentTime)) 405 438 this._currentTime = startTime; 406 else if (!isNaN(this._currentTime)){439 else { 407 440 // This happens when you stop and later restart recording. 408 441 // COMPATIBILITY (iOS 9): Timeline.recordingStarted events did not include a timestamp. -
trunk/Source/WebKit2/ChangeLog
r201168 r201171 1 2016-05-19 Brian Burg <bburg@apple.com> 2 3 Web Inspector: timelines should not update via requestAnimationFrame unless Web Inspector is visible 4 https://bugs.webkit.org/show_bug.cgi?id=157897 5 <rdar://problem/26330802> 6 7 Reviewed by Timothy Hatcher. 8 9 The UIProcess needs to notify the Inspector frontend when it is truly visible. 10 The frontend can't use document.visibilityState because it doesn't seem to work 11 if the inspector frontend's WKWebView is created but not attached to a window. 12 13 * UIProcess/WebInspectorProxy.cpp: 14 (WebKit::WebInspectorProxy::open): 15 (WebKit::WebInspectorProxy::didClose): 16 Send visibility updates to the inspector process when the inspector becomes 17 "visible" or "not visible". It becomes visible if it is attached to the 18 inspected page's window, or gets its own native window. 19 20 * WebProcess/WebPage/WebInspectorUI.cpp: 21 (WebKit::WebInspectorUI::frontendLoaded): 22 (WebKit::WebInspectorUI::setDockingUnavailable): 23 (WebKit::WebInspectorUI::setIsVisible): 24 Call InspectorFrontendAPI.updateVisibilityState to let the frontend know. 25 26 * WebProcess/WebPage/WebInspectorUI.h: 27 * WebProcess/WebPage/WebInspectorUI.messages.in: 28 Add new message. 29 1 30 2016-05-19 Brian Burg <bburg@apple.com> 2 31 -
trunk/Source/WebKit2/UIProcess/WebInspectorProxy.cpp
r201101 r201171 582 582 583 583 m_isVisible = true; 584 m_inspectorPage->process().send(Messages::WebInspectorUI::SetIsVisible(m_isVisible), m_inspectorPage->pageID()); 584 585 585 586 platformOpen(); … … 590 591 if (!m_inspectorPage) 591 592 return; 592 593 m_inspectorPage->process().removeMessageReceiver(Messages::WebInspectorProxy::messageReceiverName(), m_inspectedPage->pageID());594 593 595 594 m_isVisible = false; … … 597 596 m_showMessageSent = false; 598 597 m_ignoreFirstBringToFront = false; 598 599 m_inspectorPage->process().send(Messages::WebInspectorUI::SetIsVisible(m_isVisible), m_inspectorPage->pageID()); 600 m_inspectorPage->process().removeMessageReceiver(Messages::WebInspectorProxy::messageReceiverName(), m_inspectedPage->pageID()); 599 601 600 602 if (m_isAttached) -
trunk/Source/WebKit2/WebProcess/WebPage/WebInspectorUI.cpp
r201101 r201171 96 96 setDockingUnavailable(m_dockingUnavailable); 97 97 setDockSide(m_dockSide); 98 setIsVisible(m_isVisible); 98 99 99 100 WebProcess::singleton().parentProcessConnection()->send(Messages::WebInspectorProxy::FrontendLoaded(), m_inspectedPageIdentifier); … … 179 180 void WebInspectorUI::setDockingUnavailable(bool unavailable) 180 181 { 182 m_dockingUnavailable = unavailable; 183 181 184 m_frontendAPIDispatcher.dispatchCommand(ASCIILiteral("setDockingUnavailable"), unavailable); 182 m_dockingUnavailable = unavailable; 185 } 186 187 void WebInspectorUI::setIsVisible(bool visible) 188 { 189 m_isVisible = visible; 190 191 m_frontendAPIDispatcher.dispatchCommand(ASCIILiteral("setIsVisible"), visible); 183 192 } 184 193 -
trunk/Source/WebKit2/WebProcess/WebPage/WebInspectorUI.h
r201101 r201171 75 75 void setDockingUnavailable(bool); 76 76 77 void setIsVisible(bool); 78 77 79 void didSave(const String& url); 78 80 void didAppend(const String& url); … … 127 129 bool m_underTest { false }; 128 130 bool m_dockingUnavailable { false }; 131 bool m_isVisible { false }; 129 132 DockSide m_dockSide { DockSide::Undocked }; 130 133 unsigned m_inspectionLevel { 1 }; -
trunk/Source/WebKit2/WebProcess/WebPage/WebInspectorUI.messages.in
r201101 r201171 28 28 Detached() 29 29 SetDockingUnavailable(bool unavailable) 30 SetIsVisible(bool visible) 30 31 31 32 ShowConsole()
Note:
See TracChangeset
for help on using the changeset viewer.