browser/base/content/test/general/browser_windowopen_reflows.js

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

michael@0 1 /* Any copyright is dedicated to the Public Domain.
michael@0 2 http://creativecommons.org/publicdomain/zero/1.0/ */
michael@0 3
michael@0 4 "use strict";
michael@0 5
michael@0 6 const EXPECTED_REFLOWS = [
michael@0 7 // handleEvent flushes layout to get the tabstrip width after a resize.
michael@0 8 "handleEvent@chrome://browser/content/tabbrowser.xml|",
michael@0 9
michael@0 10 // Loading a tab causes a reflow.
michael@0 11 "loadTabs@chrome://browser/content/tabbrowser.xml|" +
michael@0 12 "loadOneOrMoreURIs@chrome://browser/content/browser.js|" +
michael@0 13 "gBrowserInit._delayedStartup@chrome://browser/content/browser.js|",
michael@0 14
michael@0 15 // Selecting the address bar causes a reflow.
michael@0 16 "select@chrome://global/content/bindings/textbox.xml|" +
michael@0 17 "focusAndSelectUrlBar@chrome://browser/content/browser.js|" +
michael@0 18 "gBrowserInit._delayedStartup@chrome://browser/content/browser.js|",
michael@0 19
michael@0 20 // Focusing the content area causes a reflow.
michael@0 21 "gBrowserInit._delayedStartup@chrome://browser/content/browser.js|",
michael@0 22
michael@0 23 // Sometimes sessionstore collects data during this test, which causes a sync reflow
michael@0 24 // (https://bugzilla.mozilla.org/show_bug.cgi?id=892154 will fix this)
michael@0 25 "ssi_getWindowDimension@resource:///modules/sessionstore/SessionStore.jsm",
michael@0 26 ];
michael@0 27
michael@0 28 if (Services.appinfo.OS == "WINNT" || Services.appinfo.OS == "Darwin") {
michael@0 29 // TabsInTitlebar._update causes a reflow on OS X and Windows trying to do calculations
michael@0 30 // since layout info is already dirty. This doesn't seem to happen before
michael@0 31 // MozAfterPaint on Linux.
michael@0 32 EXPECTED_REFLOWS.push("rect@chrome://browser/content/browser.js|" +
michael@0 33 "TabsInTitlebar._update@chrome://browser/content/browser.js|" +
michael@0 34 "updateAppearance@chrome://browser/content/browser.js|" +
michael@0 35 "handleEvent@chrome://browser/content/tabbrowser.xml|");
michael@0 36 }
michael@0 37
michael@0 38 if (Services.appinfo.OS == "Darwin") {
michael@0 39 // _onOverflow causes a reflow getting widths.
michael@0 40 EXPECTED_REFLOWS.push("OverflowableToolbar.prototype._onOverflow@resource:///modules/CustomizableUI.jsm|" +
michael@0 41 "OverflowableToolbar.prototype.init@resource:///modules/CustomizableUI.jsm|" +
michael@0 42 "OverflowableToolbar.prototype.observe@resource:///modules/CustomizableUI.jsm|" +
michael@0 43 "gBrowserInit._delayedStartup@chrome://browser/content/browser.js|");
michael@0 44 // Same as above since in packaged builds there are no function names and the resource URI includes "app"
michael@0 45 EXPECTED_REFLOWS.push("@resource://app/modules/CustomizableUI.jsm|" +
michael@0 46 "@resource://app/modules/CustomizableUI.jsm|" +
michael@0 47 "@resource://app/modules/CustomizableUI.jsm|" +
michael@0 48 "gBrowserInit._delayedStartup@chrome://browser/content/browser.js|");
michael@0 49 }
michael@0 50
michael@0 51 /*
michael@0 52 * This test ensures that there are no unexpected
michael@0 53 * uninterruptible reflows when opening new windows.
michael@0 54 */
michael@0 55 function test() {
michael@0 56 waitForExplicitFinish();
michael@0 57
michael@0 58 // Add a reflow observer and open a new window
michael@0 59 let win = OpenBrowserWindow();
michael@0 60 let docShell = win.QueryInterface(Ci.nsIInterfaceRequestor)
michael@0 61 .getInterface(Ci.nsIWebNavigation)
michael@0 62 .QueryInterface(Ci.nsIDocShell);
michael@0 63 docShell.addWeakReflowObserver(observer);
michael@0 64
michael@0 65 // Wait until the mozafterpaint event occurs.
michael@0 66 waitForMozAfterPaint(win, function paintListener() {
michael@0 67 // Remove reflow observer and clean up.
michael@0 68 docShell.removeWeakReflowObserver(observer);
michael@0 69 win.close();
michael@0 70
michael@0 71 finish();
michael@0 72 });
michael@0 73 }
michael@0 74
michael@0 75 let observer = {
michael@0 76 reflow: function (start, end) {
michael@0 77 // Gather information about the current code path.
michael@0 78 let stack = new Error().stack;
michael@0 79 let path = stack.split("\n").slice(1).map(line => {
michael@0 80 return line.replace(/:\d+:\d+$/, "");
michael@0 81 }).join("|");
michael@0 82 let pathWithLineNumbers = (new Error().stack).split("\n").slice(1).join("|");
michael@0 83
michael@0 84 // Stack trace is empty. Reflow was triggered by native code.
michael@0 85 if (path === "") {
michael@0 86 return;
michael@0 87 }
michael@0 88
michael@0 89 // Check if this is an expected reflow.
michael@0 90 for (let expectedStack of EXPECTED_REFLOWS) {
michael@0 91 if (path.startsWith(expectedStack) ||
michael@0 92 // Accept an empty function name for gBrowserInit._delayedStartup or TabsInTitlebar._update to workaround bug 906578.
michael@0 93 path.startsWith(expectedStack.replace(/(^|\|)(gBrowserInit\._delayedStartup|TabsInTitlebar\._update)@/, "$1@"))) {
michael@0 94 ok(true, "expected uninterruptible reflow '" + expectedStack + "'");
michael@0 95 return;
michael@0 96 }
michael@0 97 }
michael@0 98
michael@0 99 ok(false, "unexpected uninterruptible reflow '" + pathWithLineNumbers + "'");
michael@0 100 },
michael@0 101
michael@0 102 reflowInterruptible: function (start, end) {
michael@0 103 // We're not interested in interruptible reflows.
michael@0 104 },
michael@0 105
michael@0 106 QueryInterface: XPCOMUtils.generateQI([Ci.nsIReflowObserver,
michael@0 107 Ci.nsISupportsWeakReference])
michael@0 108 };
michael@0 109
michael@0 110 function waitForMozAfterPaint(win, callback) {
michael@0 111 win.addEventListener("MozAfterPaint", function onEnd(event) {
michael@0 112 if (event.target != win)
michael@0 113 return;
michael@0 114 win.removeEventListener("MozAfterPaint", onEnd);
michael@0 115 executeSoon(callback);
michael@0 116 });
michael@0 117 }

mercurial