Bug 1341304 - Implement devtools.panels.elements.onSelectionChanged. r=aswan

MozReview-Commit-ID: HMKvnk3wDyX
This commit is contained in:
Luca Greco
2017-06-01 20:06:53 +02:00
parent 3858a8a30b
commit f64189b389
4 changed files with 159 additions and 1 deletions

View File

@@ -216,14 +216,79 @@ class ParentDevToolsPanel {
}
}
class DevToolsSelectionObserver extends EventEmitter {
constructor(context) {
if (!context.devToolsToolbox) {
// This should never happen when this constructor is called with a valid
// devtools extension context.
throw Error("Missing mandatory toolbox");
}
super();
context.callOnClose(this);
this.toolbox = context.devToolsToolbox;
this.onSelected = this.onSelected.bind(this);
this.initialized = false;
}
on(...args) {
this.lazyInit();
super.on.apply(this, args);
}
once(...args) {
this.lazyInit();
super.once.apply(this, args);
}
async lazyInit() {
if (!this.initialized) {
this.initialized = true;
this.toolbox.on("selection-changed", this.onSelected);
}
}
close() {
if (this.destroyed) {
throw new Error("Unable to close a destroyed DevToolsSelectionObserver");
}
if (this.initialized) {
this.toolbox.off("selection-changed", this.onSelected);
}
this.toolbox = null;
this.destroyed = true;
}
onSelected(event) {
this.emit("selectionChanged");
}
}
this.devtools_panels = class extends ExtensionAPI {
getAPI(context) {
// An incremental "per context" id used in the generated devtools panel id.
let nextPanelId = 0;
const toolboxSelectionObserver = new DevToolsSelectionObserver(context);
return {
devtools: {
panels: {
elements: {
onSelectionChanged: new EventManager(
context, "devtools.panels.elements.onSelectionChanged", fire => {
const listener = (eventName) => {
fire.async();
};
toolboxSelectionObserver.on("selectionChanged", listener);
return () => {
toolboxSelectionObserver.off("selectionChanged", listener);
};
}).api(),
},
create(title, icon, url) {
// Get a fallback icon from the manifest data.
if (icon === "" && context.extension.manifest.icons) {

View File

@@ -17,7 +17,7 @@
"events": [
{
"name": "onSelectionChanged",
"unsupported": true,
"type": "function",
"description": "Fired when an object is selected in the panel."
}
],

View File

@@ -68,6 +68,7 @@ skip-if = (os == 'win' && !debug) # bug 1352668
[browser_ext_devtools_network.js]
[browser_ext_devtools_page.js]
[browser_ext_devtools_panel.js]
[browser_ext_devtools_panels_elements.js]
[browser_ext_geckoProfiler_symbolicate.js]
[browser_ext_getViews.js]
[browser_ext_identity_indication.js]

View File

@@ -0,0 +1,92 @@
/* -*- Mode: indent-tabs-mode: nil; js-indent-level: 2 -*- */
/* vim: set sts=2 sw=2 et tw=80: */
"use strict";
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
"resource://devtools/client/framework/gDevTools.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "devtools",
"resource://devtools/shared/Loader.jsm");
add_task(async function test_devtools_panels_elements_onSelectionChanged() {
let tab = await BrowserTestUtils.openNewForegroundTab(gBrowser, "http://mochi.test:8888/");
function devtools_page() {
let doTabReload = true;
browser.devtools.panels.elements.onSelectionChanged.addListener(async () => {
const [
evalResult, exceptionInfo,
] = await browser.devtools.inspectedWindow.eval("$0 && $0.tagName");
if (exceptionInfo) {
browser.test.fail("Unexpected exceptionInfo on inspectedWindow.eval: " +
JSON.stringify(exceptionInfo));
}
browser.test.sendMessage("devtools_eval_result", evalResult);
if (doTabReload) {
// Force a reload to test that the expected onSelectionChanged events are sent
// while the page is navigating and once it has been fully reloaded.
doTabReload = false;
await browser.devtools.inspectedWindow.eval("window.location.reload();");
}
});
browser.test.sendMessage("devtools_page_loaded");
}
let extension = ExtensionTestUtils.loadExtension({
manifest: {
devtools_page: "devtools_page.html",
},
files: {
"devtools_page.html": `<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
</head>
<body>
<script src="devtools_page.js"></script>
</body>
</html>`,
"devtools_page.js": devtools_page,
},
});
await extension.startup();
let target = devtools.TargetFactory.forTab(tab);
const toolbox = await gDevTools.showToolbox(target, "webconsole");
info("developer toolbox opened");
await extension.awaitMessage("devtools_page_loaded");
toolbox.selectTool("inspector");
const evalResult = await extension.awaitMessage("devtools_eval_result");
is(evalResult, "BODY", "Got the expected onSelectionChanged once the inspector is selected");
const evalResultNavigating = await extension.awaitMessage("devtools_eval_result");
is(evalResultNavigating, undefined, "Got the expected onSelectionChanged once the tab is navigating");
const evalResultNavigated = await extension.awaitMessage("devtools_eval_result");
is(evalResultNavigated, undefined, "Got the expected onSelectionChanged once the tab navigated");
const evalResultReloaded = await extension.awaitMessage("devtools_eval_result");
is(evalResultReloaded, "BODY",
"Got the expected onSelectionChanged once the tab has been completely reloaded");
await gDevTools.closeToolbox(target);
await target.destroy();
await extension.unload();
await BrowserTestUtils.removeTab(tab);
});