Bug 663778 - Changes to tests for box model highlighter r=jwalker
☠☠ backed out by 583b3de7f71a ☠ ☠
authorMichael Ratcliffe <mratcliffe@mozilla.com>
Wed, 12 Mar 2014 14:01:31 +0000
changeset 191694 b0b74401e6140002fb08e0fa4f5d6bd1d5c576f6
parent 191693 df5255cffbfae3bfa642aad3cb6ac0777972c4dc
child 191695 cbd200206f9b9ee97b7a38ad3deea33b4b68e7ad
push id474
push userasasaki@mozilla.com
push dateMon, 02 Jun 2014 21:01:02 +0000
treeherdermozilla-release@967f4cf1b31c [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersjwalker
bugs663778
milestone30.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 663778 - Changes to tests for box model highlighter r=jwalker
browser/devtools/debugger/test/browser_dbg_variables-view-frame-with.js
browser/devtools/inspector/test/browser_inspector_basic_highlighter.js
browser/devtools/inspector/test/browser_inspector_breadcrumbs.js
browser/devtools/inspector/test/browser_inspector_bug_674871.js
browser/devtools/inspector/test/browser_inspector_bug_699308_iframe_navigation.js
browser/devtools/inspector/test/browser_inspector_highlighter.js
browser/devtools/inspector/test/browser_inspector_iframeTest.js
browser/devtools/inspector/test/browser_inspector_invalidate.js
browser/devtools/inspector/test/browser_inspector_scrolling.js
browser/devtools/inspector/test/browser_inspector_sidebarstate.js
browser/devtools/inspector/test/head.js
browser/devtools/markupview/test/browser_inspector_markup_navigation.js
browser/devtools/markupview/test/head.js
browser/devtools/scratchpad/test/browser_scratchpad_revert_to_saved.js
browser/devtools/webconsole/test/browser_console_variables_view_highlighter.js
browser/devtools/webconsole/test/browser_webconsole_autocomplete_in_debugger_stackframe.js
browser/devtools/webconsole/test/browser_webconsole_bug_585991_autocomplete_keys.js
browser/devtools/webconsole/test/browser_webconsole_bug_651501_document_body_autocomplete.js
browser/devtools/webconsole/test/browser_webconsole_output_01.js
browser/devtools/webconsole/test/browser_webconsole_output_03.js
browser/devtools/webconsole/test/browser_webconsole_view_source.js
browser/devtools/webconsole/test/head.js
--- a/browser/devtools/debugger/test/browser_dbg_variables-view-frame-with.js
+++ b/browser/devtools/debugger/test/browser_dbg_variables-view-frame-with.js
@@ -202,9 +202,10 @@ function testFunctionScope() {
     "Should have the right token class for 'foo'.");
 }
 
 registerCleanupFunction(function() {
   gTab = null;
   gDebuggee = null;
   gPanel = null;
   gDebugger = null;
+  gVariables = null;
 });
--- a/browser/devtools/inspector/test/browser_inspector_basic_highlighter.js
+++ b/browser/devtools/inspector/test/browser_inspector_basic_highlighter.js
@@ -19,65 +19,44 @@ function test() {
   }, true);
 
   content.location = "data:text/html;charset=utf-8,<h1>foo</h1><span>bar</span>";
 
   function setupTest() {
     openInspector((aInspector, aToolbox) => {
       toolbox = aToolbox;
       inspector = aInspector;
-      inspector.selection.setNode(doc.querySelector("h2"), null);
-      inspector.once("inspector-updated", runTests);
+      inspector.selection.setNode(doc.querySelector("span"), "test");
+      inspector.toolbox.once("highlighter-ready", runTests);
     });
   }
 
   function runTests() {
     Task.spawn(function() {
       yield hoverH1InMarkupView();
       yield assertH1Highlighted();
-      yield mouseLeaveMarkupView();
-      yield assertNoNodeHighlighted();
 
       finishUp();
     }).then(null, Cu.reportError);
   }
 
   function hoverH1InMarkupView() {
     let deferred = promise.defer();
+    let container = getContainerForRawNode(inspector.markup, doc.querySelector("h1"));
 
-    let container = getContainerForRawNode(inspector.markup, doc.querySelector("h1"));
-    EventUtils.synthesizeMouse(container.tagLine, 2, 2, {type: "mousemove"},
-      inspector.markup.doc.defaultView);
-    inspector.toolbox.once("node-highlight", deferred.resolve);
+    inspector.toolbox.once("highlighter-ready", deferred.resolve);
+    EventUtils.synthesizeMouseAtCenter(container.tagLine, {type: "mousemove"},
+                                       inspector.markup.doc.defaultView);
 
     return deferred.promise;
   }
 
   function assertH1Highlighted() {
     ok(isHighlighting(), "The highlighter is shown on a markup container hover");
     is(getHighlitNode(), doc.querySelector("h1"), "The highlighter highlights the right node");
-    return promise.resolve();
-  }
-
-  function mouseLeaveMarkupView() {
-    let deferred = promise.defer();
-
-    // Find another element to mouseover over in order to leave the markup-view
-    let btn = toolbox.doc.querySelector(".toolbox-dock-button");
-
-    EventUtils.synthesizeMouse(btn, 2, 2, {type: "mousemove"},
-      toolbox.doc.defaultView);
-    executeSoon(deferred.resolve);
-
-    return deferred.promise;
-  }
-
-  function assertNoNodeHighlighted() {
-    ok(!isHighlighting(), "After the mouse left the markup view, the highlighter is hidden");
-    return promise.resolve();
   }
 
   function finishUp() {
     inspector = doc = toolbox = null;
     gBrowser.removeCurrentTab();
     finish();
   }
 }
--- a/browser/devtools/inspector/test/browser_inspector_breadcrumbs.js
+++ b/browser/devtools/inspector/test/browser_inspector_breadcrumbs.js
@@ -86,13 +86,13 @@ function test()
 
     let checkedButton = container.querySelector("button[checked]");
     let labelId = checkedButton.querySelector(".breadcrumbs-widget-item-id");
     let id = inspector.selection.node.id;
     is(labelId.textContent, "#" + id, "Node " + cursor + ": selection matches");
   }
 
   function finishUp() {
-    doc = nodes = null;
+    doc = nodes = inspector = null;
     gBrowser.removeCurrentTab();
     finish();
   }
 }
--- a/browser/devtools/inspector/test/browser_inspector_bug_674871.js
+++ b/browser/devtools/inspector/test/browser_inspector_bug_674871.js
@@ -59,36 +59,40 @@ function test()
   {
     inspector.toolbox.highlighterUtils.startPicker().then(() => {
       moveMouseOver(iframeNode, 1, 1, isTheIframeHighlighted);
     });
   }
 
   function isTheIframeHighlighted()
   {
-    let outlineRect = getHighlighterOutlineRect();
-    let iframeRect = iframeNode.getBoundingClientRect();
-    for (let dim of ["width", "height", "top", "left"]) {
-      is(Math.floor(outlineRect[dim]), Math.floor(iframeRect[dim]),
-         "Outline dimension is correct " + outlineRect[dim]);
-    }
+    let {p1, p2, p3, p4} = getBoxModelStatus().border.points;
+    let {top, right, bottom, left} = iframeNode.getBoundingClientRect();
+
+    is(top, p1.y, "iframeRect.top === boxModelStatus.p1.y");
+    is(top, p2.y, "iframeRect.top === boxModelStatus.p2.y");
+    is(right, p2.x, "iframeRect.right === boxModelStatus.p2.x");
+    is(right, p3.x, "iframeRect.right === boxModelStatus.p3.x");
+    is(bottom, p3.y, "iframeRect.bottom === boxModelStatus.p3.y");
+    is(bottom, p4.y, "iframeRect.bottom === boxModelStatus.p4.y");
+    is(left, p1.x, "iframeRect.left === boxModelStatus.p1.x");
+    is(left, p4.x, "iframeRect.left === boxModelStatus.p4.x");
 
     iframeNode.style.marginBottom = doc.defaultView.innerHeight + "px";
     doc.defaultView.scrollBy(0, 40);
 
     moveMouseOver(iframeNode, 40, 40, isTheIframeContentHighlighted);
   }
 
   function isTheIframeContentHighlighted()
   {
     is(getHighlitNode(), iframeBodyNode, "highlighter shows the right node");
 
-    // 184 == 200 + 11(border) + 13(padding) - 40(scroll)
-    let outlineRect = getHighlighterOutlineRect();
-    is(outlineRect.height, 184, "highlighter height");
+    let outlineRect = getSimpleBorderRect();
+    is(outlineRect.height, 200, "highlighter height");
 
     inspector.toolbox.highlighterUtils.stopPicker().then(() => {
       let target = TargetFactory.forTab(gBrowser.selectedTab);
       gDevTools.closeToolbox(target);
       finishUp();
     });
   }
 
--- a/browser/devtools/inspector/test/browser_inspector_bug_699308_iframe_navigation.js
+++ b/browser/devtools/inspector/test/browser_inspector_bug_699308_iframe_navigation.js
@@ -13,49 +13,44 @@ function test() {
       runInspectorTests();
     });
   }
 
   function showHighlighter(cb) {
     inspector.toolbox.highlighterUtils.startPicker().then(() => {
       EventUtils.synthesizeMouse(content.document.body, 1, 1,
         {type: "mousemove"}, content);
-      inspector.toolbox.once("picker-node-hovered", () => {
-        executeSoon(() => {
-          getHighlighterOutline().setAttribute("disable-transitions", "true");
-          cb();
-        });
-      });
+      inspector.toolbox.once("highlighter-ready", cb);
     });
   }
 
   function runInspectorTests() {
     iframe = content.document.querySelector("iframe");
     ok(iframe, "found the iframe element");
 
     showHighlighter(() => {
       ok(isHighlighting(), "Inspector is highlighting");
 
       iframe.addEventListener("load", onIframeLoad, false);
-
-      executeSoon(function() {
+      executeSoon(() => {
         iframe.contentWindow.location = "javascript:location.reload()";
       });
     });
   }
 
   function onIframeLoad() {
     if (++iframeLoads != 2) {
       executeSoon(function() {
         iframe.contentWindow.location = "javascript:location.reload()";
       });
       return;
     }
 
     iframe.removeEventListener("load", onIframeLoad, false);
+    info("Finished reloading iframe and inspector updated");
 
     ok(isHighlighting(), "Inspector is highlighting after iframe nav");
 
     checksAfterLoads = true;
 
     finishTest();
   }
 
--- a/browser/devtools/inspector/test/browser_inspector_highlighter.js
+++ b/browser/devtools/inspector/test/browser_inspector_highlighter.js
@@ -52,64 +52,59 @@ function createDocument() {
     inspector.selection.setNode(div, null);
     inspector.once("inspector-updated", () => {
       inspector.toolbox.highlighterUtils.startPicker().then(testMouseOverH1Highlights);
     });
   });
 }
 
 function testMouseOverH1Highlights() {
-  inspector.toolbox.once("picker-node-hovered", () => {
+  inspector.toolbox.once("highlighter-ready", () => {
     ok(isHighlighting(), "Highlighter is shown");
     is(getHighlitNode(), h1, "Highlighter's outline correspond to the selected node");
-    testOutlineDimensions();
+    testBoxModelDimensions();
   });
 
   EventUtils.synthesizeMouse(h1, 2, 2, {type: "mousemove"}, content);
 }
 
-function testOutlineDimensions() {
+function testBoxModelDimensions() {
   let h1Dims = h1.getBoundingClientRect();
-  let h1Width = h1Dims.width;
-  let h1Height = h1Dims.height;
+  let h1Width = Math.ceil(h1Dims.width);
+  let h1Height = Math.ceil(h1Dims.height);
 
-  let outlineDims = getHighlighterOutlineRect();
-  let outlineWidth = outlineDims.width;
-  let outlineHeight = outlineDims.height;
+  let outlineDims = getSimpleBorderRect();
+  let outlineWidth = Math.ceil(outlineDims.width);
+  let outlineHeight = Math.ceil(outlineDims.height);
 
   // Disabled due to bug 716245
   is(outlineWidth, h1Width, "outline width matches dimensions of element (no zoom)");
   is(outlineHeight, h1Height, "outline height matches dimensions of element (no zoom)");
 
   // zoom the page by a factor of 2
   let contentViewer = gBrowser.selectedBrowser.docShell.contentViewer
                              .QueryInterface(Ci.nsIMarkupDocumentViewer);
   contentViewer.fullZoom = 2;
 
-  // We wait at least 500ms to make sure the highlighter is not "mutting" the
-  // resize event
-
-  window.setTimeout(function() {
-    // simulate the zoomed dimensions of the div element
-    let h1Dims = h1.getBoundingClientRect();
-    // There seems to be some very minor differences in the floats, so let's
-    // floor the values
-    let h1Width = Math.floor(h1Dims.width * contentViewer.fullZoom);
-    let h1Height = Math.floor(h1Dims.height * contentViewer.fullZoom);
+  // simulate the zoomed dimensions of the div element
+  let h1Dims = h1.getBoundingClientRect();
+  // There seems to be some very minor differences in the floats, so let's
+  // floor the values
+  let h1Width = Math.floor(h1Dims.width * contentViewer.fullZoom);
+  let h1Height = Math.floor(h1Dims.height * contentViewer.fullZoom);
 
-    let outlineDims = getHighlighterOutlineRect();
-    let outlineWidth = Math.floor(outlineDims.width);
-    let outlineHeight = Math.floor(outlineDims.height);
+  let outlineDims = getSimpleBorderRect();
+  let outlineWidth = Math.floor(outlineDims.width);
+  let outlineHeight = Math.floor(outlineDims.height);
 
-    // Disabled due to bug 716245
-    is(outlineWidth, h1Width, "outline width matches dimensions of element (zoomed)");
-    is(outlineHeight, h1Height, "outline height matches dimensions of element (zoomed)");
+  is(outlineWidth, h1Width, "outline width matches dimensions of element (zoomed)");
 
-    executeSoon(finishUp);
-  }, 500);
+  is(outlineHeight, h1Height, "outline height matches dimensions of element (zoomed)");
+
+  executeSoon(finishUp);
 }
 
 function finishUp() {
   inspector.toolbox.highlighterUtils.stopPicker().then(() => {
     doc = h1 = inspector = null;
     let target = TargetFactory.forTab(gBrowser.selectedTab);
     gDevTools.closeToolbox(target);
     gBrowser.removeCurrentTab();
--- a/browser/devtools/inspector/test/browser_inspector_iframeTest.js
+++ b/browser/devtools/inspector/test/browser_inspector_iframeTest.js
@@ -30,51 +30,50 @@ function createDocument() {
 
       div2 = iframe2.contentDocument.createElement('div');
       div2.textContent = 'nested div';
       iframe2.contentDocument.body.appendChild(div2);
 
       // Open the inspector, start the picker mode, and start the tests
       openInspector(aInspector => {
         inspector = aInspector;
-        inspector.toolbox.highlighterUtils.startPicker().then(runTests);
+        inspector.once("inspector-updated", () => {
+          inspector.toolbox.highlighterUtils.startPicker().then(runTests);
+        });
       });
     }, false);
 
     iframe2.src = 'data:text/html,nested iframe';
     iframe1.contentDocument.body.appendChild(iframe2);
   }, false);
 
   iframe1.src = 'data:text/html,little iframe';
   doc.body.appendChild(iframe1);
 }
 
 function moveMouseOver(aElement, cb) {
-  inspector.toolbox.once("picker-node-hovered", () => {
-    executeSoon(cb);
-  });
+  inspector.toolbox.once("picker-node-hovered", cb);
   EventUtils.synthesizeMouseAtCenter(aElement, {type: "mousemove"},
     aElement.ownerDocument.defaultView);
 }
 
 function runTests() {
   testDiv1Highlighter();
 }
 
 function testDiv1Highlighter() {
   moveMouseOver(div1, () => {
-    getHighlighterOutline().setAttribute("disable-transitions", "true");
-    is(getHighlitNode(), div1, "highlighter matches selection");
+    is(getHighlitNode(), div1, "highlighter matches selection of div1");
     testDiv2Highlighter();
   });
 }
 
 function testDiv2Highlighter() {
   moveMouseOver(div2, () => {
-    is(getHighlitNode(), div2, "highlighter matches selection");
+    is(getHighlitNode(), div2, "highlighter matches selection of div2");
     selectRoot();
   });
 }
 
 function selectRoot() {
   // Select the root document element to clear the breadcrumbs.
   inspector.selection.setNode(doc.documentElement, null);
   inspector.once("inspector-updated", selectIframe);
--- a/browser/devtools/inspector/test/browser_inspector_invalidate.js
+++ b/browser/devtools/inspector/test/browser_inspector_invalidate.js
@@ -8,34 +8,34 @@ function test() {
 
   function createDocument() {
     div = doc.createElement("div");
     div.setAttribute("style", "width: 100px; height: 100px; background:yellow;");
     doc.body.appendChild(div);
 
     openInspector(aInspector => {
       inspector = aInspector;
-      inspector.toolbox.highlighter.showBoxModel(getNodeFront(div)).then(runTest);
+      inspector.once("inspector-updated", () => {
+        inspector.toolbox.highlighter.showBoxModel(getNodeFront(div)).then(runTest);
+      });
     });
   }
 
   function runTest() {
-    let outline = getHighlighterOutline();
-    is(outline.style.width, "100px", "outline has the right width");
+    let rect = getSimpleBorderRect();
+    is(rect.width, 100, "outline has the right width");
 
     div.style.width = "200px";
-    function pollTest() {
-      if (outline.style.width == "100px") {
-        setTimeout(pollTest, 10);
-        return;
-      }
-      is(outline.style.width, "200px", "outline updated");
-      finishUp();
-    }
-    setTimeout(pollTest, 10);
+    inspector.toolbox.once("highlighter-ready", testRectWidth);
+  }
+
+  function testRectWidth() {
+    let rect = getSimpleBorderRect();
+    is(rect.width, 200, "outline updated");
+    finishUp();
   }
 
   function finishUp() {
     inspector.toolbox.highlighter.hideBoxModel().then(() => {
       doc = div = inspector = null;
       gBrowser.removeCurrentTab();
       finish();
     });
--- a/browser/devtools/inspector/test/browser_inspector_scrolling.js
+++ b/browser/devtools/inspector/test/browser_inspector_scrolling.js
@@ -28,44 +28,44 @@ function createDocument()
   iframe.src = "data:text/html,foo bar";
   doc.body.appendChild(iframe);
 }
 
 function inspectNode(aInspector)
 {
   inspector = aInspector;
 
-  inspector.once("inspector-updated", performScrollingTest);
-  executeSoon(function() {
-    inspector.selection.setNode(div, "");
-  });
+  let highlighter = inspector.toolbox.highlighter;
+  highlighter.showBoxModel(getNodeFront(div)).then(performScrollingTest);
 }
 
 function performScrollingTest()
 {
-  executeSoon(function() {
-    // FIXME: this will fail on retina displays. EventUtils will only scroll
-    // 25px down instead of 50.
-    EventUtils.synthesizeWheel(div, 10, 10,
-      { deltaY: 50.0, deltaMode: WheelEvent.DOM_DELTA_PIXEL },
-      iframe.contentWindow);
-  });
-
   gBrowser.selectedBrowser.addEventListener("scroll", function() {
     gBrowser.selectedBrowser.removeEventListener("scroll", arguments.callee,
       false);
+    let isRetina = devicePixelRatio === 2;
+    is(iframe.contentDocument.body.scrollTop,
+      isRetina ? 25 : 50, "inspected iframe scrolled");
 
-    is(iframe.contentDocument.body.scrollTop, 50, "inspected iframe scrolled");
+    finishUp();
+  }, false);
 
-    inspector = div = iframe = doc = null;
-    let target = TargetFactory.forTab(gBrowser.selectedTab);
-    gDevTools.closeToolbox(target);
-    gBrowser.removeCurrentTab();
-    finish();
-  }, false);
+  EventUtils.synthesizeWheel(div, 10, 10,
+    { deltaY: 50.0, deltaMode: WheelEvent.DOM_DELTA_PIXEL },
+    iframe.contentWindow);
+}
+
+function finishUp()
+{
+  inspector = div = iframe = doc = null;
+  let target = TargetFactory.forTab(gBrowser.selectedTab);
+  gDevTools.closeToolbox(target);
+  gBrowser.removeCurrentTab();
+  finish();
 }
 
 function test()
 {
   waitForExplicitFinish();
   gBrowser.selectedTab = gBrowser.addTab();
   gBrowser.selectedBrowser.addEventListener("load", function() {
     gBrowser.selectedBrowser.removeEventListener("load", arguments.callee, true);
--- a/browser/devtools/inspector/test/browser_inspector_sidebarstate.js
+++ b/browser/devtools/inspector/test/browser_inspector_sidebarstate.js
@@ -20,28 +20,29 @@ function inspectorRuleViewOpened()
 {
   is(inspector.sidebar.getCurrentTabID(), "ruleview", "Rule View is selected by default");
 
   // Select the computed view and turn off the inspector.
   inspector.sidebar.select("computedview");
 
   gDevTools.once("toolbox-destroyed", inspectorClosed);
   let target = TargetFactory.forTab(gBrowser.selectedTab);
-  gDevTools.getToolbox(target).destroy();
+  gDevTools.closeToolbox(target);
 }
 
 function inspectorClosed()
 {
   openInspector(function(panel) {
     inspector = panel;
+
     if (inspector.sidebar.getCurrentTabID()) {
-      // Default sidebar already selected.
+      info("Default sidebar already selected.")
       testNewDefaultTab();
     } else {
-      // Default sidebar still to be selected.
+      info("Default sidebar still to be selected, adding select listener.");
       inspector.sidebar.once("select", testNewDefaultTab);
     }
   });
 }
 
 function testNewDefaultTab()
 {
   is(inspector.sidebar.getCurrentTabID(), "computedview", "Computed view is selected by default.");
--- a/browser/devtools/inspector/test/head.js
+++ b/browser/devtools/inspector/test/head.js
@@ -28,16 +28,17 @@ let testDir = gTestPath.substr(0, gTestP
 Services.scriptloader.loadSubScript(testDir + "../../../commandline/test/helpers.js", this);
 
 SimpleTest.registerCleanupFunction(() => {
   console.error("Here we are\n");
   let {DebuggerServer} = Cu.import("resource://gre/modules/devtools/dbg-server.jsm", {});
   console.error("DebuggerServer open connections: " + Object.getOwnPropertyNames(DebuggerServer._connections).length);
 
   Services.prefs.clearUserPref("devtools.dump.emit");
+  Services.prefs.clearUserPref("devtools.inspector.activeSidebar");
 });
 
 function openInspector(callback)
 {
   let target = TargetFactory.forTab(gBrowser.selectedTab);
   gDevTools.showToolbox(target, "inspector").then(function(toolbox) {
     callback(toolbox.getCurrentPanel(), toolbox);
   }).then(null, console.error);
@@ -55,73 +56,128 @@ function getNodeFront(node)
   return inspector.walker.frontForRawNode(node);
 }
 
 function getHighlighter()
 {
   return gBrowser.selectedBrowser.parentNode.querySelector(".highlighter-container");
 }
 
-function getHighlighterOutline()
-{
-  let h = getHighlighter();
-  if (h) {
-    return h.querySelector(".highlighter-outline");
-  }
+function getSimpleBorderRect() {
+  let {p1, p2, p3, p4} = getBoxModelStatus().border.points;
+
+  return {
+    top: p1.y,
+    left: p1.x,
+    width: p2.x - p1.x,
+    height: p4.y - p1.y
+  };
+}
+
+function getBoxModelRoot() {
+  let highlighter = getHighlighter();
+  return highlighter.querySelector(".box-model-root");
 }
 
-function getHighlighterOutlineRect() {
-  let helper = new LayoutHelpers(window.content);
-  let outline = getHighlighterOutline();
+function getBoxModelStatus() {
+  let root = getBoxModelRoot();
+  let inspector = getActiveInspector();
+
+  return {
+    visible: !root.hasAttribute("hidden"),
+    currentNode: inspector.walker.currentNode,
+    margin: {
+      points: getPointsForRegion("margin"),
+      visible: isRegionHidden("margin")
+    },
+    border: {
+      points: getPointsForRegion("border"),
+      visible: isRegionHidden("border")
+    },
+    padding: {
+      points: getPointsForRegion("padding"),
+      visible: isRegionHidden("padding")
+    },
+    content: {
+      points: getPointsForRegion("content"),
+      visible: isRegionHidden("content")
+    },
+    guides: {
+      top: getGuideStatus("top"),
+      right: getGuideStatus("right"),
+      bottom: getGuideStatus("bottom"),
+      left: getGuideStatus("left")
+    }
+  };
+}
+
+function getGuideStatus(location) {
+  let root = getBoxModelRoot();
+  let guide = root.querySelector(".box-model-guide-" + location);
 
-  if (outline) {
-    let browserOffsetRect = helper.getDirtyRect(gBrowser.selectedBrowser);
-    let outlineRect = helper.getDirtyRect(outline);
-    outlineRect.top -= browserOffsetRect.top;
-    outlineRect.left -= browserOffsetRect.left;
+  return {
+    visible: !guide.hasAttribute("hidden"),
+    x1: guide.getAttribute("x1"),
+    y1: guide.getAttribute("y1"),
+    x2: guide.getAttribute("x2"),
+    y2: guide.getAttribute("y2")
+  };
+}
+
+function getPointsForRegion(region) {
+  let root = getBoxModelRoot();
+  let box = root.querySelector(".box-model-" + region);
+  let points = box.getAttribute("points").split(/[, ]/);
 
-    return outlineRect;
-  }
+  // We multiply each value by 1 to cast it into a number
+  return {
+    p1: {
+      x: parseFloat(points[0]),
+      y: parseFloat(points[1])
+    },
+    p2: {
+      x: parseFloat(points[2]),
+      y: parseFloat(points[3])
+    },
+    p3: {
+      x: parseFloat(points[4]),
+      y: parseFloat(points[5])
+    },
+    p4: {
+      x: parseFloat(points[6]),
+      y: parseFloat(points[7])
+    }
+  };
+}
+
+function isRegionHidden(region) {
+  let root = getBoxModelRoot();
+  let box = root.querySelector(".box-model-" + region);
+
+  return !box.hasAttribute("hidden");
 }
 
 function isHighlighting()
 {
-  let outline = getHighlighterOutline();
-  return outline && !outline.hasAttribute("hidden");
+  let root = getBoxModelRoot();
+  return !root.hasAttribute("hidden");
 }
 
 function getHighlitNode()
 {
   if (isHighlighting()) {
     let helper = new LayoutHelpers(window.content);
-    let outlineRect = getHighlighterOutlineRect();
-
-    let a = {
-      x: outlineRect.left,
-      y: outlineRect.top
-    };
+    let points = getBoxModelStatus().content.points;
+    let x = (points.p1.x + points.p2.x + points.p3.x + points.p4.x) / 4;
+    let y = (points.p1.y + points.p2.y + points.p3.y + points.p4.y) / 4;
 
-    let b = {
-      x: a.x + outlineRect.width,
-      y: a.y + outlineRect.height
-    };
-
-    let {x, y} = getMidPoint(a, b);
     return helper.getElementFromPoint(window.content.document, x, y);
   }
 }
 
-function getMidPoint(aPointA, aPointB)
-{
-  let pointC = {};
-  pointC.x = (aPointB.x - aPointA.x) / 2 + aPointA.x;
-  pointC.y = (aPointB.y - aPointA.y) / 2 + aPointA.y;
-  return pointC;
-}
-
 function computedView()
 {
   let sidebar = getActiveInspector().sidebar;
   let iframe = sidebar.tabbox.querySelector(".iframe-computedview");
   return iframe.contentWindow.computedView;
 }
 
 function computedViewTree()
--- a/browser/devtools/markupview/test/browser_inspector_markup_navigation.js
+++ b/browser/devtools/markupview/test/browser_inspector_markup_navigation.js
@@ -120,17 +120,17 @@ function test() {
       case "pagedown":
         EventUtils.synthesizeKey("VK_PAGE_DOWN", {});
         break;
       case "home":
         EventUtils.synthesizeKey("VK_HOME", {});
         break;
     }
 
-    inspector.markup._waitForChildren().then(() => executeSoon(function BIMNT_newNode() {
+    inspector.markup._waitForChildren().then(() => executeSoon(() => {
       let node = inspector.selection.node;
 
       if (className == "*comment*") {
         is(node.nodeType, Node.COMMENT_NODE, "[" + cursor + "] should be a comment after moving " + key);
       } else if (className == "*text*") {
         is(node.nodeType, Node.TEXT_NODE, "[" + cursor + "] should be text after moving " + key);
       } else if (className == "*doctype*") {
         is(node.nodeType, Node.DOCUMENT_TYPE_NODE, "[" + cursor + "] should be doctype after moving " + key);
--- a/browser/devtools/markupview/test/head.js
+++ b/browser/devtools/markupview/test/head.js
@@ -115,17 +115,17 @@ function selectNode(nodeOrSelector, insp
  * @param {InspectorPanel} inspector The instance of InspectorPanel currently loaded in the toolbox
  * @return a promise that resolves when the container is hovered and the higlighter
  * is shown on the corresponding node
  */
 function hoverContainer(nodeOrSelector, inspector) {
   info("Hovering over the markup-container for node " + nodeOrSelector);
   let highlit = inspector.toolbox.once("node-highlight");
   let container = getContainerForRawNode(inspector.markup, getNode(nodeOrSelector));
-  EventUtils.synthesizeMouse(container.tagLine, 2, 2, {type: "mousemove"},
+  EventUtils.synthesizeMouseAtCenter(container.tagLine, {type: "mousemove"},
     inspector.markup.doc.defaultView);
   return highlit;
 }
 
 /**
  * Simulate a click on the markup-container (a line in the markup-view)
  * that corresponds to the node or selector passed.
  * @param {String|DOMNode} nodeOrSelector
@@ -143,33 +143,34 @@ function clickContainer(nodeOrSelector, 
   return updated;
 }
 
 /**
  * Checks if the highlighter is visible currently
  * @return {Boolean}
  */
 function isHighlighterVisible() {
-  let outline = gBrowser.selectedBrowser.parentNode.querySelector(".highlighter-container .highlighter-outline");
-  return outline && !outline.hasAttribute("hidden");
+  let highlighter = gBrowser.selectedBrowser.parentNode
+                            .querySelector(".highlighter-container .box-model-root");
+  return highlighter && !highlighter.hasAttribute("hidden");
 }
 
 /**
  * Simulate the mouse leaving the markup-view area
  * @param {InspectorPanel} inspector The instance of InspectorPanel currently loaded in the toolbox
  * @return a promise when done
  */
 function mouseLeaveMarkupView(inspector) {
   info("Leaving the markup-view area");
   let def = promise.defer();
 
   // Find another element to mouseover over in order to leave the markup-view
   let btn = inspector.toolbox.doc.querySelector(".toolbox-dock-button");
 
-  EventUtils.synthesizeMouse(btn, 2, 2, {type: "mousemove"},
+  EventUtils.synthesizeMouseAtCenter(btn, {type: "mousemove"},
     inspector.toolbox.doc.defaultView);
   executeSoon(def.resolve);
 
   return def.promise;
 }
 
 /**
  * Focus a given editable element, enter edit mode, set value, and commit
--- a/browser/devtools/scratchpad/test/browser_scratchpad_revert_to_saved.js
+++ b/browser/devtools/scratchpad/test/browser_scratchpad_revert_to_saved.js
@@ -85,18 +85,17 @@ function testAfterSecondSave() {
 function testAfterSecondRevert() {
   // Check if the file's text got reverted
   is(gScratchpad.getText(), gFileContent + "\nalert(foo.toSource());",
      "The text reverted back to the changed saved text.");
   // The revert menu should be disabled again.
   ok(menu.hasAttribute("disabled"),
      "Revert menu entry is disabled after reverting to changed saved state.");
   gFile.remove(false);
-  gFile = null;
-  gScratchpad = null;
+  gFile = gScratchpad = menu = null;
   finish();
 }
 
 function createAndLoadTemporaryFile()
 {
   // Create a temporary file.
   gFile = FileUtils.getFile("TmpD", [gFileName]);
   gFile.createUnique(Ci.nsIFile.NORMAL_FILE_TYPE, 0666);
--- a/browser/devtools/webconsole/test/browser_console_variables_view_highlighter.js
+++ b/browser/devtools/webconsole/test/browser_console_variables_view_highlighter.js
@@ -61,17 +61,17 @@ function onNodeListVviewFetched(aEvent, 
           clickOnDomNodeVariableAndAssertInspectorSelected(index);
         });
       });
 
       // Rather than trying to emulate a mouseenter event, let's call the
       // variable's highlightDomNode and see if it has the desired effect
       prop.highlightDomNode();
     } else {
-      finishTest();
+      finishUp();
     }
   }
 
   function clickOnDomNodeVariableAndAssertInspectorSelected(index) {
     let prop = props[index][1];
 
     // Make sure the inspector is initialized so we can listen to its events
     gToolbox.initInspector().then(() => {
@@ -84,8 +84,14 @@ function onNodeListVviewFetched(aEvent, 
           hoverOverDomNodeVariableAndAssertHighlighter(index + 1);
         });
       });
     });
   }
 
   hoverOverDomNodeVariableAndAssertHighlighter(0);
 }
+
+function finishUp() {
+  gWebConsole = gJSTerm = gVariablesView = gToolbox = null;
+
+  finishTest();
+}
--- a/browser/devtools/webconsole/test/browser_webconsole_autocomplete_in_debugger_stackframe.js
+++ b/browser/devtools/webconsole/test/browser_webconsole_autocomplete_in_debugger_stackframe.js
@@ -209,17 +209,17 @@ function testCompletion(hud) {
   input.setSelectionRange(11, 11);
   jsterm.complete(jsterm.COMPLETE_HINT_ONLY, testNext);
   yield undefined;
 
   newItems = popup.getItems();
   is(newItems.length, 0, "no items for foo2Obj[0]");
 
   testDriver = null;
-  executeSoon(finishTest);
+  executeSoon(finishUp);
   yield undefined;
 }
 
 function debuggerOpened(aResult)
 {
   let debuggerWin = aResult.panelWin;
   let debuggerController = debuggerWin.DebuggerController;
   let thread = debuggerController.activeThread;
@@ -232,8 +232,13 @@ function debuggerOpened(aResult)
   });
 }
 
 function onFramesAdded()
 {
   info("onFramesAdded, openConsole() now");
   executeSoon(() => openConsole(null, testNext));
 }
+
+function finishUp() {
+  testDriver = gStackframes = null;
+  finishTest();
+}
--- a/browser/devtools/webconsole/test/browser_webconsole_bug_585991_autocomplete_keys.js
+++ b/browser/devtools/webconsole/test/browser_webconsole_bug_585991_autocomplete_keys.js
@@ -327,10 +327,15 @@ function popupHideAfterCompletionInText(
 
   ok(!popup.isOpen, "popup is not open");
   is(inputNode.value, "dump(window.testBug873250b)",
      "completion was successful after VK_TAB");
   is(inputNode.selectionStart, 26, "cursor location is correct");
   is(inputNode.selectionStart, inputNode.selectionEnd, "cursor location (confirmed)");
   ok(!completeNode.value, "completeNode is empty");
 
+  finishUp();
+}
+
+function finishUp() {
+  HUD = popup = jsterm = inputNode = completeNode = null;
   finishTest();
 }
--- a/browser/devtools/webconsole/test/browser_webconsole_bug_651501_document_body_autocomplete.js
+++ b/browser/devtools/webconsole/test/browser_webconsole_bug_651501_document_body_autocomplete.js
@@ -79,10 +79,15 @@ function testPropertyPanel()
     EventUtils.synthesizeMouse(anchor, 2, 2, {}, gHUD.iframeWindow);
   });
 }
 
 function onVariablesViewReady(aEvent, aView)
 {
   findVariableViewProperties(aView, [
     { name: "body", value: "<body>" },
-  ], { webconsole: gHUD }).then(finishTest);
+  ], { webconsole: gHUD }).then(finishUp);
 }
+
+function finishUp() {
+  gHUD = null;
+  finishTest();
+}
--- a/browser/devtools/webconsole/test/browser_webconsole_output_01.js
+++ b/browser/devtools/webconsole/test/browser_webconsole_output_01.js
@@ -84,10 +84,15 @@ function test() {
     DebuggerServer.LONG_STRING_LENGTH = LONG_STRING_LENGTH;
     DebuggerServer.LONG_STRING_INITIAL_LENGTH = LONG_STRING_INITIAL_LENGTH;
   });
 
   Task.spawn(function*() {
     let {tab} = yield loadTab(TEST_URI);
     let hud = yield openConsole(tab);
     return checkOutputForInputs(hud, inputTests);
-  }).then(finishTest);
+  }).then(finishUp);
 }
+
+function finishUp() {
+  inputTests = null;
+  finishTest();
+}
--- a/browser/devtools/webconsole/test/browser_webconsole_output_03.js
+++ b/browser/devtools/webconsole/test/browser_webconsole_output_03.js
@@ -153,11 +153,17 @@ let inputTests = [
 ];
 
 function test() {
   addTab(TEST_URI);
   browser.addEventListener("load", function onLoad() {
     browser.removeEventListener("load", onLoad, true);
     openConsole().then((hud) => {
       return checkOutputForInputs(hud, inputTests);
-    }).then(finishTest);
+    }).then(finishUp);
   }, true);
 }
+
+function finishUp() {
+  inputTests = null;
+
+  finishTest();
+}
--- a/browser/devtools/webconsole/test/browser_webconsole_view_source.js
+++ b/browser/devtools/webconsole/test/browser_webconsole_view_source.js
@@ -66,22 +66,19 @@ let observer = {
   observe: function(aSubject, aTopic, aData) {
     if (aTopic != "domwindowopened") {
       return;
     }
 
     ok(true, "the view source window was opened in response to clicking " +
        "the location node");
 
-    // executeSoon() is necessary to avoid crashing Firefox. See bug 611543.
-    executeSoon(function() {
-      aSubject.close();
-      ok(containsValueInvoked, "custom containsValue() was invoked");
-      Sources.containsValue = containsValue;
-      Sources = containsValue = null;
-      finishTest();
-    });
+    aSubject.close();
+    ok(containsValueInvoked, "custom containsValue() was invoked");
+    Sources.containsValue = containsValue;
+    Sources = containsValue = null;
+    finishTest();
   }
 };
 
 registerCleanupFunction(function() {
   Services.ww.unregisterNotification(observer);
 });
--- a/browser/devtools/webconsole/test/head.js
+++ b/browser/devtools/webconsole/test/head.js
@@ -293,17 +293,17 @@ function dumpMessageElement(aMessage)
                 "severity", aMessage.severity,
                 "repeats", repeats,
                 "clipboardText", aMessage.clipboardText,
                 "text", text);
 }
 
 function finishTest()
 {
-  browser = hudId = hud = filterBox = outputNode = cs = null;
+  browser = hudId = hud = filterBox = outputNode = cs = hudBox = null;
 
   dumpConsoles();
 
   let browserConsole = HUDService.getBrowserConsole();
   if (browserConsole) {
     if (browserConsole.jsterm) {
       browserConsole.jsterm.clearOutput(true);
     }