Source/WebCore/ChangeLog

 12013-03-29 Andrey Kosyakov <caseq@chromium.org>
 2
 3 Web Inspector: display the number of dirty render objects in Layout timeline event
 4 https://bugs.webkit.org/show_bug.cgi?id=95331
 5
 6 Reviewed by NOBODY (OOPS!).
 7
 8 Count the render objects that need layout in InspectorTimelineAgent::willLayout()
 9 and display the number in popover over Layout record in Timeline panel.
 10
 11 * English.lproj/localizedStrings.js:
 12 * inspector/InspectorTimelineAgent.cpp:
 13 (WebCore::InspectorTimelineAgent::willLayout):
 14 (WebCore::InspectorTimelineAgent::didLayout):
 15 * inspector/TimelineRecordFactory.cpp:
 16 (WebCore):
 17 (WebCore::TimelineRecordFactory::createLayoutData):
 18 (WebCore::TimelineRecordFactory::appendLayoutRoot):
 19 * inspector/TimelineRecordFactory.h:
 20 (TimelineRecordFactory):
 21 * inspector/front-end/TimelinePresentationModel.js:
 22 (WebInspector.TimelinePresentationModel.Record.prototype._generatePopupContentWithImagePreview):
 23
1242013-03-22 Andrey Kosyakov <caseq@chromium.org>
225
326 Web Inspector: timeline paint rectangles are off for transformed layers

Source/WebCore/English.lproj/localizedStrings.js

@@localizedStrings["It is recommended to restart inspector after making these chan
918918localizedStrings["Limit number of captured JS stack frames"] = "Limit number of captured JS stack frames";
919919localizedStrings["Frames to capture"] = "Frames to capture";
920920localizedStrings["Select node to inspect"] = "Select node to inspect";
 921localizedStrings["Nodes that need layout"] = "Nodes that need layout";
 922localizedStrings["Layout tree size"] = "Layout tree size";

Source/WebCore/inspector/InspectorTimelineAgent.cpp

@@void InspectorTimelineAgent::didInvalidateLayout(Frame* frame)
263263
264264void InspectorTimelineAgent::willLayout(Frame* frame)
265265{
266  pushCurrentRecord(InspectorObject::create(), TimelineRecordType::Layout, true, frame);
 266 RenderObject* root = frame->view()->layoutRoot();
 267 if (!root)
 268 root = frame->document()->renderer();
 269 unsigned dirtyObjects = 0, totalObjects = 0;
 270 for (RenderObject* o = root; o; o = o->nextInPreOrder(root)) {
 271 ++totalObjects;
 272 if (o->needsLayout())
 273 ++dirtyObjects;
 274 }
 275 pushCurrentRecord(TimelineRecordFactory::createLayoutData(dirtyObjects, totalObjects), TimelineRecordType::Layout, true, frame);
267276}
268277
269278void InspectorTimelineAgent::didLayout(RenderObject* root)

@@void InspectorTimelineAgent::didLayout(RenderObject* root)
275284 Vector<FloatQuad> quads;
276285 root->absoluteQuads(quads);
277286 if (quads.size() >= 1)
278  entry.data = TimelineRecordFactory::createLayoutData(quads[0]);
 287 TimelineRecordFactory::appendLayoutRoot(entry.data.get(), quads[0]);
279288 else
280289 ASSERT_NOT_REACHED();
281290 didCompleteCurrentRecord(TimelineRecordType::Layout);

Source/WebCore/inspector/TimelineRecordFactory.cpp

@@PassRefPtr<InspectorObject> TimelineRecordFactory::createReceiveResourceData(con
178178 data->setNumber("encodedDataLength", length);
179179 return data.release();
180180}
 181
 182PassRefPtr<InspectorObject> TimelineRecordFactory::createLayoutData(unsigned dirtyObjects, unsigned totalObjects)
 183{
 184 RefPtr<InspectorObject> data = InspectorObject::create();
 185 data->setNumber("dirtyObjects", dirtyObjects);
 186 data->setNumber("totalObjects", totalObjects);
 187 return data.release();
 188}
181189
182190PassRefPtr<InspectorObject> TimelineRecordFactory::createDecodeImageData(const String& imageType)
183191{

@@PassRefPtr<InspectorObject> TimelineRecordFactory::createPaintData(const FloatQu
235243 return data.release();
236244}
237245
238 PassRefPtr<InspectorObject> TimelineRecordFactory::createLayoutData(const FloatQuad& quad)
 246void TimelineRecordFactory::appendLayoutRoot(InspectorObject* data, const FloatQuad& quad)
239247{
240  RefPtr<InspectorObject> data = InspectorObject::create();
241248 data->setArray("root", createQuad(quad));
242  return data.release();
243249}
244250
245251} // namespace WebCore

Source/WebCore/inspector/TimelineRecordFactory.h

@@namespace WebCore {
8080
8181 static PassRefPtr<InspectorObject> createResourceFinishData(const String& requestId, bool didFail, double finishTime);
8282
83  static void addRectData(InspectorObject*, const LayoutRect&);
 83 static PassRefPtr<InspectorObject> createLayoutData(unsigned dirtyObjects, unsigned totalObjects);
 84
 85 static PassRefPtr<InspectorObject> createPaintData(const LayoutRect&);
8486
8587 static PassRefPtr<InspectorObject> createDecodeImageData(const String& imageType);
8688

@@namespace WebCore {
9496
9597 static PassRefPtr<InspectorObject> createPaintData(const FloatQuad&);
9698
97  static PassRefPtr<InspectorObject> createLayoutData(const FloatQuad&);
 99 static void appendLayoutRoot(InspectorObject* data, const FloatQuad&);
98100
99101#if ENABLE(WEB_SOCKETS)
100102 static inline PassRefPtr<InspectorObject> createWebSocketCreateData(unsigned long identifier, const KURL& url, const String& protocol)

Source/WebCore/inspector/front-end/TimelinePresentationModel.js

@@WebInspector.TimelinePresentationModel.Record.prototype = {
10451045 callStackLabel = WebInspector.UIString("Styles recalculation forced");
10461046 break;
10471047 case recordTypes.Layout:
 1048 if (this.data["dirtyObjects"])
 1049 contentHelper.appendTextRow(WebInspector.UIString("Nodes that need layout"), this.data["dirtyObjects"]);
 1050 if (this.data["totalObjects"])
 1051 contentHelper.appendTextRow(WebInspector.UIString("Layout tree size"), this.data["totalObjects"]);
10481052 callSiteStackTraceLabel = WebInspector.UIString("Layout invalidated");
10491053 if (this.stackTrace) {
10501054 callStackLabel = WebInspector.UIString("Layout forced");

LayoutTests/ChangeLog

 12012-03-29 Andrey Kosyakov <caseq@chromium.org>
 2
 3 Web Inspector: display the number of dirty render objects in Layout timeline event
 4 https://bugs.webkit.org/show_bug.cgi?id=95331
 5
 6 Reviewed by NOBODY (OOPS!).
 7
 8 * inspector/timeline/timeline-layout-expected.txt: rebaselined to include new properties;
 9
1102013-03-22 Andrey Kosyakov <caseq@chromium.org>
211
312 Web Inspector: timeline paint rectangles are off for transformed layers

LayoutTests/inspector/timeline/timeline-layout-expected.txt

11Tests the Timeline API instrumentation of a Layout event
22
3 Test data
 3text
 4text
 5text
 6text
 7text
48Layout Properties:
59{
610 children : <object>
711 counters : <object>
812 data : {
 13 dirtyObjects : 3
914 root : <object>
 15 totalObjects : 8
 16 }
 17 endTime : <number>
 18 frameId : <string>
 19 stackTrace : <object>
 20 startTime : <number>
 21 type : "Layout"
 22 usedHeapSize : <number>
 23}
 24Layout Properties:
 25{
 26 children : <object>
 27 counters : <object>
 28 data : {
 29 dirtyObjects : 2
 30 root : <object>
 31 totalObjects : 11
1032 }
1133 endTime : <number>
1234 frameId : <string>

LayoutTests/inspector/timeline/timeline-layout.html

22<head>
33<script src="../../http/tests/inspector/inspector-test.js"></script>
44<script src="../../http/tests/inspector/timeline-test.js"></script>
 5<style>
 6.relayout-boundary {
 7 overflow: hidden;
 8 width: 100px;
 9 height: 100px;
 10}
 11</style>
512<script>
613
 14function invalidateAndForceLayout(element)
 15{
 16 element.style.marginTop = "10px";
 17 var unused = element.offsetHeight;
 18}
 19
720function performActions()
821{
9  var element = document.createElement("div");
10  element.innerHTML = "Test data";
11  document.body.appendChild(element);
12  // Force layout.
13  var foo = element.offsetHeight;
 22 invalidateAndForceLayout(document.getElementById("invalidate1"));
 23 invalidateAndForceLayout(document.getElementById("invalidate2"));
1424}
1525
1626function test()

@@function test()
2535<p>
2636Tests the Timeline API instrumentation of a Layout event
2737</p>
 38<div class="relayout-boundary">
 39 <div>text</div>
 40 <div></div>
 41 <div>
 42 <div id="invalidate1"><div>text</div></div>
 43 </div>
 44</div>
 45<div class="relayout-boundary">
 46 <div></div>
 47 <div>text</div>
 48 <div id="invalidate2"><div>text</div></div>
 49 <div></div>
 50 <div></div>
 51 <div>text</div>
 52</div>
2853
2954</body>
3055</html>