mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-25 13:51:41 +00:00
Bug 788977 - [toolbox] Land the developer tools window; r=harth,jwalker,mikeratcliffe,paul,dão
This commit is contained in:
parent
b4af68ab55
commit
e9233b2864
@ -1010,11 +1010,16 @@ pref("devtools.toolbar.visible", false);
|
||||
pref("devtools.gcli.allowSet", false);
|
||||
pref("devtools.commands.dir", "");
|
||||
|
||||
// Toolbox preferences
|
||||
pref("devtools.toolbox.footer.height", 250);
|
||||
pref("devtools.toolbox.sidebar.width", 500);
|
||||
pref("devtools.toolbox.host", "bottom");
|
||||
pref("devtools.toolbox.selectedTool", "webconsole");
|
||||
pref("devtools.toolbox.toolbarSpec", '["tilt toggle","scratchpad","resize toggle"]');
|
||||
pref("devtools.toolbox.sideEnabled", false);
|
||||
|
||||
// Enable the Inspector
|
||||
pref("devtools.inspector.enabled", true);
|
||||
pref("devtools.inspector.htmlHeight", 112);
|
||||
pref("devtools.inspector.htmlPanelOpen", false);
|
||||
pref("devtools.inspector.sidebarOpen", false);
|
||||
pref("devtools.inspector.activeSidebar", "ruleview");
|
||||
pref("devtools.inspector.markupPreview", false);
|
||||
|
||||
@ -1046,17 +1051,11 @@ pref("devtools.debugger.ui.variables-sorting-enabled", true);
|
||||
pref("devtools.debugger.ui.variables-non-enum-visible", true);
|
||||
pref("devtools.debugger.ui.variables-searchbox-visible", false);
|
||||
|
||||
// Enable the style inspector
|
||||
pref("devtools.styleinspector.enabled", true);
|
||||
|
||||
// Enable the Tilt inspector
|
||||
pref("devtools.tilt.enabled", true);
|
||||
pref("devtools.tilt.intro_transition", true);
|
||||
pref("devtools.tilt.outro_transition", true);
|
||||
|
||||
// Enable the rules view
|
||||
pref("devtools.ruleview.enabled", true);
|
||||
|
||||
// Enable the Scratchpad tool.
|
||||
pref("devtools.scratchpad.enabled", true);
|
||||
|
||||
@ -1081,17 +1080,6 @@ pref("devtools.gcli.eagerHelper", 2);
|
||||
// Do we allow the 'pref set' command
|
||||
pref("devtools.gcli.allowSet", false);
|
||||
|
||||
// The last Web Console height. This is initially 0 which means that the Web
|
||||
// Console will use the default height next time it shows.
|
||||
// Change to -1 if you do not want the Web Console to remember its last height.
|
||||
pref("devtools.hud.height", 0);
|
||||
|
||||
// Remember the Web Console position. Possible values:
|
||||
// above - above the web page,
|
||||
// below - below the web page,
|
||||
// window - in a separate window/popup panel.
|
||||
pref("devtools.webconsole.position", "below");
|
||||
|
||||
// Remember the Web Console filters
|
||||
pref("devtools.webconsole.filter.network", true);
|
||||
pref("devtools.webconsole.filter.networkinfo", true);
|
||||
|
@ -150,20 +150,27 @@
|
||||
<menu id="appmenu_webDeveloper"
|
||||
label="&appMenuWebDeveloper.label;">
|
||||
<menupopup id="appmenu_webDeveloper_popup">
|
||||
<menuitem id="appmenu_devToolbar" observes="devtoolsMenuBroadcaster_DevToolbar"/>
|
||||
<menuitem id="appmenu_webConsole" observes="devtoolsMenuBroadcaster_WebConsole"/>
|
||||
<menuitem id="appmenu_remoteWebConsole" observes="devtoolsMenuBroadcaster_RemoteWebConsole"/>
|
||||
<menuitem id="appmenu_pageinspect" observes="devtoolsMenuBroadcaster_Inspect"/>
|
||||
<menuitem id="appmenu_responsiveUI" observes="devtoolsMenuBroadcaster_ResponsiveUI"/>
|
||||
<menuitem id="appmenu_debugger" observes="devtoolsMenuBroadcaster_Debugger"/>
|
||||
<menuitem id="appmenu_remoteDebugger" observes="devtoolsMenuBroadcaster_RemoteDebugger"/>
|
||||
<menuitem id="appmenu_chromeDebugger" observes="devtoolsMenuBroadcaster_ChromeDebugger"/>
|
||||
<menuitem id="appmenu_scratchpad" observes="devtoolsMenuBroadcaster_Scratchpad"/>
|
||||
<menuitem id="appmenu_styleeditor" observes="devtoolsMenuBroadcaster_StyleEditor"/>
|
||||
<menuitem id="appmenu_pageSource" observes="devtoolsMenuBroadcaster_PageSource"/>
|
||||
<menuitem id="appmenu_errorConsole" observes="devtoolsMenuBroadcaster_ErrorConsole"/>
|
||||
<menuitem id="appmenu_devToolbox"
|
||||
observes="devtoolsMenuBroadcaster_DevToolbox"/>
|
||||
<menuseparator id="appmenu_devtools_separator"/>
|
||||
<menuitem id="appmenu_devToolbar"
|
||||
observes="devtoolsMenuBroadcaster_DevToolbar"/>
|
||||
<menuitem id="appmenu_remoteWebConsole"
|
||||
observes="devtoolsMenuBroadcaster_RemoteWebConsole"/>
|
||||
<menuitem id="appmenu_responsiveUI"
|
||||
observes="devtoolsMenuBroadcaster_ResponsiveUI"/>
|
||||
<menuitem id="appmenu_scratchpad"
|
||||
observes="devtoolsMenuBroadcaster_Scratchpad"/>
|
||||
<menuitem id="appmenu_pageSource"
|
||||
observes="devtoolsMenuBroadcaster_PageSource"/>
|
||||
<menuitem id="appmenu_errorConsole"
|
||||
observes="devtoolsMenuBroadcaster_ErrorConsole"/>
|
||||
<menuseparator id="appmenu_devToolsConnectSeparator"/>
|
||||
<menuitem id="appmenu_devtools_connect"
|
||||
observes="devtoolsMenuBroadcaster_connect"/>
|
||||
<menuseparator id="appmenu_devToolsEndSeparator"/>
|
||||
<menuitem id="appmenu_getMoreDevtools" observes="devtoolsMenuBroadcaster_GetMoreTools"/>
|
||||
<menuitem id="appmenu_getMoreDevtools"
|
||||
observes="devtoolsMenuBroadcaster_GetMoreTools"/>
|
||||
<menuseparator/>
|
||||
#define ID_PREFIX appmenu_developer_
|
||||
#define OMIT_ACCESSKEYS
|
||||
|
@ -19,7 +19,5 @@
|
||||
#endif
|
||||
<!ENTITY % aboutHomeDTD SYSTEM "chrome://browser/locale/aboutHome.dtd">
|
||||
%aboutHomeDTD;
|
||||
<!ENTITY % debuggerDTD SYSTEM "chrome://browser/locale/devtools/debugger.dtd">
|
||||
%debuggerDTD;
|
||||
]>
|
||||
|
||||
|
@ -557,20 +557,34 @@
|
||||
label="&webDeveloperMenu.label;"
|
||||
accesskey="&webDeveloperMenu.accesskey;">
|
||||
<menupopup id="menuWebDeveloperPopup">
|
||||
<menuitem id="menu_devToolbar" observes="devtoolsMenuBroadcaster_DevToolbar" accesskey="&devToolbarMenu.accesskey;"/>
|
||||
<menuitem id="webConsole" observes="devtoolsMenuBroadcaster_WebConsole" accesskey="&webConsoleCmd.accesskey;"/>
|
||||
<menuitem id="menu_remoteWebConsole" observes="devtoolsMenuBroadcaster_RemoteWebConsole"/>
|
||||
<menuitem id="menu_pageinspect" observes="devtoolsMenuBroadcaster_Inspect" accesskey="&inspectMenu.accesskey;"/>
|
||||
<menuitem id="menu_responsiveUI" observes="devtoolsMenuBroadcaster_ResponsiveUI" accesskey="&responsiveDesignTool.accesskey;"/>
|
||||
<menuitem id="menu_debugger" observes="devtoolsMenuBroadcaster_Debugger" accesskey="&debuggerMenu.accesskey;"/>
|
||||
<menuitem id="menu_remoteDebugger" observes="devtoolsMenuBroadcaster_RemoteDebugger"/>
|
||||
<menuitem id="menu_chromeDebugger" observes="devtoolsMenuBroadcaster_ChromeDebugger"/>
|
||||
<menuitem id="menu_scratchpad" observes="devtoolsMenuBroadcaster_Scratchpad" accesskey="&scratchpad.accesskey;"/>
|
||||
<menuitem id="menu_styleeditor" observes="devtoolsMenuBroadcaster_StyleEditor" accesskey="&styleeditor.accesskey;"/>
|
||||
<menuitem id="menu_pageSource" observes="devtoolsMenuBroadcaster_PageSource" accesskey="&pageSourceCmd.accesskey;"/>
|
||||
<menuitem id="javascriptConsole" observes="devtoolsMenuBroadcaster_ErrorConsole" accesskey="&errorConsoleCmd.accesskey;"/>
|
||||
<menuitem id="menu_devToolbox"
|
||||
observes="devtoolsMenuBroadcaster_DevToolbox"
|
||||
accesskey="&devToolbox.accesskey;"/>
|
||||
<menuseparator id="menu_devtools_separator"/>
|
||||
<menuitem id="menu_devToolbar"
|
||||
observes="devtoolsMenuBroadcaster_DevToolbar"
|
||||
accesskey="&devToolbarMenu.accesskey;"/>
|
||||
<menuitem id="menu_remoteWebConsole"
|
||||
observes="devtoolsMenuBroadcaster_RemoteWebConsole"/>
|
||||
<menuitem id="menu_responsiveUI"
|
||||
observes="devtoolsMenuBroadcaster_ResponsiveUI"
|
||||
accesskey="&responsiveDesignTool.accesskey;"/>
|
||||
<menuitem id="menu_scratchpad"
|
||||
observes="devtoolsMenuBroadcaster_Scratchpad"
|
||||
accesskey="&scratchpad.accesskey;"/>
|
||||
<menuitem id="menu_pageSource"
|
||||
observes="devtoolsMenuBroadcaster_PageSource"
|
||||
accesskey="&pageSourceCmd.accesskey;"/>
|
||||
<menuitem id="javascriptConsole"
|
||||
observes="devtoolsMenuBroadcaster_ErrorConsole"
|
||||
accesskey="&errorConsoleCmd.accesskey;"/>
|
||||
<menuseparator id="menu_devToolsConnectSeparator"/>
|
||||
<menuitem id="menu_devtools_connect"
|
||||
observes="devtoolsMenuBroadcaster_connect"/>
|
||||
<menuseparator id="devToolsEndSeparator"/>
|
||||
<menuitem id="getMoreDevtools" observes="devtoolsMenuBroadcaster_GetMoreTools" accesskey="&getMoreDevtoolsCmd.accesskey;"/>
|
||||
<menuitem id="getMoreDevtools"
|
||||
observes="devtoolsMenuBroadcaster_GetMoreTools"
|
||||
accesskey="&getMoreDevtoolsCmd.accesskey;"/>
|
||||
</menupopup>
|
||||
</menu>
|
||||
<menuitem id="menu_pageInfo"
|
||||
|
@ -88,19 +88,15 @@
|
||||
|
||||
<command id="Tools:Search" oncommand="BrowserSearch.webSearch();"/>
|
||||
<command id="Tools:Downloads" oncommand="BrowserDownloadsUI();"/>
|
||||
<command id="Tools:DevToolbox" oncommand="gDevTools.toggleToolboxCommand(gBrowser);"/>
|
||||
<command id="Tools:DevToolbar" oncommand="DeveloperToolbar.toggle();" disabled="true" hidden="true"/>
|
||||
<command id="Tools:DevToolbarFocus" oncommand="DeveloperToolbar.focusToggle();" disabled="true"/>
|
||||
<command id="Tools:WebConsole" oncommand="HUDConsoleUI.toggleHUD();"/>
|
||||
<command id="Tools:RemoteWebConsole" oncommand="HUDConsoleUI.toggleRemoteHUD();" disabled="true" hidden="true"/>
|
||||
<command id="Tools:Inspect" oncommand="InspectorUI.toggleInspectorUI();"/>
|
||||
<command id="Tools:Debugger" oncommand="DebuggerUI.toggleDebugger();" disabled="true" hidden="true"/>
|
||||
<command id="Tools:RemoteDebugger" oncommand="DebuggerUI.toggleRemoteDebugger();" disabled="true" hidden="true"/>
|
||||
<command id="Tools:ChromeDebugger" oncommand="DebuggerUI.toggleChromeDebugger();" disabled="true" hidden="true"/>
|
||||
<command id="Tools:Scratchpad" oncommand="Scratchpad.openScratchpad();" disabled="true" hidden="true"/>
|
||||
<command id="Tools:StyleEditor" oncommand="StyleEditor.toggle();" disabled="true" hidden="true"/>
|
||||
<command id="Tools:ResponsiveUI" oncommand="ResponsiveUI.toggle();" disabled="true" hidden="true"/>
|
||||
<command id="Tools:Addons" oncommand="BrowserOpenAddonsMgr();"/>
|
||||
<command id="Tools:ErrorConsole" oncommand="toJavaScriptConsole()" disabled="true" hidden="true"/>
|
||||
<command id="Tools:DevToolsConnect" oncommand="DevToolsXULCommands.openConnectScreen(gBrowser)"/>
|
||||
<command id="Tools:Sanitize"
|
||||
oncommand="Cc['@mozilla.org/browser/browserglue;1'].getService(Ci.nsIBrowserGlue).sanitize(window);"/>
|
||||
<command id="Tools:PrivateBrowsing"
|
||||
@ -127,27 +123,6 @@
|
||||
oncommand="PlacesCommandHook.showPlacesOrganizer('History');"/>
|
||||
</commandset>
|
||||
|
||||
<commandset id="inspectorCommands">
|
||||
<command id="Inspector:Inspect"
|
||||
oncommand="InspectorUI.toggleInspection();"/>
|
||||
<command id="Inspector:Sidebar"
|
||||
oncommand="InspectorUI.toggleSidebar();"/>
|
||||
<command id="Inspector:Tilt"
|
||||
oncommand="Tilt.initialize();"/>
|
||||
<command id="Inspector:HTMLPanel"
|
||||
oncommand="InspectorUI.toggleHTMLPanel();"/>
|
||||
<command id="Inspector:CopyInner"
|
||||
oncommand="InspectorUI.copyInnerHTML();"/>
|
||||
<command id="Inspector:CopyOuter"
|
||||
oncommand="InspectorUI.copyOuterHTML();"/>
|
||||
<command id="Inspector:DeleteNode"
|
||||
oncommand="InspectorUI.deleteNode();"/>
|
||||
<command id="Inspector:ToggleVeil"
|
||||
oncommand="InspectorUI.toggleVeil();"/>
|
||||
<command id="Inspector:ToggleInfobar"
|
||||
oncommand="InspectorUI.toggleInfobar();"/>
|
||||
</commandset>
|
||||
|
||||
<broadcasterset id="mainBroadcasterSet">
|
||||
<broadcaster id="viewBookmarksSidebar" autoCheck="false" label="&bookmarksButton.label;"
|
||||
type="checkbox" group="sidebar" sidebarurl="chrome://browser/content/bookmarks/bookmarksPanel.xul"
|
||||
@ -195,45 +170,23 @@
|
||||
<broadcaster id="socialSidebarBroadcaster" hidden="true"/>
|
||||
|
||||
<!-- DevTools broadcasters -->
|
||||
<broadcaster id="devtoolsMenuBroadcaster_DevToolbox"
|
||||
label="&devToolbarToolsButton.label;"
|
||||
type="checkbox" autocheck="false"
|
||||
command="Tools:DevToolbox"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_DevToolbar"
|
||||
label="&devToolbarMenu.label;"
|
||||
type="checkbox" autocheck="false"
|
||||
command="Tools:DevToolbar"
|
||||
key="key_devToolbar"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_WebConsole"
|
||||
label="&webConsoleCmd.label;"
|
||||
type="checkbox" autocheck="false"
|
||||
key="key_webConsole"
|
||||
command="Tools:WebConsole"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_RemoteWebConsole"
|
||||
label="&remoteWebConsoleCmd.label;"
|
||||
type="checkbox" autocheck="false"
|
||||
command="Tools:RemoteWebConsole"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_Inspect"
|
||||
label="&inspectMenu.label;"
|
||||
type="checkbox" autocheck="false"
|
||||
command="Tools:Inspect"
|
||||
key="key_inspect"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_Debugger"
|
||||
label="&debuggerMenu.label2;"
|
||||
type="checkbox" autocheck="false"
|
||||
command="Tools:Debugger"
|
||||
key="key_debugger"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_RemoteDebugger"
|
||||
label="&remoteDebuggerMenu.label;"
|
||||
command="Tools:RemoteDebugger"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_ChromeDebugger"
|
||||
label="&chromeDebuggerMenu.label;"
|
||||
command="Tools:ChromeDebugger"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_Scratchpad"
|
||||
label="&scratchpad.label;"
|
||||
command="Tools:Scratchpad"
|
||||
key="key_scratchpad"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_StyleEditor"
|
||||
label="&styleeditor.label;"
|
||||
type="checkbox" autocheck="false"
|
||||
command="Tools:StyleEditor"
|
||||
key="key_styleeditor"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_ResponsiveUI"
|
||||
label="&responsiveDesignTool.label;"
|
||||
type="checkbox" autocheck="false"
|
||||
@ -250,6 +203,9 @@
|
||||
<broadcaster id="devtoolsMenuBroadcaster_GetMoreTools"
|
||||
label="&getMoreDevtoolsCmd.label;"
|
||||
oncommand="openUILinkIn('https://addons.mozilla.org/firefox/collections/mozilla/webdeveloper/', 'tab');"/>
|
||||
<broadcaster id="devtoolsMenuBroadcaster_connect"
|
||||
label="&devtoolsConnect.label;"
|
||||
command="Tools:DevToolsConnect"/>
|
||||
|
||||
<!-- SocialAPI broadcasters -->
|
||||
<broadcaster id="socialBroadcaster_userDetails"
|
||||
@ -271,7 +227,7 @@
|
||||
|
||||
#
|
||||
# Search Command Key Logic works like this:
|
||||
#
|
||||
#
|
||||
# Unix: Ctrl+K (cross platform binding)
|
||||
# Ctrl+J (in case of emacs Ctrl-K conflict)
|
||||
# Mac: Cmd+K (cross platform binding)
|
||||
@ -303,27 +259,6 @@
|
||||
<key id="key_errorConsole" key="&errorConsoleCmd.commandkey;" command="Tools:ErrorConsole" modifiers="accel,shift"/>
|
||||
<key id="key_devToolbar" keycode="&devToolbar.keycode;" modifiers="shift"
|
||||
keytext="&devToolbar.keytext;" command="Tools:DevToolbarFocus"/>
|
||||
<key id="key_webConsole" key="&webConsoleCmd.commandkey;" oncommand="HUDConsoleUI.toggleHUD();"
|
||||
#ifdef XP_MACOSX
|
||||
modifiers="accel,alt"
|
||||
#else
|
||||
modifiers="accel,shift"
|
||||
#endif
|
||||
/>
|
||||
<key id="key_debugger" key="&debuggerMenu.commandkey;" command="Tools:Debugger"
|
||||
#ifdef XP_MACOSX
|
||||
modifiers="accel,alt"
|
||||
#else
|
||||
modifiers="accel,shift"
|
||||
#endif
|
||||
/>
|
||||
<key id="key_inspect" key="&inspectMenu.commandkey;" command="Inspector:Inspect"
|
||||
#ifdef XP_MACOSX
|
||||
modifiers="accel,alt"
|
||||
#else
|
||||
modifiers="accel,shift"
|
||||
#endif
|
||||
/>
|
||||
<key id="key_responsiveUI" key="&responsiveDesignTool.commandkey;" command="Tools:ResponsiveUI"
|
||||
#ifdef XP_MACOSX
|
||||
modifiers="accel,alt"
|
||||
@ -333,8 +268,6 @@
|
||||
/>
|
||||
<key id="key_scratchpad" keycode="&scratchpad.keycode;" modifiers="shift"
|
||||
keytext="&scratchpad.keytext;" command="Tools:Scratchpad"/>
|
||||
<key id="key_styleeditor" keycode="&styleeditor.keycode;" modifiers="shift"
|
||||
keytext="&styleeditor.keytext;" command="Tools:StyleEditor"/>
|
||||
<key id="openFileKb" key="&openFileCmd.commandkey;" command="Browser:OpenFile" modifiers="accel"/>
|
||||
<key id="key_savePage" key="&savePageCmd.commandkey;" command="Browser:SavePage" modifiers="accel"/>
|
||||
<key id="printKb" key="&printCmd.commandkey;" command="cmd_print" modifiers="accel"/>
|
||||
|
@ -562,10 +562,6 @@ statuspanel[inactive][previoustype=overLink] {
|
||||
-moz-box-align: end;
|
||||
}
|
||||
|
||||
.styleInspector {
|
||||
min-width: 350px;
|
||||
}
|
||||
|
||||
.panel-inner-arrowcontentfooter[footertype="promobox"] {
|
||||
-moz-binding: url("chrome://browser/content/urlbarBindings.xml#promobox");
|
||||
}
|
||||
@ -593,22 +589,16 @@ html|*#gcli-output-frame,
|
||||
direction: ltr;
|
||||
}
|
||||
|
||||
#developer-toolbar-webconsole[error-count] > .toolbarbutton-icon {
|
||||
#developer-toolbar-toolbox-button[error-count] > .toolbarbutton-icon {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#developer-toolbar-webconsole[error-count]:before {
|
||||
#developer-toolbar-toolbox-button[error-count]:before {
|
||||
content: attr(error-count);
|
||||
display: -moz-box;
|
||||
-moz-box-pack: center;
|
||||
}
|
||||
|
||||
/* We don't show the Style Editor button in the developer toolbar for now.
|
||||
See bug 771203 */
|
||||
#developer-toolbar-styleeditor {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/* Responsive Mode */
|
||||
|
||||
.browserContainer[responsivemode] {
|
||||
|
@ -118,24 +118,6 @@ XPCOMUtils.defineLazyGetter(this, "DeveloperToolbar", function() {
|
||||
return new tmp.DeveloperToolbar(window, document.getElementById("developer-toolbar"));
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "InspectorUI", function() {
|
||||
let tmp = {};
|
||||
Cu.import("resource:///modules/inspector.jsm", tmp);
|
||||
return new tmp.InspectorUI(window);
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "DebuggerUI", function() {
|
||||
let tmp = {};
|
||||
Cu.import("resource:///modules/devtools/DebuggerUI.jsm", tmp);
|
||||
return new tmp.DebuggerUI(window);
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "Tilt", function() {
|
||||
let tmp = {};
|
||||
Cu.import("resource:///modules/devtools/Tilt.jsm", tmp);
|
||||
return new tmp.Tilt(window);
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "Social", function() {
|
||||
let tmp = {};
|
||||
Cu.import("resource:///modules/Social.jsm", tmp);
|
||||
@ -1436,36 +1418,6 @@ var gBrowserInit = {
|
||||
}
|
||||
}
|
||||
|
||||
// Enable Debugger?
|
||||
let enabled = gPrefService.getBoolPref("devtools.debugger.enabled");
|
||||
if (enabled) {
|
||||
let cmd = document.getElementById("Tools:Debugger");
|
||||
cmd.removeAttribute("disabled");
|
||||
cmd.removeAttribute("hidden");
|
||||
}
|
||||
|
||||
// Enable Remote Debugger?
|
||||
let enabled = gPrefService.getBoolPref("devtools.debugger.remote-enabled");
|
||||
if (enabled) {
|
||||
let cmd = document.getElementById("Tools:RemoteDebugger");
|
||||
cmd.removeAttribute("disabled");
|
||||
cmd.removeAttribute("hidden");
|
||||
|
||||
cmd = document.getElementById("Tools:RemoteWebConsole");
|
||||
cmd.removeAttribute("disabled");
|
||||
cmd.removeAttribute("hidden");
|
||||
}
|
||||
|
||||
// Enable Chrome Debugger?
|
||||
let enabled = gPrefService.getBoolPref("devtools.chrome.enabled") &&
|
||||
gPrefService.getBoolPref("devtools.debugger.chrome-enabled") &&
|
||||
gPrefService.getBoolPref("devtools.debugger.remote-enabled");
|
||||
if (enabled) {
|
||||
let cmd = document.getElementById("Tools:ChromeDebugger");
|
||||
cmd.removeAttribute("disabled");
|
||||
cmd.removeAttribute("hidden");
|
||||
}
|
||||
|
||||
// Enable Error Console?
|
||||
// Temporarily enabled. See bug 798925.
|
||||
let consoleEnabled = true || gPrefService.getBoolPref("devtools.errorconsole.enabled") ||
|
||||
@ -1484,14 +1436,6 @@ var gBrowserInit = {
|
||||
cmd.removeAttribute("hidden");
|
||||
}
|
||||
|
||||
// Enable Style Editor?
|
||||
let styleEditorEnabled = gPrefService.getBoolPref(StyleEditor.prefEnabledName);
|
||||
if (styleEditorEnabled) {
|
||||
let cmd = document.getElementById("Tools:StyleEditor");
|
||||
cmd.removeAttribute("disabled");
|
||||
cmd.removeAttribute("hidden");
|
||||
}
|
||||
|
||||
#ifdef MENUBAR_CAN_AUTOHIDE
|
||||
// If the user (or the locale) hasn't enabled the top-level "Character
|
||||
// Encoding" menu via the "browser.menu.showCharacterEncoding" preference,
|
||||
@ -1509,6 +1453,9 @@ var gBrowserInit = {
|
||||
cmd.removeAttribute("hidden");
|
||||
}
|
||||
|
||||
// Add Devtools menuitems and listeners
|
||||
gDevTools.registerBrowserWindow(window);
|
||||
|
||||
let appMenuButton = document.getElementById("appmenu-button");
|
||||
let appMenuPopup = document.getElementById("appmenu-popup");
|
||||
if (appMenuButton && appMenuPopup) {
|
||||
@ -1551,8 +1498,7 @@ var gBrowserInit = {
|
||||
if (!gStartupRan)
|
||||
return;
|
||||
|
||||
if (!__lookupGetter__("InspectorUI"))
|
||||
InspectorUI.destroy();
|
||||
gDevTools.forgetBrowserWindow(window);
|
||||
|
||||
// First clean up services initialized in gBrowserInit.onLoad (or those whose
|
||||
// uninit methods don't depend on the services having been initialized).
|
||||
@ -1650,7 +1596,7 @@ var gBrowserInit = {
|
||||
'viewToolbarsMenu', 'viewSidebarMenuMenu', 'Browser:Reload',
|
||||
'viewFullZoomMenu', 'pageStyleMenu', 'charsetMenu', 'View:PageSource', 'View:FullScreen',
|
||||
'viewHistorySidebar', 'Browser:AddBookmarkAs', 'Browser:BookmarkAllTabs',
|
||||
'View:PageInfo', 'Tasks:InspectPage', 'Browser:ToggleTabView', 'Browser:ToggleAddonBar'];
|
||||
'View:PageInfo', 'Browser:ToggleTabView', 'Browser:ToggleAddonBar'];
|
||||
var element;
|
||||
|
||||
for (let disabledItem of disabledItems) {
|
||||
@ -7456,6 +7402,12 @@ var TabContextMenu = {
|
||||
}
|
||||
};
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "DevToolsXULCommands",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "HUDConsoleUI", function () {
|
||||
let tempScope = {};
|
||||
Cu.import("resource:///modules/HUDService.jsm", tempScope);
|
||||
@ -7551,41 +7503,6 @@ XPCOMUtils.defineLazyGetter(ResponsiveUI, "ResponsiveUIManager", function() {
|
||||
return tmp.ResponsiveUIManager;
|
||||
});
|
||||
|
||||
var StyleEditor = {
|
||||
prefEnabledName: "devtools.styleeditor.enabled",
|
||||
/**
|
||||
* Opens the style editor. If the UI is already open, it will be focused.
|
||||
*
|
||||
* @param {CSSStyleSheet} [aSelectedStyleSheet] default Stylesheet.
|
||||
* @param {Number} [aLine] Line to which the caret should be moved (one-indexed).
|
||||
* @param {Number} [aCol] Column to which the caret should be moved (one-indexed).
|
||||
*/
|
||||
openChrome: function SE_openChrome(aSelectedStyleSheet, aLine, aCol)
|
||||
{
|
||||
let contentWindow = gBrowser.selectedBrowser.contentWindow;
|
||||
let win = this.StyleEditorManager.getEditorForWindow(contentWindow);
|
||||
if (win) {
|
||||
this.StyleEditorManager.selectEditor(win);
|
||||
return win;
|
||||
} else {
|
||||
return this.StyleEditorManager.newEditor(contentWindow, window,
|
||||
aSelectedStyleSheet, aLine, aCol);
|
||||
}
|
||||
},
|
||||
|
||||
toggle: function SE_toggle()
|
||||
{
|
||||
this.StyleEditorManager.toggleEditor(gBrowser.contentWindow, window);
|
||||
}
|
||||
};
|
||||
|
||||
XPCOMUtils.defineLazyGetter(StyleEditor, "StyleEditorManager", function() {
|
||||
let tmp = {};
|
||||
Cu.import("resource:///modules/devtools/StyleEditor.jsm", tmp);
|
||||
return new tmp.StyleEditorManager(window);
|
||||
});
|
||||
|
||||
|
||||
XPCOMUtils.defineLazyGetter(window, "gShowPageResizers", function () {
|
||||
#ifdef XP_WIN
|
||||
// Only show resizers on Windows 2000 and XP
|
||||
|
@ -278,22 +278,6 @@
|
||||
noautofocus="true"
|
||||
position="topcenter topright"/>
|
||||
|
||||
<menupopup id="inspector-node-popup">
|
||||
<menuitem id="inspectorHTMLCopyInner"
|
||||
label="&inspectorHTMLCopyInner.label;"
|
||||
accesskey="&inspectorHTMLCopyInner.accesskey;"
|
||||
command="Inspector:CopyInner"/>
|
||||
<menuitem id="inspectorHTMLCopyOuter"
|
||||
label="&inspectorHTMLCopyOuter.label;"
|
||||
accesskey="&inspectorHTMLCopyOuter.accesskey;"
|
||||
command="Inspector:CopyOuter"/>
|
||||
<menuseparator/>
|
||||
<menuitem id="inspectorHTMLDelete"
|
||||
label="&inspectorHTMLDelete.label;"
|
||||
accesskey="&inspectorHTMLDelete.accesskey;"
|
||||
command="Inspector:DeleteNode"/>
|
||||
</menupopup>
|
||||
|
||||
<menupopup id="toolbar-context-menu"
|
||||
onpopupshowing="onViewToolbarsPopupShowing(event);">
|
||||
<menuseparator/>
|
||||
@ -1064,19 +1048,6 @@
|
||||
<chatbar id="pinnedchats" layer="true" mousethrough="always" hidden="true"/>
|
||||
<statuspanel id="statusbar-display" inactive="true"/>
|
||||
</vbox>
|
||||
<splitter id="devtools-side-splitter" hidden="true"/>
|
||||
<vbox id="devtools-sidebar-box" hidden="true"
|
||||
style="min-width: 18em; width: 22em; max-width: 42em;" persist="width">
|
||||
<toolbar id="devtools-sidebar-toolbar"
|
||||
class="devtools-toolbar"
|
||||
nowindowdrag="true">
|
||||
<spacer flex="1"/>
|
||||
<toolbarbutton tooltiptext="&inspectSidebarCloseButton.tooltiptext;"
|
||||
class="devtools-closebutton"
|
||||
command="Inspector:Sidebar"/>
|
||||
</toolbar>
|
||||
<deck id="devtools-sidebar-deck" flex="1"/>
|
||||
</vbox>
|
||||
<splitter id="social-sidebar-splitter"
|
||||
class="chromeclass-extrachrome sidebar-splitter"
|
||||
observes="socialSidebarBroadcaster"/>
|
||||
@ -1115,52 +1086,6 @@
|
||||
</hbox>
|
||||
|
||||
<vbox id="browser-bottombox" layer="true">
|
||||
<toolbar id="inspector-toolbar"
|
||||
class="devtools-toolbar"
|
||||
nowindowdrag="true"
|
||||
hidden="true">
|
||||
#ifdef XP_MACOSX
|
||||
<toolbarbutton id="highlighter-closebutton"
|
||||
class="devtools-closebutton"
|
||||
oncommand="InspectorUI.closeInspectorUI(false);"
|
||||
tooltiptext="&inspectCloseButton.tooltiptext;"/>
|
||||
#endif
|
||||
<toolbarbutton id="inspector-inspect-toolbutton"
|
||||
class="devtools-toolbarbutton"
|
||||
command="Inspector:Inspect"/>
|
||||
<toolbarbutton id="inspector-treepanel-toolbutton"
|
||||
class="devtools-toolbarbutton"
|
||||
tabindex="0"
|
||||
aria-label="&markupButton.arialabel;"
|
||||
accesskey="&markupButton.accesskey;"
|
||||
command="Inspector:HTMLPanel"/>
|
||||
<arrowscrollbox id="inspector-breadcrumbs"
|
||||
flex="1" orient="horizontal"
|
||||
clicktoscroll="true"/>
|
||||
<hbox id="inspector-tools">
|
||||
<toolbarbutton id="inspector-3D-button"
|
||||
class="devtools-toolbarbutton"
|
||||
hidden="true"
|
||||
label="&inspect3DViewButton.label;"
|
||||
accesskey="&inspect3DViewButton.accesskey;"
|
||||
tabindex="0"
|
||||
command="Inspector:Tilt"/>
|
||||
<toolbarbutton id="inspector-style-button"
|
||||
class="devtools-toolbarbutton"
|
||||
label="&inspectStyleButton.label;"
|
||||
accesskey="&inspectStyleButton.accesskey;"
|
||||
tabindex="0"
|
||||
command="Inspector:Sidebar"/>
|
||||
<!-- registered tools go here -->
|
||||
</hbox>
|
||||
#ifndef XP_MACOSX
|
||||
<toolbarbutton id="highlighter-closebutton"
|
||||
class="devtools-closebutton"
|
||||
oncommand="InspectorUI.closeInspectorUI(false);"
|
||||
tooltiptext="&inspectCloseButton.tooltiptext;"/>
|
||||
#endif
|
||||
</toolbar>
|
||||
|
||||
<toolbar id="developer-toolbar"
|
||||
class="devtools-toolbar"
|
||||
hidden="true">
|
||||
@ -1177,36 +1102,9 @@
|
||||
<hbox class="gclitoolbar-complete-node"/>
|
||||
<textbox class="gclitoolbar-input-node" rows="1"/>
|
||||
</stack>
|
||||
<toolbarbutton id="developer-toolbar-webconsole"
|
||||
<toolbarbutton id="developer-toolbar-toolbox-button"
|
||||
class="developer-toolbar-button"
|
||||
observes="devtoolsMenuBroadcaster_WebConsole"/>
|
||||
<toolbarbutton id="developer-toolbar-inspector"
|
||||
class="developer-toolbar-button"
|
||||
observes="devtoolsMenuBroadcaster_Inspect"/>
|
||||
<toolbarbutton id="developer-toolbar-styleeditor"
|
||||
class="developer-toolbar-button"
|
||||
observes="devtoolsMenuBroadcaster_StyleEditor"/>
|
||||
<toolbarbutton id="developer-toolbar-debugger"
|
||||
class="developer-toolbar-button"
|
||||
observes="devtoolsMenuBroadcaster_Debugger"/>
|
||||
<toolbarbutton id="developer-toolbar-other-tools"
|
||||
type="menu"
|
||||
class="developer-toolbar-button"
|
||||
label="&devToolbarOtherToolsButton.label;">
|
||||
<menupopup position="before_end">
|
||||
<menuitem observes="devtoolsMenuBroadcaster_DevToolbar"/>
|
||||
<menuitem observes="devtoolsMenuBroadcaster_ResponsiveUI"/>
|
||||
<menuitem observes="devtoolsMenuBroadcaster_RemoteDebugger"/>
|
||||
<menuitem observes="devtoolsMenuBroadcaster_ChromeDebugger"/>
|
||||
<menuitem observes="devtoolsMenuBroadcaster_Scratchpad"/>
|
||||
<menuitem observes="devtoolsMenuBroadcaster_StyleEditor"/>
|
||||
<menuitem observes="devtoolsMenuBroadcaster_PageSource"/>
|
||||
<menuitem observes="devtoolsMenuBroadcaster_ErrorConsole"/>
|
||||
<menuseparator/>
|
||||
<menuitem observes="devtoolsMenuBroadcaster_GetMoreTools"/>
|
||||
</menupopup>
|
||||
</toolbarbutton>
|
||||
|
||||
observes="devtoolsMenuBroadcaster_DevToolbox"/>
|
||||
#ifndef XP_MACOSX
|
||||
<toolbarbutton id="developer-toolbar-closebutton"
|
||||
class="devtools-closebutton"
|
||||
|
@ -2,64 +2,60 @@
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#highlighter-container {
|
||||
.highlighter-container {
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
#highlighter-controls {
|
||||
.highlighter-controls {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
left: 0;
|
||||
}
|
||||
|
||||
#highlighter-outline-container {
|
||||
.highlighter-outline-container {
|
||||
overflow: hidden;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#highlighter-outline {
|
||||
.highlighter-outline {
|
||||
position: absolute;
|
||||
}
|
||||
|
||||
#highlighter-outline[hidden] {
|
||||
.highlighter-outline[hidden] {
|
||||
opacity: 0;
|
||||
pointer-events: none;
|
||||
display: -moz-box;
|
||||
}
|
||||
|
||||
#highlighter-outline:not([disable-transitions]) {
|
||||
.highlighter-outline:not([disable-transitions]) {
|
||||
transition-property: opacity, top, left, width, height;
|
||||
transition-duration: 0.1s;
|
||||
transition-timing-function: linear;
|
||||
}
|
||||
|
||||
.inspector-breadcrumbs-button {
|
||||
direction: ltr;
|
||||
}
|
||||
|
||||
/*
|
||||
* Node Infobar
|
||||
*/
|
||||
|
||||
#highlighter-nodeinfobar-container {
|
||||
.highlighter-nodeinfobar-container {
|
||||
position: absolute;
|
||||
max-width: 95%;
|
||||
}
|
||||
|
||||
#highlighter-nodeinfobar-container[hidden] {
|
||||
.highlighter-nodeinfobar-container[hidden] {
|
||||
opacity: 0;
|
||||
pointer-events: none;
|
||||
display: -moz-box;
|
||||
}
|
||||
|
||||
#highlighter-nodeinfobar-container:not([disable-transitions]),
|
||||
#highlighter-nodeinfobar-container[disable-transitions][force-transitions] {
|
||||
.highlighter-nodeinfobar-container:not([disable-transitions]),
|
||||
.highlighter-nodeinfobar-container[disable-transitions][force-transitions] {
|
||||
transition-property: transform, opacity, top, left;
|
||||
transition-duration: 0.1s;
|
||||
transition-timing-function: linear;
|
||||
}
|
||||
|
||||
#highlighter-nodeinfobar-text {
|
||||
.highlighter-nodeinfobar-text {
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
text-overflow: ellipsis;
|
||||
@ -70,19 +66,19 @@
|
||||
display: none;
|
||||
}
|
||||
|
||||
#highlighter-nodeinfobar-container:not([locked]):not(:hover) > #highlighter-nodeinfobar > .highlighter-nodeinfobar-button {
|
||||
.highlighter-nodeinfobar-container:not([locked]):not(:hover) > .highlighter-nodeinfobar > .highlighter-nodeinfobar-button {
|
||||
visibility: hidden;
|
||||
}
|
||||
|
||||
#highlighter-nodeinfobar-container[locked] > #highlighter-nodeinfobar,
|
||||
#highlighter-nodeinfobar-container:not([locked]):hover > #highlighter-nodeinfobar {
|
||||
.highlighter-nodeinfobar-container[locked] > .highlighter-nodeinfobar,
|
||||
.highlighter-nodeinfobar-container:not([locked]):hover > .highlighter-nodeinfobar {
|
||||
pointer-events: auto;
|
||||
}
|
||||
|
||||
html|*#highlighter-nodeinfobar-id,
|
||||
html|*#highlighter-nodeinfobar-classes,
|
||||
html|*#highlighter-nodeinfobar-pseudo-classes,
|
||||
html|*#highlighter-nodeinfobar-tagname {
|
||||
html|*.highlighter-nodeinfobar-id,
|
||||
html|*.highlighter-nodeinfobar-classes,
|
||||
html|*.highlighter-nodeinfobar-pseudo-classes,
|
||||
html|*.highlighter-nodeinfobar-tagname {
|
||||
-moz-user-select: text;
|
||||
cursor: text;
|
||||
}
|
||||
@ -91,41 +87,18 @@ html|*#highlighter-nodeinfobar-tagname {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#highlighter-nodeinfobar-container[position="top"]:not([hide-arrow]) > #highlighter-nodeinfobar-arrow-bottom {
|
||||
.highlighter-nodeinfobar-container[position="top"]:not([hide-arrow]) > .highlighter-nodeinfobar-arrow-bottom {
|
||||
display: block;
|
||||
}
|
||||
|
||||
#highlighter-nodeinfobar-container[position="bottom"]:not([hide-arrow]) > #highlighter-nodeinfobar-arrow-top {
|
||||
.highlighter-nodeinfobar-container[position="bottom"]:not([hide-arrow]) > .highlighter-nodeinfobar-arrow-top {
|
||||
display: block;
|
||||
}
|
||||
|
||||
#highlighter-nodeinfobar-container[disabled] {
|
||||
.highlighter-nodeinfobar-container[disabled] {
|
||||
visibility: hidden;
|
||||
}
|
||||
|
||||
html|*#highlighter-nodeinfobar-tagname {
|
||||
html|*.highlighter-nodeinfobar-tagname {
|
||||
text-transform: lowercase;
|
||||
}
|
||||
|
||||
.devtools-toolbarbutton:not([label]) > .toolbarbutton-text {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#inspector-option-toolbarbutton > .toolbarbutton-menu-dropmarker {
|
||||
display: none;
|
||||
}
|
||||
|
||||
#inspector-layoutview-container > iframe {
|
||||
/* header size */
|
||||
height: 28px;
|
||||
}
|
||||
|
||||
#inspector-layoutview-container:not([disable-transitions]) > iframe {
|
||||
transition-property: height;
|
||||
transition-duration: 0.2s;
|
||||
}
|
||||
|
||||
#inspector-layoutview-container > iframe[open] {
|
||||
/* header size + layout view size: 28px + 145px */
|
||||
height: 173px;
|
||||
}
|
||||
|
@ -412,11 +412,19 @@ nsContextMenu.prototype = {
|
||||
},
|
||||
|
||||
inspectNode: function CM_inspectNode() {
|
||||
if (InspectorUI.isTreePanelOpen) {
|
||||
InspectorUI.inspectNode(this.target);
|
||||
InspectorUI.stopInspecting();
|
||||
let gBrowser = this.browser.ownerDocument.defaultView.gBrowser;
|
||||
let imported = {};
|
||||
Cu.import("resource:///modules/devtools/Target.jsm", imported);
|
||||
var target = imported.TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let inspector = gDevTools.getPanelForTarget("inspector", target);
|
||||
if (inspector && inspector.isReady) {
|
||||
inspector.selection.setNode(this.target);
|
||||
} else {
|
||||
InspectorUI.openInspectorUI(this.target);
|
||||
let toolbox = gDevTools.openToolboxForTab(target, "inspector");
|
||||
toolbox.once("inspector-ready", function(event, panel) {
|
||||
let inspector = gDevTools.getPanelForTarget("inspector", target);
|
||||
inspector.selection.setNode(this.target, "browser-context-menu");
|
||||
}.bind(this));
|
||||
}
|
||||
},
|
||||
|
||||
|
@ -13,7 +13,7 @@ include $(DEPTH)/config/autoconf.mk
|
||||
include $(topsrcdir)/config/config.mk
|
||||
|
||||
DIRS = \
|
||||
highlighter \
|
||||
inspector \
|
||||
markupview \
|
||||
webconsole \
|
||||
commandline \
|
||||
@ -26,6 +26,7 @@ DIRS = \
|
||||
layoutview \
|
||||
shared \
|
||||
responsivedesign \
|
||||
framework \
|
||||
$(NULL)
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
@ -12,6 +12,12 @@ Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "HUDService",
|
||||
"resource:///modules/HUDService.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "TargetFactory",
|
||||
"resource:///modules/devtools/Target.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
|
||||
/**
|
||||
* 'break' command
|
||||
*/
|
||||
@ -30,12 +36,15 @@ gcli.addCommand({
|
||||
description: gcli.lookup("breaklistDesc"),
|
||||
returnType: "html",
|
||||
exec: function(args, context) {
|
||||
let win = HUDService.currentContext();
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (!dbg) {
|
||||
return gcli.lookup("breakaddDebuggerStopped");
|
||||
}
|
||||
let breakpoints = dbg.breakpoints;
|
||||
|
||||
let breakpoints = dbg.getAllBreakpoints();
|
||||
|
||||
if (Object.keys(breakpoints).length === 0) {
|
||||
return gcli.lookup("breaklistNone");
|
||||
@ -76,11 +85,13 @@ gcli.addCommand({
|
||||
type: {
|
||||
name: "selection",
|
||||
data: function() {
|
||||
let win = HUDService.currentContext();
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = HUDService.currentContext().gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
let files = [];
|
||||
if (dbg) {
|
||||
let sourcesView = dbg.contentWindow.DebuggerView.Sources;
|
||||
let sourcesView = dbg.panelWin.DebuggerView.Sources;
|
||||
for (let item in sourcesView) {
|
||||
files.push(item.value);
|
||||
}
|
||||
@ -99,8 +110,11 @@ gcli.addCommand({
|
||||
returnType: "html",
|
||||
exec: function(args, context) {
|
||||
args.type = "line";
|
||||
let win = HUDService.currentContext();
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (!dbg) {
|
||||
return gcli.lookup("breakaddDebuggerStopped");
|
||||
}
|
||||
@ -131,12 +145,14 @@ gcli.addCommand({
|
||||
name: "number",
|
||||
min: 0,
|
||||
max: function() {
|
||||
let win = HUDService.currentContext();
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (!dbg) {
|
||||
return gcli.lookup("breakaddDebuggerStopped");
|
||||
}
|
||||
return Object.keys(dbg.breakpoints).length - 1;
|
||||
return Object.keys(dbg.getAllBreakpoints()).length - 1;
|
||||
},
|
||||
},
|
||||
description: gcli.lookup("breakdelBreakidDesc")
|
||||
@ -144,14 +160,16 @@ gcli.addCommand({
|
||||
],
|
||||
returnType: "html",
|
||||
exec: function(args, context) {
|
||||
let win = HUDService.currentContext();
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (!dbg) {
|
||||
return gcli.lookup("breakaddDebuggerStopped");
|
||||
}
|
||||
|
||||
let breakpoints = dbg.breakpoints;
|
||||
let id = Object.keys(dbg.breakpoints)[args.breakid];
|
||||
let breakpoints = dbg.getAllBreakpoints();
|
||||
let id = Object.keys(breakpoints)[args.breakid];
|
||||
if (!id || !(id in breakpoints)) {
|
||||
return gcli.lookup("breakNotFound");
|
||||
}
|
||||
|
@ -9,8 +9,8 @@ this.EXPORTED_SYMBOLS = [ ];
|
||||
Cu.import("resource:///modules/devtools/gcli.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "HUDService",
|
||||
"resource:///modules/HUDService.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "Debugger", function() {
|
||||
let JsDebugger = {};
|
||||
@ -22,6 +22,9 @@ XPCOMUtils.defineLazyGetter(this, "Debugger", function() {
|
||||
return global.Debugger;
|
||||
});
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "TargetFactory",
|
||||
"resource:///modules/devtools/Target.jsm");
|
||||
|
||||
let debuggers = [];
|
||||
|
||||
/**
|
||||
@ -50,8 +53,9 @@ gcli.addCommand({
|
||||
|
||||
debuggers.push(dbg);
|
||||
|
||||
let tab = context.environment.chromeDocument.defaultView.gBrowser.selectedTab;
|
||||
HUDService.activateHUDForContext(tab);
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
gDevTools.openToolboxForTab(target, "webconsole");
|
||||
|
||||
return gcli.lookup("calllogStartReply");
|
||||
},
|
||||
|
@ -10,8 +10,10 @@ const { classes: Cc, interfaces: Ci, utils: Cu } = Components;
|
||||
Cu.import("resource:///modules/devtools/gcli.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "HUDService",
|
||||
"resource:///modules/HUDService.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "TargetFactory",
|
||||
"resource:///modules/devtools/Target.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "Debugger", function() {
|
||||
let JsDebugger = {};
|
||||
@ -108,8 +110,9 @@ gcli.addCommand({
|
||||
": " + this.callDescription(frame));
|
||||
}.bind(this);
|
||||
|
||||
let tab = context.environment.chromeDocument.defaultView.gBrowser.selectedTab;
|
||||
HUDService.activateHUDForContext(tab);
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
gDevTools.openToolboxForTab(target, "webconsole");
|
||||
|
||||
return gcli.lookup("calllogChromeStartReply");
|
||||
},
|
||||
|
@ -11,6 +11,10 @@ Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "HUDService",
|
||||
"resource:///modules/HUDService.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "TargetFactory",
|
||||
"resource:///modules/devtools/Target.jsm");
|
||||
|
||||
/**
|
||||
* 'console' command
|
||||
@ -44,8 +48,9 @@ gcli.addCommand({
|
||||
name: "console close",
|
||||
description: gcli.lookup("consolecloseDesc"),
|
||||
exec: function Command_consoleClose(args, context) {
|
||||
let tab = context.environment.chromeDocument.defaultView.gBrowser.selectedTab
|
||||
HUDService.deactivateHUDForContext(tab);
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
gDevTools.closeToolbox(target);
|
||||
}
|
||||
});
|
||||
|
||||
@ -56,7 +61,8 @@ gcli.addCommand({
|
||||
name: "console open",
|
||||
description: gcli.lookup("consoleopenDesc"),
|
||||
exec: function Command_consoleOpen(args, context) {
|
||||
let tab = context.environment.chromeDocument.defaultView.gBrowser.selectedTab
|
||||
HUDService.activateHUDForContext(tab);
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
gDevTools.openToolboxForTab(target, "webconsole");
|
||||
}
|
||||
});
|
||||
|
@ -9,6 +9,11 @@ this.EXPORTED_SYMBOLS = [ ];
|
||||
Cu.import("resource:///modules/devtools/gcli.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "TargetFactory",
|
||||
"resource:///modules/devtools/Target.jsm");
|
||||
|
||||
/**
|
||||
* 'dbg' command
|
||||
*/
|
||||
@ -26,19 +31,9 @@ gcli.addCommand({
|
||||
description: gcli.lookup("dbgOpen"),
|
||||
params: [],
|
||||
exec: function (args, context) {
|
||||
let win = context.environment.chromeDocument.defaultView;
|
||||
let tab = win.gBrowser.selectedTab;
|
||||
let dbg = win.DebuggerUI.findDebugger();
|
||||
|
||||
if (dbg) {
|
||||
if (dbg.ownerTab !== tab) {
|
||||
win.DebuggerUI.toggleDebugger();
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
win.DebuggerUI.toggleDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
gDevTools.openToolboxForTab(target, "jsdebugger");
|
||||
}
|
||||
});
|
||||
|
||||
@ -50,12 +45,12 @@ gcli.addCommand({
|
||||
description: gcli.lookup("dbgClose"),
|
||||
params: [],
|
||||
exec: function (args, context) {
|
||||
let win = context.environment.chromeDocument.defaultView;
|
||||
let tab = win.gBrowser.selectedTab;
|
||||
let dbg = win.DebuggerUI.findDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (dbg) {
|
||||
dbg.close();
|
||||
if (dbg /* FIXME: and debugger panel is currently active */) {
|
||||
gDevTools.closeToolbox(target);
|
||||
}
|
||||
}
|
||||
});
|
||||
@ -68,11 +63,12 @@ gcli.addCommand({
|
||||
description: gcli.lookup("dbgInterrupt"),
|
||||
params: [],
|
||||
exec: function(args, context) {
|
||||
let win = context.environment.chromeDocument.defaultView;
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (dbg) {
|
||||
let controller = dbg.contentWindow.DebuggerController;
|
||||
let controller = dbg._controller;
|
||||
let thread = controller.activeThread;
|
||||
if (!thread.paused) {
|
||||
thread.interrupt();
|
||||
@ -89,11 +85,12 @@ gcli.addCommand({
|
||||
description: gcli.lookup("dbgContinue"),
|
||||
params: [],
|
||||
exec: function(args, context) {
|
||||
let win = context.environment.chromeDocument.defaultView;
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (dbg) {
|
||||
let controller = dbg.contentWindow.DebuggerController;
|
||||
let controller = dbg._controller;
|
||||
let thread = controller.activeThread;
|
||||
if (thread.paused) {
|
||||
thread.resume();
|
||||
@ -121,11 +118,12 @@ gcli.addCommand({
|
||||
description: gcli.lookup("dbgStepOverDesc"),
|
||||
params: [],
|
||||
exec: function(args, context) {
|
||||
let win = context.environment.chromeDocument.defaultView;
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (dbg) {
|
||||
let controller = dbg.contentWindow.DebuggerController;
|
||||
let controller = dbg._controller;
|
||||
let thread = controller.activeThread;
|
||||
if (thread.paused) {
|
||||
thread.stepOver();
|
||||
@ -142,11 +140,12 @@ gcli.addCommand({
|
||||
description: gcli.lookup("dbgStepInDesc"),
|
||||
params: [],
|
||||
exec: function(args, context) {
|
||||
let win = context.environment.chromeDocument.defaultView;
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (dbg) {
|
||||
let controller = dbg.contentWindow.DebuggerController;
|
||||
let controller = dbg._controller;
|
||||
let thread = controller.activeThread;
|
||||
if (thread.paused) {
|
||||
thread.stepIn();
|
||||
@ -163,11 +162,12 @@ gcli.addCommand({
|
||||
description: gcli.lookup("dbgStepOutDesc"),
|
||||
params: [],
|
||||
exec: function(args, context) {
|
||||
let win = context.environment.chromeDocument.defaultView;
|
||||
let dbg = win.DebuggerUI.getDebugger();
|
||||
let gBrowser = context.environment.chromeDocument.defaultView.gBrowser;
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
|
||||
if (dbg) {
|
||||
let controller = dbg.contentWindow.DebuggerController;
|
||||
let controller = dbg._controller;
|
||||
let thread = controller.activeThread;
|
||||
if (thread.paused) {
|
||||
thread.stepOut();
|
||||
|
@ -24,3 +24,4 @@ Cu.import("resource:///modules/devtools/CmdResize.jsm");
|
||||
Cu.import("resource:///modules/devtools/CmdRestart.jsm");
|
||||
Cu.import("resource:///modules/devtools/CmdScreenshot.jsm");
|
||||
Cu.import("resource:///modules/devtools/CmdTilt.jsm");
|
||||
Cu.import("resource:///modules/devtools/CmdScratchpad.jsm");
|
||||
|
@ -1,3 +1,11 @@
|
||||
/* vim: set ts=2 et sw=2 tw=80: */
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
|
||||
let tempScope = {};
|
||||
Cu.import("resource:///modules/devtools/Target.jsm", tempScope);
|
||||
let TargetFactory = tempScope.TargetFactory;
|
||||
|
||||
function test() {
|
||||
const TEST_URI = "http://example.com/browser/browser/devtools/commandline/" +
|
||||
"test/browser_dbg_cmd.html";
|
||||
@ -7,54 +15,40 @@ function test() {
|
||||
});
|
||||
}
|
||||
|
||||
function testDbgCmd() {
|
||||
DeveloperToolbarTest.exec({
|
||||
typed: "dbg open",
|
||||
blankOutput: true
|
||||
});
|
||||
function testCommands(dbg, cmd) {
|
||||
// Wait for the initial resume...
|
||||
dbg._controller.activeThread.addOneTimeListener("resumed", function () {
|
||||
info("Starting tests.");
|
||||
|
||||
let pane = DebuggerUI.findDebugger();
|
||||
ok(pane, "Debugger was opened.");
|
||||
let frame = pane._frame;
|
||||
let contentDoc = content.window.document;
|
||||
let output = contentDoc.querySelector("input[type=text]");
|
||||
let btnDoit = contentDoc.querySelector("input[type=button]");
|
||||
|
||||
frame.addEventListener("Debugger:Connected", function dbgConnected(aEvent) {
|
||||
frame.removeEventListener("Debugger:Connected", dbgConnected, true);
|
||||
|
||||
// Wait for the initial resume...
|
||||
aEvent.target.ownerDocument.defaultView.gClient
|
||||
.addOneTimeListener("resumed", function() {
|
||||
|
||||
info("Starting tests.");
|
||||
|
||||
let contentDoc = content.window.document;
|
||||
let output = contentDoc.querySelector("input[type=text]");
|
||||
let btnDoit = contentDoc.querySelector("input[type=button]");
|
||||
|
||||
cmd("dbg interrupt", function() {
|
||||
ok(true, "debugger is paused");
|
||||
pane.contentWindow.gClient.addOneTimeListener("resumed", function() {
|
||||
ok(true, "debugger continued");
|
||||
pane.contentWindow.gClient.addOneTimeListener("paused", function() {
|
||||
cmd("dbg interrupt", function() {
|
||||
ok(true, "debugger is paused");
|
||||
dbg._controller.activeThread.addOneTimeListener("resumed", function () {
|
||||
ok(true, "debugger continued");
|
||||
dbg._controller.activeThread.addOneTimeListener("paused", function() {
|
||||
cmd("dbg step in", function() {
|
||||
cmd("dbg step in", function() {
|
||||
cmd("dbg step in", function() {
|
||||
cmd("dbg step in", function() {
|
||||
is(output.value, "step in", "debugger stepped in");
|
||||
cmd("dbg step over", function() {
|
||||
is(output.value, "step over", "debugger stepped over");
|
||||
cmd("dbg step out", function() {
|
||||
is(output.value, "step out", "debugger stepped out");
|
||||
is(output.value, "step in", "debugger stepped in");
|
||||
cmd("dbg step over", function() {
|
||||
is(output.value, "step over", "debugger stepped over");
|
||||
cmd("dbg step out", function() {
|
||||
is(output.value, "step out", "debugger stepped out");
|
||||
cmd("dbg continue", function() {
|
||||
cmd("dbg continue", function() {
|
||||
cmd("dbg continue", function() {
|
||||
is(output.value, "dbg continue", "debugger continued");
|
||||
DeveloperToolbarTest.exec({
|
||||
typed: "dbg close",
|
||||
blankOutput: true
|
||||
});
|
||||
|
||||
let dbg = DebuggerUI.findDebugger();
|
||||
ok(!dbg, "Debugger was closed.");
|
||||
finish();
|
||||
is(output.value, "dbg continue", "debugger continued");
|
||||
DeveloperToolbarTest.exec({
|
||||
typed: "dbg close",
|
||||
blankOutput: true
|
||||
});
|
||||
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
ok(!gDevTools.getToolboxForTarget(target),
|
||||
"Debugger was closed.");
|
||||
finish();
|
||||
});
|
||||
});
|
||||
});
|
||||
@ -62,21 +56,42 @@ function testDbgCmd() {
|
||||
});
|
||||
});
|
||||
});
|
||||
EventUtils.sendMouseEvent({type:"click"}, btnDoit);
|
||||
});
|
||||
DeveloperToolbarTest.exec({
|
||||
typed: "dbg continue",
|
||||
blankOutput: true
|
||||
});
|
||||
EventUtils.sendMouseEvent({type:"click"}, btnDoit);
|
||||
});
|
||||
DeveloperToolbarTest.exec({
|
||||
typed: "dbg continue",
|
||||
blankOutput: true
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function testDbgCmd() {
|
||||
DeveloperToolbarTest.exec({
|
||||
typed: "dbg open",
|
||||
blankOutput: true
|
||||
});
|
||||
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let toolbox = gDevTools.getToolboxForTarget(target);
|
||||
|
||||
toolbox.once("jsdebugger-ready", function dbgReady() {
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
ok(dbg, "DebuggerPanel exists");
|
||||
|
||||
function cmd(aTyped, aCallback) {
|
||||
pane.contentWindow.gClient.addOneTimeListener("paused", aCallback);
|
||||
dbg._controller.activeThread.addOneTimeListener("paused", aCallback);
|
||||
DeveloperToolbarTest.exec({
|
||||
typed: aTyped,
|
||||
blankOutput: true
|
||||
});
|
||||
}
|
||||
|
||||
if (dbg._controller.activeThread) {
|
||||
testCommands(dbg, cmd);
|
||||
} else {
|
||||
dbg.once("connected", testCommands.bind(null, dbg, cmd));
|
||||
}
|
||||
});
|
||||
}
|
||||
|
@ -6,6 +6,10 @@
|
||||
const TEST_URI = "http://example.com/browser/browser/devtools/commandline/" +
|
||||
"test/browser_dbg_cmd_break.html";
|
||||
|
||||
let tempScope = {};
|
||||
Cu.import("resource:///modules/devtools/Target.jsm", tempScope);
|
||||
let TargetFactory = tempScope.TargetFactory;
|
||||
|
||||
function test() {
|
||||
DeveloperToolbarTest.test(TEST_URI, [ testBreakCommands ]);
|
||||
}
|
||||
@ -35,86 +39,84 @@ function testBreakCommands() {
|
||||
status: 'ERROR'
|
||||
});
|
||||
|
||||
let pane = DebuggerUI.toggleDebugger();
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let toolbox = gDevTools.openToolboxForTab(target, "jsdebugger");
|
||||
toolbox.once("jsdebugger-ready", function dbgReady() {
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
ok(dbg, "DebuggerPanel exists");
|
||||
dbg.once("connected", function() {
|
||||
// Wait for the initial resume...
|
||||
dbg.panelWin.gClient.addOneTimeListener("resumed", function() {
|
||||
dbg._view.Variables.lazyEmpty = false;
|
||||
|
||||
var dbgConnected = DeveloperToolbarTest.checkCalled(function() {
|
||||
pane._frame.removeEventListener("Debugger:Connected", dbgConnected, true);
|
||||
|
||||
// Wait for the initial resume.
|
||||
let client = pane.contentWindow.gClient;
|
||||
|
||||
var resumed = DeveloperToolbarTest.checkCalled(function() {
|
||||
|
||||
var framesAdded = DeveloperToolbarTest.checkCalled(function() {
|
||||
helpers.setInput('break add line ' + TEST_URI + ' ' + content.wrappedJSObject.line0);
|
||||
helpers.check({
|
||||
hints: '',
|
||||
status: 'VALID',
|
||||
args: {
|
||||
file: { value: TEST_URI },
|
||||
line: { value: content.wrappedJSObject.line0 },
|
||||
}
|
||||
});
|
||||
|
||||
DeveloperToolbarTest.exec({
|
||||
args: {
|
||||
type: 'line',
|
||||
file: TEST_URI,
|
||||
line: content.wrappedJSObject.line0
|
||||
},
|
||||
completed: false
|
||||
});
|
||||
|
||||
helpers.setInput('break list');
|
||||
helpers.check({
|
||||
input: 'break list',
|
||||
hints: '',
|
||||
markup: 'VVVVVVVVVV',
|
||||
status: 'VALID'
|
||||
});
|
||||
|
||||
DeveloperToolbarTest.exec();
|
||||
|
||||
var cleanup = DeveloperToolbarTest.checkCalled(function() {
|
||||
helpers.setInput('break del 9');
|
||||
var client = dbg.panelWin.gClient;
|
||||
var framesAdded = DeveloperToolbarTest.checkCalled(function() {
|
||||
helpers.setInput('break add line ' + TEST_URI + ' ' + content.wrappedJSObject.line0);
|
||||
helpers.check({
|
||||
input: 'break del 9',
|
||||
hints: '',
|
||||
markup: 'VVVVVVVVVVE',
|
||||
status: 'ERROR',
|
||||
args: {
|
||||
breakid: { status: 'ERROR', message: '9 is greater than maximum allowed: 0.' },
|
||||
}
|
||||
});
|
||||
|
||||
helpers.setInput('break del 0');
|
||||
helpers.check({
|
||||
input: 'break del 0',
|
||||
hints: '',
|
||||
markup: 'VVVVVVVVVVV',
|
||||
hints: '',
|
||||
status: 'VALID',
|
||||
args: {
|
||||
breakid: { value: 0 },
|
||||
file: { value: TEST_URI },
|
||||
line: { value: content.wrappedJSObject.line0 },
|
||||
}
|
||||
});
|
||||
|
||||
DeveloperToolbarTest.exec({
|
||||
args: { breakid: 0 },
|
||||
args: {
|
||||
type: 'line',
|
||||
file: TEST_URI,
|
||||
line: content.wrappedJSObject.line0
|
||||
},
|
||||
completed: false
|
||||
});
|
||||
|
||||
helpers.setInput('break list');
|
||||
helpers.check({
|
||||
input: 'break list',
|
||||
hints: '',
|
||||
markup: 'VVVVVVVVVV',
|
||||
status: 'VALID'
|
||||
});
|
||||
|
||||
DeveloperToolbarTest.exec();
|
||||
|
||||
var cleanup = DeveloperToolbarTest.checkCalled(function() {
|
||||
helpers.setInput('break del 9');
|
||||
helpers.check({
|
||||
input: 'break del 9',
|
||||
hints: '',
|
||||
markup: 'VVVVVVVVVVE',
|
||||
status: 'ERROR',
|
||||
args: {
|
||||
breakid: { status: 'ERROR', message: '9 is greater than maximum allowed: 0.' },
|
||||
}
|
||||
});
|
||||
|
||||
helpers.setInput('break del 0');
|
||||
helpers.check({
|
||||
input: 'break del 0',
|
||||
hints: '',
|
||||
markup: 'VVVVVVVVVVV',
|
||||
status: 'VALID',
|
||||
args: {
|
||||
breakid: { value: 0 },
|
||||
}
|
||||
});
|
||||
|
||||
DeveloperToolbarTest.exec({
|
||||
args: { breakid: 0 },
|
||||
completed: false
|
||||
});
|
||||
});
|
||||
|
||||
client.activeThread.resume(cleanup);
|
||||
});
|
||||
|
||||
client.activeThread.resume(cleanup);
|
||||
client.activeThread.addOneTimeListener("framesadded", framesAdded);
|
||||
|
||||
// Trigger newScript notifications using eval.
|
||||
content.wrappedJSObject.firstCall();
|
||||
});
|
||||
|
||||
client.activeThread.addOneTimeListener("framesadded", framesAdded);
|
||||
|
||||
// Trigger newScript notifications using eval.
|
||||
content.wrappedJSObject.firstCall();
|
||||
});
|
||||
|
||||
client.addOneTimeListener("resumed", resumed);
|
||||
});
|
||||
|
||||
pane._frame.addEventListener("Debugger:Connected", dbgConnected, true);
|
||||
}
|
||||
|
144
browser/devtools/debugger/DebuggerPanel.jsm
Normal file
144
browser/devtools/debugger/DebuggerPanel.jsm
Normal file
@ -0,0 +1,144 @@
|
||||
/* -*- Mode: javascript; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ft=javascript ts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
"use strict";
|
||||
|
||||
const { classes: Cc, interfaces: Ci, utils: Cu } = Components;
|
||||
|
||||
this.EXPORTED_SYMBOLS = ["DebuggerDefinition"];
|
||||
|
||||
const STRINGS_URI = "chrome://browser/locale/devtools/debugger.properties";
|
||||
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "Services",
|
||||
"resource://gre/modules/Services.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "EventEmitter",
|
||||
"resource:///modules/devtools/EventEmitter.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "DebuggerServer",
|
||||
"resource://gre/modules/devtools/dbg-server.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
XPCOMUtils.defineLazyGetter(this, "_strings",
|
||||
function() Services.strings.createBundle(STRINGS_URI));
|
||||
|
||||
XPCOMUtils.defineLazyGetter(this, "osString", function() {
|
||||
return Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULRuntime).OS;
|
||||
});
|
||||
|
||||
this.DebuggerDefinition = {
|
||||
id: "jsdebugger",
|
||||
key: l10n("open.commandkey"),
|
||||
accesskey: l10n("debuggerMenu.accesskey"),
|
||||
modifiers: osString == "Darwin" ? "accel,alt" : "accel,shift",
|
||||
ordinal: 1,
|
||||
killswitch: "devtools.debugger.enabled",
|
||||
icon: "chrome://browser/skin/devtools/tools-icons-small.png",
|
||||
url: "chrome://browser/content/debugger.xul",
|
||||
label: l10n("ToolboxDebugger.label"),
|
||||
|
||||
isTargetSupported: function(target) {
|
||||
return true;
|
||||
},
|
||||
|
||||
build: function(iframeWindow, toolbox) {
|
||||
return new DebuggerPanel(iframeWindow, toolbox);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
function DebuggerPanel(iframeWindow, toolbox) {
|
||||
this._toolbox = toolbox;
|
||||
this._controller = iframeWindow.DebuggerController;
|
||||
this._view = iframeWindow.DebuggerView;
|
||||
this._controller._target = this.target;
|
||||
this._bkp = this._controller.Breakpoints;
|
||||
this.panelWin = iframeWindow;
|
||||
|
||||
this._ensureOnlyOneRunningDebugger();
|
||||
if (!this.target.isRemote) {
|
||||
if (!DebuggerServer.initialized) {
|
||||
DebuggerServer.init();
|
||||
DebuggerServer.addBrowserActors();
|
||||
}
|
||||
}
|
||||
|
||||
let onDebuggerLoaded = function () {
|
||||
iframeWindow.removeEventListener("Debugger:Loaded", onDebuggerLoaded, true);
|
||||
this.setReady();
|
||||
}.bind(this);
|
||||
|
||||
let onDebuggerConnected = function () {
|
||||
iframeWindow.removeEventListener("Debugger:Connected",
|
||||
onDebuggerConnected, true);
|
||||
this.emit("connected");
|
||||
}.bind(this);
|
||||
|
||||
iframeWindow.addEventListener("Debugger:Loaded", onDebuggerLoaded, true);
|
||||
iframeWindow.addEventListener("Debugger:Connected",
|
||||
onDebuggerConnected, true);
|
||||
|
||||
new EventEmitter(this);
|
||||
}
|
||||
|
||||
DebuggerPanel.prototype = {
|
||||
// DevToolPanel API
|
||||
get target() this._toolbox.target,
|
||||
|
||||
get isReady() this._isReady,
|
||||
|
||||
setReady: function() {
|
||||
this._isReady = true;
|
||||
this.emit("ready");
|
||||
},
|
||||
|
||||
destroy: function() {
|
||||
delete this._toolbox;
|
||||
delete this._target;
|
||||
delete this._controller;
|
||||
delete this._view;
|
||||
delete this._bkp;
|
||||
delete this.panelWin;
|
||||
},
|
||||
|
||||
// DebuggerPanel API
|
||||
|
||||
addBreakpoint: function() {
|
||||
this._bkp.addBreakpoint.apply(this._bkp, arguments);
|
||||
},
|
||||
|
||||
removeBreakpoint: function() {
|
||||
this._bkp.removeBreakpoint.apply(this._bkp, arguments);
|
||||
},
|
||||
|
||||
getBreakpoint: function() {
|
||||
return this._bkp.getBreakpoint.apply(this._bkp, arguments);
|
||||
},
|
||||
|
||||
getAllBreakpoints: function() {
|
||||
return this._bkp.store;
|
||||
},
|
||||
|
||||
// Private
|
||||
|
||||
_ensureOnlyOneRunningDebugger: function() {
|
||||
// FIXME
|
||||
},
|
||||
};
|
||||
|
||||
/**
|
||||
* Lookup l10n string from a string bundle.
|
||||
* @param {string} aName The key to lookup.
|
||||
* @returns A localized version of the given key.
|
||||
*/
|
||||
function l10n(aName)
|
||||
{
|
||||
try {
|
||||
return _strings.GetStringFromName(aName);
|
||||
} catch (ex) {
|
||||
Services.console.logStringMessage("Error reading '" + aName + "'");
|
||||
throw new Error("l10n error with " + aName);
|
||||
}
|
||||
}
|
@ -48,6 +48,7 @@ let DebuggerController = {
|
||||
return;
|
||||
}
|
||||
this._isInitialized = true;
|
||||
|
||||
window.removeEventListener("load", this._startupDebugger, true);
|
||||
|
||||
DebuggerView.initialize(function() {
|
||||
@ -145,14 +146,32 @@ let DebuggerController = {
|
||||
* wiring event handlers as necessary.
|
||||
*/
|
||||
_connect: function DC__connect() {
|
||||
if (window._isRemoteDebugger && !this._prepareConnection()) {
|
||||
function callback() {
|
||||
window.dispatchEvent("Debugger:Connected");
|
||||
}
|
||||
|
||||
let client;
|
||||
// Remote debugging gets the debuggee from a RemoteTarget object.
|
||||
if (this._target.isRemote) {
|
||||
client = this.client = this._target.client;
|
||||
|
||||
this._target.on("close", this._onTabDetached);
|
||||
this._target.on("navigate", this._onTabNavigated);
|
||||
|
||||
if (this._target.chrome) {
|
||||
let dbg = this._target.form.chromeDebugger;
|
||||
this._startChromeDebugging(client, dbg, callback);
|
||||
} else {
|
||||
this._startDebuggingTab(client, this._target.form, callback);
|
||||
}
|
||||
return;
|
||||
}
|
||||
let transport = (window._isChromeDebugger || window._isRemoteDebugger)
|
||||
? debuggerSocketConnect(Prefs.remoteHost, Prefs.remotePort)
|
||||
: DebuggerServer.connectPipe();
|
||||
|
||||
let client = this.client = new DebuggerClient(transport);
|
||||
// Content debugging can connect directly to the page.
|
||||
// TODO: convert this to use a TabTarget.
|
||||
let transport = DebuggerServer.connectPipe();
|
||||
client = this.client = new DebuggerClient(transport);
|
||||
|
||||
client.addListener("tabNavigated", this._onTabNavigated);
|
||||
client.addListener("tabDetached", this._onTabDetached);
|
||||
|
||||
@ -160,12 +179,11 @@ let DebuggerController = {
|
||||
client.listTabs(function(aResponse) {
|
||||
if (window._isChromeDebugger) {
|
||||
let dbg = aResponse.chromeDebugger;
|
||||
this._startChromeDebugging(client, dbg);
|
||||
this._startChromeDebugging(client, dbg, callback);
|
||||
} else {
|
||||
let tab = aResponse.tabs[aResponse.selected];
|
||||
this._startDebuggingTab(client, tab);
|
||||
this._startDebuggingTab(client, tab, callback);
|
||||
}
|
||||
window.dispatchEvent("Debugger:Connected");
|
||||
}.bind(this));
|
||||
}.bind(this));
|
||||
},
|
||||
@ -180,9 +198,12 @@ let DebuggerController = {
|
||||
}
|
||||
this.client.removeListener("tabNavigated", this._onTabNavigated);
|
||||
this.client.removeListener("tabDetached", this._onTabDetached);
|
||||
this.client.close();
|
||||
|
||||
this.client = null;
|
||||
if (!this._target.isRemote) {
|
||||
this.client.close();
|
||||
this.client = null;
|
||||
}
|
||||
|
||||
this.tabClient = null;
|
||||
this.activeThread = null;
|
||||
},
|
||||
@ -212,7 +233,8 @@ let DebuggerController = {
|
||||
* @param object aTabGrip
|
||||
* The remote protocol grip of the tab.
|
||||
*/
|
||||
_startDebuggingTab: function DC__startDebuggingTab(aClient, aTabGrip) {
|
||||
_startDebuggingTab: function DC__startDebuggingTab
|
||||
(aClient, aTabGrip, aCallback=function(){}) {
|
||||
if (!aClient) {
|
||||
Cu.reportError("No client found!");
|
||||
return;
|
||||
@ -238,6 +260,7 @@ let DebuggerController = {
|
||||
this.SourceScripts.connect();
|
||||
aThreadClient.resume();
|
||||
|
||||
aCallback();
|
||||
}.bind(this));
|
||||
}.bind(this));
|
||||
},
|
||||
@ -250,7 +273,8 @@ let DebuggerController = {
|
||||
* @param object aChromeDebugger
|
||||
* The remote protocol grip of the chrome debugger.
|
||||
*/
|
||||
_startChromeDebugging: function DC__startChromeDebugging(aClient, aChromeDebugger) {
|
||||
_startChromeDebugging: function DC__startChromeDebugging
|
||||
(aClient, aChromeDebugger, aCallback=function(){}) {
|
||||
if (!aClient) {
|
||||
Cu.reportError("No client found!");
|
||||
return;
|
||||
@ -269,6 +293,7 @@ let DebuggerController = {
|
||||
this.SourceScripts.connect();
|
||||
aThreadClient.resume();
|
||||
|
||||
aCallback();
|
||||
}.bind(this));
|
||||
},
|
||||
|
||||
|
@ -25,7 +25,6 @@ ToolbarView.prototype = {
|
||||
*/
|
||||
initialize: function DVT_initialize() {
|
||||
dumpn("Initializing the ToolbarView");
|
||||
this._closeButton = document.getElementById("close");
|
||||
this._togglePanesButton = document.getElementById("toggle-panes");
|
||||
this._resumeButton = document.getElementById("resume");
|
||||
this._stepOverButton = document.getElementById("step-over");
|
||||
@ -44,7 +43,6 @@ ToolbarView.prototype = {
|
||||
this._stepInTooltip = L10N.getFormatStr("stepInTooltip", [stepInKey]);
|
||||
this._stepOutTooltip = L10N.getFormatStr("stepOutTooltip", [stepOutKey]);
|
||||
|
||||
this._closeButton.addEventListener("click", this._onCloseClick, false);
|
||||
this._togglePanesButton.addEventListener("mousedown", this._onTogglePanesPressed, false);
|
||||
this._resumeButton.addEventListener("mousedown", this._onResumePressed, false);
|
||||
this._stepOverButton.addEventListener("mousedown", this._onStepOverPressed, false);
|
||||
@ -55,7 +53,6 @@ ToolbarView.prototype = {
|
||||
this._stepInButton.setAttribute("tooltiptext", this._stepInTooltip);
|
||||
this._stepOutButton.setAttribute("tooltiptext", this._stepOutTooltip);
|
||||
|
||||
this.toggleCloseButton(!window._isRemoteDebugger && !window._isChromeDebugger);
|
||||
// TODO: bug 806775
|
||||
// this.toggleChromeGlobalsContainer(window._isChromeDebugger);
|
||||
},
|
||||
@ -65,7 +62,6 @@ ToolbarView.prototype = {
|
||||
*/
|
||||
destroy: function DVT_destroy() {
|
||||
dumpn("Destroying the ToolbarView");
|
||||
this._closeButton.removeEventListener("click", this._onCloseClick, false);
|
||||
this._togglePanesButton.removeEventListener("mousedown", this._onTogglePanesPressed, false);
|
||||
this._resumeButton.removeEventListener("mousedown", this._onResumePressed, false);
|
||||
this._stepOverButton.removeEventListener("mousedown", this._onStepOverPressed, false);
|
||||
@ -73,16 +69,6 @@ ToolbarView.prototype = {
|
||||
this._stepOutButton.removeEventListener("mousedown", this._onStepOutPressed, false);
|
||||
},
|
||||
|
||||
/**
|
||||
* Sets the close button hidden or visible. It's hidden by default.
|
||||
*
|
||||
* @param boolean aVisibleFlag
|
||||
* Specifies the intended visibility.
|
||||
*/
|
||||
toggleCloseButton: function DVT_toggleCloseButton(aVisibleFlag) {
|
||||
this._closeButton.setAttribute("hidden", !aVisibleFlag);
|
||||
},
|
||||
|
||||
/**
|
||||
* Sets the resume button state based on the debugger active thread.
|
||||
*
|
||||
@ -177,7 +163,6 @@ ToolbarView.prototype = {
|
||||
}
|
||||
},
|
||||
|
||||
_closeButton: null,
|
||||
_togglePanesButton: null,
|
||||
_resumeButton: null,
|
||||
_stepOverButton: null,
|
||||
|
@ -153,11 +153,6 @@
|
||||
|
||||
<vbox id="body" flex="1">
|
||||
<toolbar id="dbg-toolbar" class="devtools-toolbar">
|
||||
#ifdef XP_MACOSX
|
||||
<toolbarbutton id="close"
|
||||
class="devtools-closebutton"
|
||||
tooltiptext="&debuggerUI.closeButton.tooltip;"/>
|
||||
#endif
|
||||
<hbox id="debugger-controls">
|
||||
<toolbarbutton id="resume"
|
||||
class="devtools-toolbarbutton"
|
||||
@ -186,11 +181,6 @@
|
||||
class="devtools-option-toolbarbutton"
|
||||
tooltiptext="&debuggerUI.optsButton.tooltip;"
|
||||
popup="debuggerPrefsContextMenu"/>
|
||||
#ifndef XP_MACOSX
|
||||
<toolbarbutton id="close"
|
||||
class="devtools-closebutton"
|
||||
tooltiptext="&debuggerUI.closeButton.tooltip;"/>
|
||||
#endif
|
||||
</toolbar>
|
||||
|
||||
<panel id="searchbox-panel"
|
||||
|
@ -12,9 +12,9 @@ include $(DEPTH)/config/autoconf.mk
|
||||
|
||||
MOCHITEST_BROWSER_TESTS = \
|
||||
browser_dbg_leaktest.js \
|
||||
browser_dbg_createChrome.js \
|
||||
browser_dbg_debugger-tab-switch.js \
|
||||
browser_dbg_debugger-tab-switch-window.js \
|
||||
$(warning browser_dbg_createChrome.js disabled until issue 156 is fixed) \
|
||||
$(browser_dbg_debugger-tab-switch.js disabled until issues 106, 40 are fixed) \
|
||||
$(browser_dbg_debugger-tab-switch-window.js disabled until issues 106, 40 are fixed) \
|
||||
browser_dbg_debuggerstatement.js \
|
||||
browser_dbg_listtabs.js \
|
||||
browser_dbg_tabactor-01.js \
|
||||
@ -45,7 +45,6 @@ MOCHITEST_BROWSER_TESTS = \
|
||||
browser_dbg_propertyview-reexpand.js \
|
||||
browser_dbg_reload-same-script.js \
|
||||
browser_dbg_pane-collapse.js \
|
||||
browser_dbg_panesize.js \
|
||||
browser_dbg_panesize-inner.js \
|
||||
browser_dbg_stack-01.js \
|
||||
browser_dbg_stack-02.js \
|
||||
@ -82,7 +81,6 @@ MOCHITEST_BROWSER_TESTS = \
|
||||
browser_dbg_iframes.js \
|
||||
browser_dbg_pause-exceptions.js \
|
||||
browser_dbg_multiple-windows.js \
|
||||
browser_dbg_menustatus.js \
|
||||
browser_dbg_bfcache.js \
|
||||
browser_dbg_breakpoint-new-script.js \
|
||||
browser_dbg_bug737803_editor_actual_location.js \
|
||||
|
@ -20,7 +20,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testInitialLoad();
|
||||
});
|
||||
|
@ -17,7 +17,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
testAddBreakpoint();
|
||||
|
@ -31,9 +31,11 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
resumed = true;
|
||||
|
||||
gDebugger.addEventListener("Debugger:SourceShown", onScriptShown);
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
framesAdded = true;
|
||||
executeSoon(startTest);
|
||||
@ -50,12 +52,10 @@ function test()
|
||||
executeSoon(startTest);
|
||||
}
|
||||
|
||||
window.addEventListener("Debugger:SourceShown", onScriptShown);
|
||||
|
||||
function startTest()
|
||||
{
|
||||
if (scriptShown && framesAdded && resumed && !testStarted) {
|
||||
window.removeEventListener("Debugger:SourceShown", onScriptShown);
|
||||
gDebugger.removeEventListener("Debugger:SourceShown", onScriptShown);
|
||||
testStarted = true;
|
||||
Services.tm.currentThread.dispatch({ run: performTest }, 0);
|
||||
}
|
||||
@ -77,7 +77,7 @@ function test()
|
||||
isnot(gScripts.selectedValue, gScripts.values[0],
|
||||
"the correct script is selected");
|
||||
|
||||
gBreakpoints = gPane.breakpoints;
|
||||
gBreakpoints = gPane.getAllBreakpoints();
|
||||
is(Object.keys(gBreakpoints), 0, "no breakpoints");
|
||||
ok(!gPane.getBreakpoint("foo", 3), "getBreakpoint('foo', 3) returns falsey");
|
||||
|
||||
@ -127,7 +127,7 @@ function test()
|
||||
is(Object.keys(gBreakpoints).length, 1,
|
||||
"the list of debugger breakpoints holds only one breakpoint");
|
||||
is(gPane.getBreakpoint(gScripts.selectedValue, 6), aBreakpointClient,
|
||||
"getBreakpoint(selectedScript, 2) returns the correct breakpoint");
|
||||
"getBreakpoint returns the correct breakpoint");
|
||||
|
||||
info("remove the first breakpoint");
|
||||
gEditor.addEventListener(SourceEditor.EVENTS.BREAKPOINT_CHANGE,
|
||||
|
@ -29,9 +29,11 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
resumed = true;
|
||||
|
||||
gDebugger.addEventListener("Debugger:SourceShown", onScriptShown);
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
framesAdded = true;
|
||||
executeSoon(startTest);
|
||||
@ -48,12 +50,10 @@ function test()
|
||||
executeSoon(startTest);
|
||||
}
|
||||
|
||||
window.addEventListener("Debugger:SourceShown", onScriptShown);
|
||||
|
||||
function startTest()
|
||||
{
|
||||
if (scriptShown && framesAdded && resumed && !testStarted) {
|
||||
window.removeEventListener("Debugger:SourceShown", onScriptShown);
|
||||
gDebugger.removeEventListener("Debugger:SourceShown", onScriptShown);
|
||||
testStarted = true;
|
||||
Services.tm.currentThread.dispatch({ run: performTest }, 0);
|
||||
}
|
||||
@ -79,7 +79,7 @@ function test()
|
||||
isnot(gScripts.selectedValue, gScripts.values[0],
|
||||
"the correct script is selected");
|
||||
|
||||
gBreakpoints = gPane.breakpoints;
|
||||
gBreakpoints = gPane.getAllBreakpoints();
|
||||
is(Object.keys(gBreakpoints), 0, "no breakpoints");
|
||||
ok(!gPane.getBreakpoint("chocolate", 3), "getBreakpoint('chocolate', 3) returns falsey");
|
||||
|
||||
|
@ -19,7 +19,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gWatch = gDebugger.DebuggerView.WatchExpressions;
|
||||
|
||||
gDebugger.DebuggerView.togglePanes({ visible: true, animated: false });
|
||||
|
@ -20,7 +20,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gWatch = gDebugger.DebuggerView.WatchExpressions;
|
||||
gVars = gDebugger.DebuggerView.Variables;
|
||||
|
||||
|
@ -28,7 +28,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
resumed = true;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -30,9 +30,11 @@ function test() {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebuggee = aDebuggee;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
resumed = true;
|
||||
|
||||
gDebugger.addEventListener("Debugger:SourceShown", onScriptShown);
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function () {
|
||||
framesAdded = true;
|
||||
executeSoon(startTest);
|
||||
@ -48,11 +50,9 @@ function test() {
|
||||
executeSoon(startTest);
|
||||
}
|
||||
|
||||
window.addEventListener("Debugger:SourceShown", onScriptShown);
|
||||
|
||||
function startTest() {
|
||||
if (scriptShown && framesAdded && resumed && !testStarted) {
|
||||
window.removeEventListener("Debugger:SourceShown", onScriptShown);
|
||||
gDebugger.removeEventListener("Debugger:SourceShown", onScriptShown);
|
||||
testStarted = true;
|
||||
Services.tm.currentThread.dispatch({ run: performTest }, 0);
|
||||
}
|
||||
@ -61,7 +61,7 @@ function test() {
|
||||
function performTest() {
|
||||
gScripts = gDebugger.DebuggerView.Sources;
|
||||
gEditor = gDebugger.editor;
|
||||
gBreakpoints = gPane.breakpoints;
|
||||
gBreakpoints = gPane.getAllBreakpoints();
|
||||
is(Object.keys(gBreakpoints), 0, "There are no breakpoints");
|
||||
|
||||
gEditor.addEventListener(SourceEditor.EVENTS.BREAKPOINT_CHANGE,
|
||||
|
@ -29,7 +29,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gBreakpoints = gDebugger.DebuggerController.Breakpoints;
|
||||
gBreakpointsPane = gDebugger.DebuggerView.Breakpoints;
|
||||
|
||||
@ -79,7 +79,7 @@ function test()
|
||||
is(gScripts.selectedValue, gScripts.values[0],
|
||||
"The correct script is selected");
|
||||
|
||||
gBreakpoints = gPane.breakpoints;
|
||||
gBreakpoints = gPane.getAllBreakpoints();
|
||||
is(Object.keys(gBreakpoints).length, 13, "thirteen breakpoints");
|
||||
ok(!gPane.getBreakpoint("foo", 3), "getBreakpoint('foo', 3) returns falsey");
|
||||
|
||||
|
@ -33,7 +33,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gBreakpoints = gDebugger.DebuggerController.Breakpoints;
|
||||
gBreakpointsPane = gDebugger.DebuggerView.Breakpoints;
|
||||
|
||||
@ -83,7 +83,7 @@ function test()
|
||||
is(gScripts.selectedValue, gScripts.values[0],
|
||||
"The correct script is selected");
|
||||
|
||||
gBreakpoints = gPane.breakpoints;
|
||||
gBreakpoints = gPane.getAllBreakpoints();
|
||||
is(Object.keys(gBreakpoints), 0, "no breakpoints");
|
||||
ok(!gPane.getBreakpoint("foo", 3), "getBreakpoint('foo', 3) returns falsey");
|
||||
|
||||
|
@ -13,7 +13,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testNonEnumProperties();
|
||||
});
|
||||
|
@ -15,7 +15,7 @@ function test() {
|
||||
debug_tab_pane(DEBUGGER_TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testCleanExit();
|
||||
});
|
||||
|
@ -18,7 +18,7 @@ function test() {
|
||||
debug_remote(TEST_URL, function(aTab, aDebuggee, aWindow) {
|
||||
gTab = aTab;
|
||||
gWindow = aWindow;
|
||||
let gDebugger = gWindow.contentWindow;
|
||||
let gDebugger = gWindow.panelWin;
|
||||
|
||||
info("Current remote window x: " +
|
||||
Services.prefs.getIntPref("devtools.debugger.ui.win-x"));
|
||||
|
@ -18,7 +18,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testAnonCall();
|
||||
});
|
||||
|
@ -14,10 +14,7 @@ function test() {
|
||||
debug_tab_pane(TEST_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
let gDebugger = gPane.contentWindow;
|
||||
|
||||
is(gDebugger.document.getElementById("close").getAttribute("hidden"), "false",
|
||||
"The close button should be visible in a normal content debugger.");
|
||||
let gDebugger = gPane.panelWin;
|
||||
|
||||
is(gDebugger.DebuggerController.activeThread.paused, false,
|
||||
"Should be running after debug_tab_pane.");
|
||||
|
@ -24,7 +24,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
resumed = true;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -20,7 +20,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
framesAdded = true;
|
||||
|
@ -20,7 +20,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
framesAdded = true;
|
||||
|
@ -17,7 +17,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -16,7 +16,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gView = gDebugger.DebuggerView;
|
||||
|
||||
testPanesState();
|
||||
|
@ -7,65 +7,70 @@
|
||||
function test() {
|
||||
var tab1 = addTab(TAB1_URL, function() {
|
||||
gBrowser.selectedTab = tab1;
|
||||
let target1 = TargetFactory.forTab(tab1);
|
||||
|
||||
ok(!DebuggerUI.getDebugger(),
|
||||
"Shouldn't have a debugger pane for this tab yet.");
|
||||
ok(!gDevTools.getPanelForTarget("jsdebugger", target1),
|
||||
"Shouldn't have a debugger panel for this tab yet.");
|
||||
|
||||
let pane = DebuggerUI.toggleDebugger();
|
||||
ok(pane, "toggleDebugger() should return a pane.");
|
||||
let toolbox = gDevTools.openToolboxForTab(target1, "jsdebugger");
|
||||
toolbox.once("jsdebugger-ready", function dbgReady() {
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target1);
|
||||
ok(dbg, "We should have a debugger panel.");
|
||||
|
||||
let preferredSfw = Services.prefs.getIntPref("devtools.debugger.ui.stackframes-width");
|
||||
let preferredBpw = Services.prefs.getIntPref("devtools.debugger.ui.variables-width");
|
||||
let someWidth1, someWidth2;
|
||||
let preferredSfw = Services.prefs.getIntPref("devtools.debugger.ui.stackframes-width");
|
||||
let preferredBpw = Services.prefs.getIntPref("devtools.debugger.ui.variables-width");
|
||||
let someWidth1, someWidth2;
|
||||
|
||||
do {
|
||||
someWidth1 = parseInt(Math.random() * 200) + 100;
|
||||
someWidth2 = parseInt(Math.random() * 200) + 100;
|
||||
} while (someWidth1 == preferredSfw ||
|
||||
someWidth2 == preferredBpw)
|
||||
do {
|
||||
someWidth1 = parseInt(Math.random() * 200) + 100;
|
||||
someWidth2 = parseInt(Math.random() * 200) + 100;
|
||||
} while (someWidth1 == preferredSfw ||
|
||||
someWidth2 == preferredBpw)
|
||||
|
||||
info("Preferred stackframes width: " + preferredSfw);
|
||||
info("Preferred variables width: " + preferredBpw);
|
||||
info("Generated stackframes width: " + someWidth1);
|
||||
info("Generated variables width: " + someWidth2);
|
||||
let someWidth1 = parseInt(Math.random() * 200) + 100;
|
||||
let someWidth2 = parseInt(Math.random() * 200) + 100;
|
||||
|
||||
is(DebuggerUI.getDebugger(), pane,
|
||||
"getDebugger() should return the same pane as toggleDebugger().");
|
||||
info("Preferred stackframes width: " + preferredSfw);
|
||||
info("Preferred variables width: " + preferredBpw);
|
||||
info("Generated stackframes width: " + someWidth1);
|
||||
info("Generated variables width: " + someWidth2);
|
||||
|
||||
let content = pane.contentWindow;
|
||||
let stackframes;
|
||||
let variables;
|
||||
let content = dbg.panelWin;
|
||||
let stackframes;
|
||||
let variables;
|
||||
|
||||
wait_for_connect_and_resume(function() {
|
||||
ok(content.Prefs.stackframesWidth,
|
||||
"The debugger preferences should have a saved stackframesWidth value.");
|
||||
ok(content.Prefs.variablesWidth,
|
||||
"The debugger preferences should have a saved variablesWidth value.");
|
||||
wait_for_connect_and_resume(function() {
|
||||
ok(content.Prefs.stackframesWidth,
|
||||
"The debugger preferences should have a saved stackframesWidth value.");
|
||||
ok(content.Prefs.variablesWidth,
|
||||
"The debugger preferences should have a saved variablesWidth value.");
|
||||
|
||||
stackframes = content.document.getElementById("stackframes+breakpoints");
|
||||
variables = content.document.getElementById("variables+expressions");
|
||||
stackframes = content.document.getElementById("stackframes+breakpoints");
|
||||
variables = content.document.getElementById("variables+expressions");
|
||||
|
||||
is(content.Prefs.stackframesWidth, stackframes.getAttribute("width"),
|
||||
"The stackframes pane width should be the same as the preferred value.");
|
||||
is(content.Prefs.variablesWidth, variables.getAttribute("width"),
|
||||
"The variables pane width should be the same as the preferred value.");
|
||||
is(content.Prefs.stackframesWidth, stackframes.getAttribute("width"),
|
||||
"The stackframes pane width should be the same as the preferred value.");
|
||||
is(content.Prefs.variablesWidth, variables.getAttribute("width"),
|
||||
"The variables pane width should be the same as the preferred value.");
|
||||
|
||||
stackframes.setAttribute("width", someWidth1);
|
||||
variables.setAttribute("width", someWidth2);
|
||||
stackframes.setAttribute("width", someWidth1);
|
||||
variables.setAttribute("width", someWidth2);
|
||||
|
||||
removeTab(tab1);
|
||||
removeTab(tab1);
|
||||
}, tab1);
|
||||
|
||||
window.addEventListener("Debugger:Shutdown", function dbgShutdown() {
|
||||
window.removeEventListener("Debugger:Shutdown", dbgShutdown, true);
|
||||
|
||||
is(content.Prefs.stackframesWidth, stackframes.getAttribute("width"),
|
||||
"The stackframes pane width should have been saved by now.");
|
||||
is(content.Prefs.variablesWidth, variables.getAttribute("width"),
|
||||
"The variables pane width should have been saved by now.");
|
||||
|
||||
finish();
|
||||
|
||||
}, true);
|
||||
});
|
||||
|
||||
window.addEventListener("Debugger:Shutdown", function dbgShutdown() {
|
||||
window.removeEventListener("Debugger:Shutdown", dbgShutdown, true);
|
||||
|
||||
is(content.Prefs.stackframesWidth, stackframes.getAttribute("width"),
|
||||
"The stackframes pane width should have been saved by now.");
|
||||
is(content.Prefs.variablesWidth, variables.getAttribute("width"),
|
||||
"The variables pane width should have been saved by now.");
|
||||
|
||||
finish();
|
||||
|
||||
}, true);
|
||||
});
|
||||
}
|
||||
|
@ -1,55 +0,0 @@
|
||||
/* vim:set ts=2 sw=2 sts=2 et: */
|
||||
/*
|
||||
* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/
|
||||
*/
|
||||
|
||||
function test() {
|
||||
var tab1 = addTab(TAB1_URL, function() {
|
||||
gBrowser.selectedTab = tab1;
|
||||
|
||||
ok(!DebuggerUI.getDebugger(),
|
||||
"Shouldn't have a debugger pane for this tab yet.");
|
||||
|
||||
let pane = DebuggerUI.toggleDebugger();
|
||||
ok(pane, "toggleDebugger() should return a pane.");
|
||||
|
||||
let preferredHeight = Services.prefs.getIntPref("devtools.debugger.ui.height");
|
||||
let someHeight;
|
||||
|
||||
do {
|
||||
someHeight = parseInt(Math.random() * 200) + 200;
|
||||
} while (someHeight == preferredHeight)
|
||||
|
||||
info("Preferred pane height: " + preferredHeight);
|
||||
info("Generated pane height: " + someHeight);
|
||||
|
||||
is(DebuggerUI.getDebugger(), pane,
|
||||
"getDebugger() should return the same pane as toggleDebugger().");
|
||||
|
||||
ok(DebuggerUI.preferences.height,
|
||||
"The debugger preferences should have a saved height value.");
|
||||
|
||||
is(DebuggerUI.preferences.height, pane._frame.height,
|
||||
"The debugger pane height should be the same as the preferred value.");
|
||||
|
||||
pane._frame.height = someHeight;
|
||||
|
||||
ok(DebuggerUI.preferences.height !== someHeight,
|
||||
"Height preferences shouldn't have been updated yet.");
|
||||
|
||||
wait_for_connect_and_resume(function() {
|
||||
removeTab(tab1);
|
||||
});
|
||||
|
||||
window.addEventListener("Debugger:Shutdown", function dbgShutdown() {
|
||||
window.removeEventListener("Debugger:Shutdown", dbgShutdown, true);
|
||||
|
||||
is(DebuggerUI.preferences.height, someHeight,
|
||||
"Height preferences should have been updated by now.");
|
||||
|
||||
finish();
|
||||
|
||||
}, true);
|
||||
});
|
||||
}
|
@ -20,7 +20,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
gDebugger.DebuggerView.Variables.nonEnumVisible = false;
|
||||
@ -30,7 +30,7 @@ function test()
|
||||
|
||||
function testWithFrame()
|
||||
{
|
||||
gPane.contentWindow.gClient.addOneTimeListener("paused", function() {
|
||||
gPane.panelWin.gClient.addOneTimeListener("paused", function() {
|
||||
gDebugger.addEventListener("Debugger:FetchedVariables", function testA() {
|
||||
// We expect 2 Debugger:FetchedVariables events, one from the global object
|
||||
// scope and the regular one.
|
||||
@ -48,7 +48,7 @@ function testWithFrame()
|
||||
gDebugger.DebuggerView.Options._togglePauseOnExceptions();
|
||||
|
||||
gCount = 0;
|
||||
gPane.contentWindow.gClient.addOneTimeListener("resumed", function() {
|
||||
gPane.panelWin.gClient.addOneTimeListener("resumed", function() {
|
||||
gDebugger.addEventListener("Debugger:FetchedVariables", function testB() {
|
||||
// We expect 2 Debugger:FetchedVariables events, one from the global object
|
||||
// scope and the regular one.
|
||||
@ -96,7 +96,7 @@ function testWithFrame()
|
||||
}
|
||||
|
||||
function resumeAndFinish() {
|
||||
gPane.contentWindow.gClient.addOneTimeListener("resumed", function() {
|
||||
gPane.panelWin.gClient.addOneTimeListener("resumed", function() {
|
||||
Services.tm.currentThread.dispatch({ run: function() {
|
||||
|
||||
closeDebuggerAndFinish(false);
|
||||
|
@ -15,7 +15,7 @@ function test() {
|
||||
debug_tab_pane(STACK_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gView = gDebugger.DebuggerView;
|
||||
gLH = gDebugger.LayoutHelpers;
|
||||
gL10N = gDebugger.L10N;
|
||||
|
@ -18,7 +18,7 @@ function test() {
|
||||
debug_tab_pane(TEST_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
let gDebugger = gPane.contentWindow;
|
||||
let gDebugger = gPane.panelWin;
|
||||
|
||||
is(gDebugger.DebuggerController._isInitialized, true,
|
||||
"Controller should be initialized after debug_tab_pane.");
|
||||
|
@ -13,7 +13,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -13,7 +13,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -13,7 +13,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -13,7 +13,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -13,7 +13,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -13,7 +13,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -17,7 +17,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testFrameParameters();
|
||||
});
|
||||
|
@ -17,7 +17,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testFrameParameters();
|
||||
});
|
||||
|
@ -19,7 +19,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
gDebugger.DebuggerView.Variables.nonEnumVisible = false;
|
||||
|
@ -19,7 +19,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
gDebugger.DebuggerView.Variables.nonEnumVisible = false;
|
||||
|
@ -18,7 +18,7 @@ function test()
|
||||
debug_tab_pane(TAB1_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gVariablesView = gDebugger.DebuggerView.Variables;
|
||||
|
||||
testVariablesView();
|
||||
|
@ -18,7 +18,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
gDebugger.DebuggerView.Variables.nonEnumVisible = false;
|
||||
|
@ -21,7 +21,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
|
@ -21,7 +21,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
|
@ -24,7 +24,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
testSearchbox();
|
||||
|
@ -24,7 +24,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
testSearchbox();
|
||||
|
@ -21,7 +21,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
|
@ -21,7 +21,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = false;
|
||||
|
@ -21,7 +21,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
|
@ -21,7 +21,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
gDebugger.DebuggerController.StackFrames.autoScopeExpand = true;
|
||||
|
@ -20,7 +20,7 @@ function test()
|
||||
debug_tab_pane(TAB_URL, function(aTab, aDebuggee, aPane) {
|
||||
gTab = aTab;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebuggee = aDebuggee;
|
||||
|
||||
addBreakpoint();
|
||||
|
@ -28,7 +28,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gView = gDebugger.DebuggerView;
|
||||
resumed = true;
|
||||
|
||||
|
@ -25,7 +25,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
resumed = true;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -24,7 +24,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebugger.SourceResults.prototype.alwaysExpand = false;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -26,7 +26,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebugger.SourceResults.prototype.alwaysExpand = false;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -27,7 +27,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebugger.SourceResults.prototype.alwaysExpand = false;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -27,7 +27,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebugger.SourceResults.prototype.alwaysExpand = false;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -27,7 +27,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebugger.SourceResults.prototype.alwaysExpand = false;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -27,7 +27,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebugger.SourceResults.prototype.alwaysExpand = false;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -28,7 +28,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebugger.SourceResults.prototype.alwaysExpand = false;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -27,7 +27,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gDebugger.SourceResults.prototype.alwaysExpand = false;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
|
@ -18,7 +18,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
runTest();
|
||||
|
@ -13,7 +13,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -24,7 +24,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSelectLine();
|
||||
});
|
||||
|
@ -14,7 +14,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testSimpleCall();
|
||||
});
|
||||
|
@ -14,7 +14,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testEvalCall();
|
||||
});
|
||||
|
@ -14,7 +14,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testRecurse();
|
||||
});
|
||||
|
@ -14,7 +14,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
testEvalCallResume();
|
||||
});
|
||||
|
@ -22,7 +22,7 @@ function test() {
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
|
||||
gDebugger.DebuggerController.activeThread.addOneTimeListener("framesadded", function() {
|
||||
framesAdded = true;
|
||||
|
@ -29,7 +29,7 @@ function test()
|
||||
gTab = aTab;
|
||||
gDebuggee = aDebuggee;
|
||||
gPane = aPane;
|
||||
gDebugger = gPane.contentWindow;
|
||||
gDebugger = gPane.panelWin;
|
||||
gScripts = gDebugger.DebuggerView.Sources._container;
|
||||
resumed = true;
|
||||
|
||||
|
@ -14,6 +14,10 @@ let DebuggerServer = tempScope.DebuggerServer;
|
||||
let DebuggerTransport = tempScope.DebuggerTransport;
|
||||
let DebuggerClient = tempScope.DebuggerClient;
|
||||
let Services = tempScope.Services;
|
||||
Cu.import("resource:///modules/devtools/gDevTools.jsm", tempScope);
|
||||
let gDevTools = tempScope.gDevTools;
|
||||
Cu.import("resource:///modules/devtools/Target.jsm", tempScope);
|
||||
let TargetFactory = tempScope.TargetFactory;
|
||||
|
||||
const EXAMPLE_URL = "http://example.com/browser/browser/devtools/debugger/test/";
|
||||
const TAB1_URL = EXAMPLE_URL + "browser_dbg_tab1.html";
|
||||
@ -86,11 +90,25 @@ function removeTab(aTab, aWindow) {
|
||||
}
|
||||
|
||||
function closeDebuggerAndFinish(aRemoteFlag, aCallback, aWindow) {
|
||||
let targetWindow = aWindow || window;
|
||||
let debuggerUI = targetWindow.DebuggerUI;
|
||||
|
||||
let debuggerClosed = false;
|
||||
let debuggerDisconnected = false;
|
||||
// let targetWindow = aWindow || window;
|
||||
ok(gTab, "There is a gTab to use for getting a toolbox reference");
|
||||
let target = TargetFactory.forTab(gTab);
|
||||
|
||||
// let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
window.addEventListener("Debugger:Shutdown", function cleanup() {
|
||||
window.removeEventListener("Debugger:Shutdown", cleanup, false);
|
||||
debuggerDisconnected = true;
|
||||
_maybeFinish();
|
||||
}, false);
|
||||
|
||||
let toolbox = gDevTools.getToolboxForTarget(target);
|
||||
toolbox.once("destroyed", function() {
|
||||
debuggerClosed = true;
|
||||
_maybeFinish();
|
||||
});
|
||||
toolbox.destroy();
|
||||
|
||||
function _maybeFinish() {
|
||||
if (debuggerClosed && debuggerDisconnected) {
|
||||
@ -100,20 +118,15 @@ function closeDebuggerAndFinish(aRemoteFlag, aCallback, aWindow) {
|
||||
}
|
||||
}
|
||||
|
||||
debuggerUI.chromeWindow.addEventListener("Debugger:Shutdown", function cleanup() {
|
||||
debuggerUI.chromeWindow.removeEventListener("Debugger:Shutdown", cleanup, false);
|
||||
debuggerDisconnected = true;
|
||||
_maybeFinish();
|
||||
}, false);
|
||||
if (!aRemoteFlag) {
|
||||
debuggerUI.getDebugger().close(function() {
|
||||
debuggerClosed = true;
|
||||
_maybeFinish();
|
||||
});
|
||||
} else {
|
||||
debuggerClosed = true;
|
||||
debuggerUI.getRemoteDebugger().close();
|
||||
}
|
||||
// if (!aRemoteFlag) {
|
||||
// dbg.getDebugger().close(function() {
|
||||
// debuggerClosed = true;
|
||||
// _maybeFinish();
|
||||
// });
|
||||
// } else {
|
||||
// debuggerClosed = true;
|
||||
// dbg.getRemoteDebugger().close();
|
||||
// }
|
||||
}
|
||||
|
||||
function get_tab_actor_for_url(aClient, aURL, aCallback) {
|
||||
@ -129,7 +142,7 @@ function get_tab_actor_for_url(aClient, aURL, aCallback) {
|
||||
|
||||
function attach_tab_actor_for_url(aClient, aURL, aCallback) {
|
||||
get_tab_actor_for_url(aClient, aURL, function(actor) {
|
||||
aClient.request({ to: actor.actor, type: "attach" }, function(aResponse) {
|
||||
aClient.attachTab(actor.actor, function(aResponse) {
|
||||
aCallback(actor, aResponse);
|
||||
});
|
||||
});
|
||||
@ -137,45 +150,44 @@ function attach_tab_actor_for_url(aClient, aURL, aCallback) {
|
||||
|
||||
function attach_thread_actor_for_url(aClient, aURL, aCallback) {
|
||||
attach_tab_actor_for_url(aClient, aURL, function(aTabActor, aResponse) {
|
||||
aClient.request({ "to": actor.threadActor, "type": "attach" }, function(aResponse) {
|
||||
aClient.attachThread(actor.threadActor, function(aResponse, aThreadClient) {
|
||||
// We don't care about the pause right now (use
|
||||
// get_actor_for_url() if you do), so resume it.
|
||||
aClient.request({ to: actor.threadActor, type: "resume" }, function(aResponse) {
|
||||
aThreadClient.resume(function(aResponse) {
|
||||
aCallback(actor);
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function wait_for_connect_and_resume(aOnDebugging, aWindow) {
|
||||
let targetWindow = aWindow || window;
|
||||
let targetDocument = targetWindow.document;
|
||||
|
||||
targetDocument.addEventListener("Debugger:Connected", function dbgConnected(aEvent) {
|
||||
targetDocument.removeEventListener("Debugger:Connected", dbgConnected, true);
|
||||
|
||||
function wait_for_connect_and_resume(aOnDebugging, aTab) {
|
||||
let target = TargetFactory.forTab(aTab);
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
dbg.once("connected", function dbgConnected() {
|
||||
// Wait for the initial resume...
|
||||
aEvent.target.ownerDocument.defaultView.gClient.addOneTimeListener("resumed", function() {
|
||||
dbg.panelWin.gClient.addOneTimeListener("resumed", function() {
|
||||
aOnDebugging();
|
||||
});
|
||||
}, true);
|
||||
});
|
||||
}
|
||||
|
||||
function debug_tab_pane(aURL, aOnDebugging) {
|
||||
let tab = addTab(aURL, function() {
|
||||
gBrowser.selectedTab = gTab;
|
||||
let debuggee = tab.linkedBrowser.contentWindow.wrappedJSObject;
|
||||
let debuggee = gBrowser.selectedTab.linkedBrowser.contentWindow.wrappedJSObject;
|
||||
|
||||
let pane = DebuggerUI.toggleDebugger();
|
||||
pane._frame.addEventListener("Debugger:Connected", function dbgConnected() {
|
||||
pane._frame.removeEventListener("Debugger:Connected", dbgConnected, true);
|
||||
|
||||
// Wait for the initial resume...
|
||||
pane.contentWindow.gClient.addOneTimeListener("resumed", function() {
|
||||
pane.contentWindow.DebuggerView.Variables.lazyEmpty = false;
|
||||
aOnDebugging(tab, debuggee, pane);
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
let toolbox = gDevTools.openToolboxForTab(target, "jsdebugger");
|
||||
toolbox.once("jsdebugger-ready", function dbgReady() {
|
||||
let dbg = gDevTools.getPanelForTarget("jsdebugger", target);
|
||||
dbg.once("connected", function() {
|
||||
// Wait for the initial resume...
|
||||
dbg.panelWin.gClient.addOneTimeListener("resumed", function() {
|
||||
dbg._view.Variables.lazyEmpty = false;
|
||||
aOnDebugging(tab, debuggee, dbg);
|
||||
});
|
||||
});
|
||||
}, true);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
@ -192,7 +204,7 @@ function debug_remote(aURL, aOnDebugging, aBeforeTabAdded) {
|
||||
win._dbgwin.removeEventListener("Debugger:Connected", dbgConnected, true);
|
||||
|
||||
// Wait for the initial resume...
|
||||
win.contentWindow.gClient.addOneTimeListener("resumed", function() {
|
||||
win.panelWin.gClient.addOneTimeListener("resumed", function() {
|
||||
win._dbgwin.DebuggerView.Variables.lazyEmpty = false;
|
||||
aOnDebugging(tab, debuggee, win);
|
||||
});
|
||||
|
@ -10,17 +10,9 @@ VPATH = @srcdir@
|
||||
|
||||
include $(DEPTH)/config/autoconf.mk
|
||||
|
||||
EXTRA_JS_MODULES = \
|
||||
highlighter.jsm \
|
||||
$(NULL)
|
||||
|
||||
EXTRA_PP_JS_MODULES = \
|
||||
inspector.jsm \
|
||||
$(NULL)
|
||||
|
||||
TEST_DIRS += test
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
libs::
|
||||
$(NSINSTALL) $(srcdir)/CmdInspect.jsm $(FINAL_TARGET)/modules/devtools
|
||||
$(NSINSTALL) $(srcdir)/*.jsm $(FINAL_TARGET)/modules/devtools
|
191
browser/devtools/framework/Sidebar.jsm
Normal file
191
browser/devtools/framework/Sidebar.jsm
Normal file
@ -0,0 +1,191 @@
|
||||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ft=javascript ts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
const Cc = Components.classes;
|
||||
const Cu = Components.utils;
|
||||
const Ci = Components.interfaces;
|
||||
|
||||
this.EXPORTED_SYMBOLS = ["ToolSidebar"];
|
||||
|
||||
Cu.import("resource:///modules/devtools/EventEmitter.jsm");
|
||||
|
||||
const XULNS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
|
||||
|
||||
/**
|
||||
* ToolSidebar provides methods to register tabs in the sidebar.
|
||||
* It's assumed that the sidebar contains a xul:tabbox.
|
||||
*
|
||||
* @param {Node} tabbox
|
||||
* <tabbox> node;
|
||||
* @param {ToolPanel} panel
|
||||
* Related ToolPanel instance;
|
||||
* @param {Boolean} showTabstripe
|
||||
* Show the tabs.
|
||||
*/
|
||||
this.ToolSidebar = function ToolSidebar(tabbox, panel, showTabstripe=true)
|
||||
{
|
||||
new EventEmitter(this);
|
||||
|
||||
this._tabbox = tabbox;
|
||||
this._panelDoc = this._tabbox.ownerDocument;
|
||||
this._toolPanel = panel;
|
||||
|
||||
this._tabbox.tabpanels.addEventListener("select", this, true);
|
||||
|
||||
this._tabs = new Map();
|
||||
|
||||
if (!showTabstripe) {
|
||||
this._tabbox.setAttribute("hidetabs", "true");
|
||||
}
|
||||
}
|
||||
|
||||
ToolSidebar.prototype = {
|
||||
/**
|
||||
* Register a tab. A tab is a document.
|
||||
* The document must have a title, which will be used as the name of the tab.
|
||||
*
|
||||
* @param {string} tab uniq id
|
||||
* @param {string} url
|
||||
*/
|
||||
addTab: function ToolSidebar_addTab(id, url, selected=false) {
|
||||
let iframe = this._panelDoc.createElementNS(XULNS, "iframe");
|
||||
iframe.className = "iframe-" + id;
|
||||
iframe.setAttribute("flex", "1");
|
||||
iframe.setAttribute("src", url);
|
||||
|
||||
let tab = this._tabbox.tabs.appendItem();
|
||||
|
||||
let onIFrameLoaded = function() {
|
||||
tab.setAttribute("label", iframe.contentDocument.title);
|
||||
iframe.removeEventListener("DOMContentLoaded", onIFrameLoaded, true);
|
||||
if ("setPanel" in iframe.contentWindow) {
|
||||
iframe.contentWindow.setPanel(this._toolPanel, iframe);
|
||||
}
|
||||
this.emit(id + "-ready");
|
||||
}.bind(this);
|
||||
|
||||
iframe.addEventListener("DOMContentLoaded", onIFrameLoaded, true);
|
||||
|
||||
let tabpanel = this._panelDoc.createElementNS(XULNS, "tabpanel");
|
||||
tabpanel.setAttribute("id", "sidebar-panel-" + id);
|
||||
tabpanel.appendChild(iframe);
|
||||
this._tabbox.tabpanels.appendChild(tabpanel);
|
||||
|
||||
tab.linkedPanel = "sidebar-panel-" + id;
|
||||
|
||||
// We store the index of this tab.
|
||||
this._tabs.set(id, tab);
|
||||
|
||||
if (selected) {
|
||||
// For some reason I don't understand, if we call this.select in this
|
||||
// event loop (after inserting the tab), the tab will never get the
|
||||
// the "selected" attribute set to true.
|
||||
this._panelDoc.defaultView.setTimeout(function() {
|
||||
this.select(id);
|
||||
}.bind(this), 0);
|
||||
}
|
||||
|
||||
this.emit("new-tab-registered", id);
|
||||
},
|
||||
|
||||
/**
|
||||
* Select a specific tab.
|
||||
*/
|
||||
select: function ToolSidebar_select(id) {
|
||||
let tab = this._tabs.get(id);
|
||||
if (tab) {
|
||||
this._tabbox.selectedTab = tab;
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Return the id of the selected tab.
|
||||
*/
|
||||
getCurrentTabID: function ToolSidebar_getCurrentTabID() {
|
||||
let currentID = null;
|
||||
for (let [id, tab] of this._tabs) {
|
||||
if (this._tabbox.tabs.selectedItem == tab) {
|
||||
currentID = id;
|
||||
break;
|
||||
}
|
||||
}
|
||||
return currentID;
|
||||
},
|
||||
|
||||
/**
|
||||
* Event handler.
|
||||
*/
|
||||
handleEvent: function ToolSidebar_eventHandler(event) {
|
||||
if (event.type == "select") {
|
||||
let previousTool = this._currentTool;
|
||||
this._currentTool = this.getCurrentTabID();
|
||||
if (previousTool) {
|
||||
this.emit(previousTool + "-unselected");
|
||||
}
|
||||
|
||||
this.emit(this._currentTool + "-selected");
|
||||
this.emit("select", this._currentTool);
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Toggle sidebar's visibility state.
|
||||
*/
|
||||
toggle: function ToolSidebar_toggle() {
|
||||
if (this._tabbox.hasAttribute("hidden")) {
|
||||
this.show();
|
||||
} else {
|
||||
this.hide();
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Show the sidebar.
|
||||
*/
|
||||
show: function ToolSidebar_show() {
|
||||
this._tabbox.removeAttribute("hidden");
|
||||
},
|
||||
|
||||
/**
|
||||
* Show the sidebar.
|
||||
*/
|
||||
hide: function ToolSidebar_hide() {
|
||||
this._tabbox.setAttribute("hidden", "true");
|
||||
},
|
||||
|
||||
/**
|
||||
* Return the window containing the tab content.
|
||||
*/
|
||||
getWindowForTab: function ToolSidebar_getWindowForTab(id) {
|
||||
if (!this._tabs.has(id)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
let panel = this._panelDoc.getElementById(this._tabs.get(id).linkedPanel);
|
||||
return panel.firstChild.contentWindow;
|
||||
},
|
||||
|
||||
/**
|
||||
* Clean-up.
|
||||
*/
|
||||
destroy: function ToolSidebar_destroy() {
|
||||
this._tabbox.removeEventListener("select", this, true);
|
||||
|
||||
while (this._tabbox.tabpanels.hasChildNodes()) {
|
||||
this._tabbox.tabpanels.removeChild(this._tabbox.tabpanels.firstChild);
|
||||
}
|
||||
|
||||
while (this._tabbox.tabs.hasChildNodes()) {
|
||||
this._tabbox.tabs.removeChild(this._tabbox.tabs.firstChild);
|
||||
}
|
||||
|
||||
this._tabs = null;
|
||||
this._tabbox = null;
|
||||
this._panelDoc = null;
|
||||
this._toolPanel = null;
|
||||
},
|
||||
}
|
385
browser/devtools/framework/Target.jsm
Normal file
385
browser/devtools/framework/Target.jsm
Normal file
@ -0,0 +1,385 @@
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
this.EXPORTED_SYMBOLS = [ "TargetFactory" ];
|
||||
|
||||
const Cu = Components.utils;
|
||||
const Ci = Components.interfaces;
|
||||
Cu.import("resource:///modules/devtools/EventEmitter.jsm");
|
||||
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
|
||||
|
||||
|
||||
const targets = new WeakMap();
|
||||
|
||||
/**
|
||||
* Functions for creating Targets
|
||||
*/
|
||||
this.TargetFactory = {
|
||||
/**
|
||||
* Construct a Target
|
||||
* @param {XULTab} tab
|
||||
* The tab to use in creating a new target
|
||||
* @return A target object
|
||||
*/
|
||||
forTab: function TF_forTab(tab) {
|
||||
let target = targets.get(tab);
|
||||
if (target == null) {
|
||||
target = new TabTarget(tab);
|
||||
targets.set(tab, target);
|
||||
}
|
||||
return target;
|
||||
},
|
||||
|
||||
/**
|
||||
* Creating a target for a tab that is being closed is a problem because it
|
||||
* allows a leak as a result of coming after the close event which normally
|
||||
* clears things up. This function allows us to ask if there is a known
|
||||
* target for a tab without creating a target
|
||||
* @return true/false
|
||||
*/
|
||||
isKnownTab: function TF_isKnownTab(tab) {
|
||||
return targets.has(tab);
|
||||
},
|
||||
|
||||
/**
|
||||
* Construct a Target
|
||||
* @param {nsIDOMWindow} window
|
||||
* The chromeWindow to use in creating a new target
|
||||
* @return A target object
|
||||
*/
|
||||
forWindow: function TF_forWindow(window) {
|
||||
let target = targets.get(window);
|
||||
if (target == null) {
|
||||
target = new WindowTarget(window);
|
||||
targets.set(window, target);
|
||||
}
|
||||
return target;
|
||||
},
|
||||
|
||||
/**
|
||||
* Construct a Target for a remote global
|
||||
* @param {Object} form
|
||||
* The serialized form of a debugging protocol actor.
|
||||
* @param {DebuggerClient} client
|
||||
* The debuger client instance to communicate with the server.
|
||||
* @param {boolean} chrome
|
||||
* A flag denoting that the debugging target is the remote process as a
|
||||
* whole and not a single tab.
|
||||
* @return A target object
|
||||
*/
|
||||
forRemote: function TF_forRemote(form, client, chrome) {
|
||||
let target = targets.get(form);
|
||||
if (target == null) {
|
||||
target = new RemoteTarget(form, client, chrome);
|
||||
targets.set(form, target);
|
||||
}
|
||||
return target;
|
||||
},
|
||||
|
||||
/**
|
||||
* Get all of the targets known to some browser instance (local if null)
|
||||
* @return An array of target objects
|
||||
*/
|
||||
allTargets: function TF_allTargets() {
|
||||
let windows = [];
|
||||
let wm = Components.classes["@mozilla.org/appshell/window-mediator;1"]
|
||||
.getService(Components.interfaces.nsIWindowMediator);
|
||||
let en = wm.getXULWindowEnumerator(null);
|
||||
while (en.hasMoreElements()) {
|
||||
windows.push(en.getNext());
|
||||
}
|
||||
|
||||
return windows.map(function(window) {
|
||||
return TargetFactory.forWindow(window);
|
||||
});
|
||||
},
|
||||
};
|
||||
|
||||
/**
|
||||
* The 'version' property allows the developer tools equivalent of browser
|
||||
* detection. Browser detection is evil, however while we don't know what we
|
||||
* will need to detect in the future, it is an easy way to postpone work.
|
||||
* We should be looking to use 'supports()' in place of version where
|
||||
* possible.
|
||||
*/
|
||||
function getVersion() {
|
||||
// FIXME: return something better
|
||||
return 20;
|
||||
}
|
||||
|
||||
/**
|
||||
* A better way to support feature detection, but we're not yet at a place
|
||||
* where we have the features well enough defined for this to make lots of
|
||||
* sense.
|
||||
*/
|
||||
function supports(feature) {
|
||||
// FIXME: return something better
|
||||
return false;
|
||||
};
|
||||
|
||||
/**
|
||||
* A Target represents something that we can debug. Targets are generally
|
||||
* read-only. Any changes that you wish to make to a target should be done via
|
||||
* a Tool that attaches to the target. i.e. a Target is just a pointer saying
|
||||
* "the thing to debug is over there".
|
||||
*
|
||||
* Providing a generalized abstraction of a web-page or web-browser (available
|
||||
* either locally or remotely) is beyond the scope of this class (and maybe
|
||||
* also beyond the scope of this universe) However Target does attempt to
|
||||
* abstract some common events and read-only properties common to many Tools.
|
||||
*
|
||||
* Supported read-only properties:
|
||||
* - name, isRemote, url
|
||||
*
|
||||
* Target extends EventEmitter and provides support for the following events:
|
||||
* - close: The target window has been closed. All tools attached to this
|
||||
* target should close. This event is not currently cancelable.
|
||||
* - navigate: The target window has navigated to a different URL
|
||||
*
|
||||
* Optional events:
|
||||
* - will-navigate: The target window will navigate to a different URL
|
||||
* - hidden: The target is not visible anymore (for TargetTab, another tab is selected)
|
||||
* - visible: The target is visible (for TargetTab, tab is selected)
|
||||
*
|
||||
* Target also supports 2 functions to help allow 2 different versions of
|
||||
* Firefox debug each other. The 'version' property is the equivalent of
|
||||
* browser detection - simple and easy to implement but gets fragile when things
|
||||
* are not quite what they seem. The 'supports' property is the equivalent of
|
||||
* feature detection - harder to setup, but more robust long-term.
|
||||
*
|
||||
* Comparing Targets: 2 instances of a Target object can point at the same
|
||||
* thing, so t1 !== t2 and t1 != t2 even when they represent the same object.
|
||||
* To compare to targets use 't1.equals(t2)'.
|
||||
*/
|
||||
function Target() {
|
||||
throw new Error("Use TargetFactory.newXXX or Target.getXXX to create a Target in place of 'new Target()'");
|
||||
}
|
||||
|
||||
Object.defineProperty(Target.prototype, "version", {
|
||||
get: getVersion,
|
||||
enumerable: true
|
||||
});
|
||||
|
||||
|
||||
/**
|
||||
* A TabTarget represents a page living in a browser tab. Generally these will
|
||||
* be web pages served over http(s), but they don't have to be.
|
||||
*/
|
||||
function TabTarget(tab) {
|
||||
new EventEmitter(this);
|
||||
this._tab = tab;
|
||||
this._setupListeners();
|
||||
}
|
||||
|
||||
TabTarget.prototype = {
|
||||
_webProgressListener: null,
|
||||
|
||||
supports: supports,
|
||||
get version() { return getVersion(); },
|
||||
|
||||
get tab() {
|
||||
return this._tab;
|
||||
},
|
||||
|
||||
get name() {
|
||||
return this._tab.linkedBrowser.contentDocument.title;
|
||||
},
|
||||
|
||||
get url() {
|
||||
return this._tab.linkedBrowser.contentDocument.location.href;
|
||||
},
|
||||
|
||||
get isRemote() {
|
||||
return false;
|
||||
},
|
||||
|
||||
/**
|
||||
* Listen to the different tabs events.
|
||||
*/
|
||||
_setupListeners: function TabTarget__setupListeners() {
|
||||
this._webProgressListener = new TabWebProgressListener(this);
|
||||
this.tab.linkedBrowser.addProgressListener(this._webProgressListener);
|
||||
this.tab.addEventListener("TabClose", this);
|
||||
this.tab.parentNode.addEventListener("TabSelect", this);
|
||||
},
|
||||
|
||||
/**
|
||||
* Handle tabs events.
|
||||
*/
|
||||
handleEvent: function (event) {
|
||||
switch (event.type) {
|
||||
case "TabClose":
|
||||
this.destroy();
|
||||
break;
|
||||
case "TabSelect":
|
||||
if (this.tab.selected) {
|
||||
this.emit("visible", event);
|
||||
} else {
|
||||
this.emit("hidden", event);
|
||||
}
|
||||
break;
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Target is not alive anymore.
|
||||
*/
|
||||
destroy: function() {
|
||||
if (this._destroyed) {
|
||||
return;
|
||||
}
|
||||
this.tab.linkedBrowser.removeProgressListener(this._webProgressListener)
|
||||
this._webProgressListener.target = null;
|
||||
this._webProgressListener = null;
|
||||
this.tab.removeEventListener("TabClose", this);
|
||||
this.tab.parentNode.removeEventListener("TabSelect", this);
|
||||
this._destroyed = true;
|
||||
this.emit("close");
|
||||
|
||||
targets.delete(this._tab);
|
||||
this._tab = null;
|
||||
},
|
||||
|
||||
toString: function() {
|
||||
return 'TabTarget:' + this.tab;
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* WebProgressListener for TabTarget.
|
||||
*
|
||||
* @param object aTarget
|
||||
* The TabTarget instance to work with.
|
||||
*/
|
||||
function TabWebProgressListener(aTarget) {
|
||||
this.target = aTarget;
|
||||
}
|
||||
|
||||
TabWebProgressListener.prototype = {
|
||||
target: null,
|
||||
|
||||
QueryInterface: XPCOMUtils.generateQI([Ci.nsIWebProgressListener, Ci.nsISupportsWeakReference]),
|
||||
|
||||
onStateChange: function TWPL_onStateChange(progress, request, flag, status) {
|
||||
let isStart = flag & Ci.nsIWebProgressListener.STATE_START;
|
||||
let isDocument = flag & Ci.nsIWebProgressListener.STATE_IS_DOCUMENT;
|
||||
let isNetwork = flag & Ci.nsIWebProgressListener.STATE_IS_NETWORK;
|
||||
let isRequest = flag & Ci.nsIWebProgressListener.STATE_IS_REQUEST;
|
||||
|
||||
// Skip non-interesting states.
|
||||
if (!isStart || !isDocument || !isRequest || !isNetwork) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (this.target) {
|
||||
this.target.emit("will-navigate", request);
|
||||
}
|
||||
},
|
||||
|
||||
onProgressChange: function() {},
|
||||
onSecurityChange: function() {},
|
||||
onStatusChange: function() {},
|
||||
|
||||
onLocationChange: function TwPL_onLocationChange(webProgress) {
|
||||
let window = webProgress.DOMWindow;
|
||||
if (this.target) {
|
||||
this.target.emit("navigate", window);
|
||||
}
|
||||
},
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* A WindowTarget represents a page living in a xul window or panel. Generally
|
||||
* these will have a chrome: URL
|
||||
*/
|
||||
function WindowTarget(window) {
|
||||
new EventEmitter(this);
|
||||
this._window = window;
|
||||
}
|
||||
|
||||
WindowTarget.prototype = {
|
||||
supports: supports,
|
||||
get version() { return getVersion(); },
|
||||
|
||||
get window() {
|
||||
return this._window;
|
||||
},
|
||||
|
||||
get name() {
|
||||
return this._window.document.title;
|
||||
},
|
||||
|
||||
get url() {
|
||||
return this._window.document.location.href;
|
||||
},
|
||||
|
||||
get isRemote() {
|
||||
return false;
|
||||
},
|
||||
|
||||
toString: function() {
|
||||
return 'WindowTarget:' + this.window;
|
||||
},
|
||||
};
|
||||
|
||||
/**
|
||||
* A RemoteTarget represents a page living in a remote Firefox instance.
|
||||
*/
|
||||
function RemoteTarget(form, client, chrome) {
|
||||
new EventEmitter(this);
|
||||
this._client = client;
|
||||
this._form = form;
|
||||
this._chrome = chrome;
|
||||
|
||||
this.destroy = this.destroy.bind(this);
|
||||
this.client.addListener("tabDetached", this.destroy);
|
||||
|
||||
this._onTabNavigated = function onRemoteTabNavigated() {
|
||||
this.emit("navigate");
|
||||
}.bind(this);
|
||||
this.client.addListener("tabNavigated", this._onTabNavigated);
|
||||
}
|
||||
|
||||
RemoteTarget.prototype = {
|
||||
supports: supports,
|
||||
get version() getVersion(),
|
||||
|
||||
get isRemote() true,
|
||||
|
||||
get chrome() this._chrome,
|
||||
|
||||
get name() this._form._title,
|
||||
|
||||
get url() this._form._url,
|
||||
|
||||
get client() this._client,
|
||||
|
||||
get form() this._form,
|
||||
|
||||
/**
|
||||
* Target is not alive anymore.
|
||||
*/
|
||||
destroy: function RT_destroy() {
|
||||
if (this._destroyed) {
|
||||
return;
|
||||
}
|
||||
this.client.removeListener("tabNavigated", this._onTabNavigated);
|
||||
this.client.removeListener("tabDetached", this.destroy);
|
||||
|
||||
this._client.close(function onClosed() {
|
||||
this._client = null;
|
||||
this._destroyed = true;
|
||||
this.emit("close");
|
||||
}.bind(this));
|
||||
},
|
||||
|
||||
toString: function() {
|
||||
return 'RemoteTarget:' + this.form.actor;
|
||||
},
|
||||
};
|
19
browser/devtools/framework/ToolDefinitions.jsm
Normal file
19
browser/devtools/framework/ToolDefinitions.jsm
Normal file
@ -0,0 +1,19 @@
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
this.EXPORTED_SYMBOLS = [ "defaultTools" ];
|
||||
|
||||
Components.utils.import("resource:///modules/WebConsolePanel.jsm");
|
||||
Components.utils.import("resource:///modules/devtools/DebuggerPanel.jsm");
|
||||
Components.utils.import("resource:///modules/devtools/StyleEditorDefinition.jsm");
|
||||
Components.utils.import("resource:///modules/devtools/InspectorDefinition.jsm");
|
||||
|
||||
this.defaultTools = [
|
||||
StyleEditorDefinition,
|
||||
WebConsoleDefinition,
|
||||
DebuggerDefinition,
|
||||
InspectorDefinition,
|
||||
];
|
523
browser/devtools/framework/Toolbox.jsm
Normal file
523
browser/devtools/framework/Toolbox.jsm
Normal file
@ -0,0 +1,523 @@
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
const { classes: Cc, interfaces: Ci, utils: Cu } = Components;
|
||||
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource:///modules/devtools/EventEmitter.jsm");
|
||||
Cu.import("resource:///modules/devtools/ToolboxHosts.jsm");
|
||||
Cu.import("resource:///modules/devtools/gcli.jsm");
|
||||
Cu.import('resource://gre/modules/XPCOMUtils.jsm');
|
||||
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "gDevTools",
|
||||
"resource:///modules/devtools/gDevTools.jsm");
|
||||
XPCOMUtils.defineLazyModuleGetter(this, "CommandUtils",
|
||||
"resource:///modules/devtools/DeveloperToolbar.jsm");
|
||||
|
||||
Components.utils.import("resource://gre/modules/devtools/Require.jsm");
|
||||
|
||||
let Requisition = require('gcli/cli').Requisition;
|
||||
let CommandOutputManager = require('gcli/canon').CommandOutputManager;
|
||||
|
||||
this.EXPORTED_SYMBOLS = [ "Toolbox" ];
|
||||
|
||||
/**
|
||||
* A "Toolbox" is the component that holds all the tools for one specific
|
||||
* target. Visually, it's a document that includes the tools tabs and all
|
||||
* the iframes where the tool panels will be living in.
|
||||
*
|
||||
* @param {object} target
|
||||
* The object the toolbox is debugging.
|
||||
* @param {Toolbox.HostType} hostType
|
||||
* Type of host that will host the toolbox (e.g. sidebar, window)
|
||||
* @param {string} selectedTool
|
||||
* Tool to select initially
|
||||
*/
|
||||
this.Toolbox = function Toolbox(target, hostType, selectedTool) {
|
||||
this._target = target;
|
||||
this._toolPanels = new Map();
|
||||
|
||||
this._onLoad = this._onLoad.bind(this);
|
||||
this._toolRegistered = this._toolRegistered.bind(this);
|
||||
this._toolUnregistered = this._toolUnregistered.bind(this);
|
||||
this.destroy = this.destroy.bind(this);
|
||||
|
||||
this._target.once("close", this.destroy);
|
||||
|
||||
if (!hostType) {
|
||||
hostType = Services.prefs.getCharPref(this._prefs.LAST_HOST);
|
||||
}
|
||||
if (!selectedTool) {
|
||||
selectedTool = Services.prefs.getCharPref(this._prefs.LAST_TOOL);
|
||||
}
|
||||
let definitions = gDevTools.getToolDefinitions();
|
||||
if (!definitions.get(selectedTool)) {
|
||||
selectedTool = "webconsole";
|
||||
}
|
||||
this._defaultToolId = selectedTool;
|
||||
|
||||
this._host = this._createHost(hostType);
|
||||
|
||||
new EventEmitter(this);
|
||||
|
||||
gDevTools.on("tool-registered", this._toolRegistered);
|
||||
gDevTools.on("tool-unregistered", this._toolUnregistered);
|
||||
}
|
||||
|
||||
/**
|
||||
* The toolbox can be 'hosted' either embedded in a browser window
|
||||
* or in a separate window.
|
||||
*/
|
||||
Toolbox.HostType = {
|
||||
BOTTOM: "bottom",
|
||||
SIDE: "side",
|
||||
WINDOW: "window"
|
||||
}
|
||||
|
||||
Toolbox.prototype = {
|
||||
_URL: "chrome://browser/content/devtools/framework/toolbox.xul",
|
||||
|
||||
_prefs: {
|
||||
LAST_HOST: "devtools.toolbox.host",
|
||||
LAST_TOOL: "devtools.toolbox.selectedTool",
|
||||
SIDE_ENABLED: "devtools.toolbox.sideEnabled"
|
||||
},
|
||||
|
||||
HostType: Toolbox.HostType,
|
||||
|
||||
/**
|
||||
* Returns a *copy* of the _toolPanels collection.
|
||||
*
|
||||
* @return {Map} panels
|
||||
* All the running panels in the toolbox
|
||||
*/
|
||||
getToolPanels: function TB_getToolPanels() {
|
||||
let panels = new Map();
|
||||
|
||||
for (let [key, value] of this._toolPanels) {
|
||||
panels.set(key, value);
|
||||
}
|
||||
return panels;
|
||||
},
|
||||
|
||||
/**
|
||||
* Get/alter the target of a Toolbox so we're debugging something different.
|
||||
* See Target.jsm for more details.
|
||||
* TODO: Do we allow |toolbox.target = null;| ?
|
||||
*/
|
||||
get target() {
|
||||
return this._target;
|
||||
},
|
||||
|
||||
set target(value) {
|
||||
this._target = value;
|
||||
},
|
||||
|
||||
/**
|
||||
* Get/alter the host of a Toolbox, i.e. is it in browser or in a separate
|
||||
* tab. See HostType for more details.
|
||||
*/
|
||||
get hostType() {
|
||||
return this._host.type;
|
||||
},
|
||||
|
||||
set hostType(value) {
|
||||
this._switchToHost(value);
|
||||
},
|
||||
|
||||
/**
|
||||
* Get/alter the currently displayed tool.
|
||||
*/
|
||||
get currentToolId() {
|
||||
return this._currentToolId;
|
||||
},
|
||||
|
||||
set currentToolId(value) {
|
||||
this._currentToolId = value;
|
||||
},
|
||||
|
||||
/**
|
||||
* Get the iframe containing the toolbox UI.
|
||||
*/
|
||||
get frame() {
|
||||
return this._host.frame;
|
||||
},
|
||||
|
||||
/**
|
||||
* Shortcut to the document containing the toolbox UI
|
||||
*/
|
||||
get doc() {
|
||||
return this.frame.contentDocument;
|
||||
},
|
||||
|
||||
/**
|
||||
* Open the toolbox
|
||||
*/
|
||||
open: function TBOX_open() {
|
||||
this._host.once("ready", function(event, iframe) {
|
||||
iframe.addEventListener("DOMContentLoaded", this._onLoad, true);
|
||||
iframe.setAttribute("src", this._URL);
|
||||
}.bind(this));
|
||||
|
||||
this._host.open();
|
||||
},
|
||||
|
||||
/**
|
||||
* Build the buttons for changing hosts. Called every time
|
||||
* the host changes.
|
||||
*/
|
||||
_buildDockButtons: function TBOX_createDockButtons() {
|
||||
let dockBox = this.doc.getElementById("toolbox-dock-buttons");
|
||||
|
||||
while (dockBox.firstChild) {
|
||||
dockBox.removeChild(dockBox.firstChild);
|
||||
}
|
||||
|
||||
let sideEnabled = Services.prefs.getBoolPref(this._prefs.SIDE_ENABLED);
|
||||
|
||||
for each (let position in this.HostType) {
|
||||
if (position == this.hostType ||
|
||||
(!sideEnabled && position == this.HostType.SIDE)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
let button = this.doc.createElement("toolbarbutton");
|
||||
button.id = "toolbox-dock-" + position;
|
||||
button.className = "toolbox-dock-button";
|
||||
button.addEventListener("command", function(position) {
|
||||
this.hostType = position;
|
||||
}.bind(this, position));
|
||||
|
||||
dockBox.appendChild(button);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Onload handler for the toolbox's iframe
|
||||
*/
|
||||
_onLoad: function TBOX_onLoad() {
|
||||
this.frame.removeEventListener("DOMContentLoaded", this._onLoad, true);
|
||||
this.isReady = true;
|
||||
|
||||
let closeButton = this.doc.getElementById("toolbox-close");
|
||||
closeButton.addEventListener("command", this.destroy, true);
|
||||
|
||||
this._buildDockButtons();
|
||||
|
||||
this._buildTabs();
|
||||
this._buildButtons(this.frame);
|
||||
|
||||
this.selectTool(this._defaultToolId);
|
||||
|
||||
this.emit("ready");
|
||||
},
|
||||
|
||||
/**
|
||||
* Add tabs to the toolbox UI for registered tools
|
||||
*/
|
||||
_buildTabs: function TBOX_buildTabs() {
|
||||
for (let [id, definition] of gDevTools.getToolDefinitions()) {
|
||||
this._buildTabForTool(definition);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Add buttons to the UI as specified in the devtools.window.toolbarSpec pref
|
||||
*
|
||||
* @param {iframe} frame
|
||||
* The iframe to contain the buttons
|
||||
*/
|
||||
_buildButtons: function TBOX_buildButtons(frame) {
|
||||
let toolbarSpec = CommandUtils.getCommandbarSpec("devtools.toolbox.toolbarSpec");
|
||||
let environment = { chromeDocument: frame.ownerDocument };
|
||||
let requisition = new Requisition(environment);
|
||||
requisition.commandOutputManager = new CommandOutputManager();
|
||||
|
||||
let buttons = CommandUtils.createButtons(toolbarSpec, this.doc, requisition);
|
||||
|
||||
let container = this.doc.getElementById("toolbox-buttons");
|
||||
buttons.forEach(function(button) {
|
||||
container.appendChild(button);
|
||||
}.bind(this));
|
||||
},
|
||||
|
||||
/**
|
||||
* Build a tab for one tool definition and add to the toolbox
|
||||
*
|
||||
* @param {string} toolDefinition
|
||||
* Tool definition of the tool to build a tab for.
|
||||
*/
|
||||
_buildTabForTool: function TBOX_buildTabForTool(toolDefinition) {
|
||||
const MAX_ORDINAL = 99;
|
||||
if (!toolDefinition.isTargetSupported(this._target)) {
|
||||
return;
|
||||
}
|
||||
|
||||
let tabs = this.doc.getElementById("toolbox-tabs");
|
||||
let deck = this.doc.getElementById("toolbox-deck");
|
||||
|
||||
let id = toolDefinition.id;
|
||||
|
||||
let radio = this.doc.createElement("radio");
|
||||
radio.setAttribute("label", toolDefinition.label);
|
||||
radio.className = "toolbox-tab devtools-tab";
|
||||
radio.id = "toolbox-tab-" + id;
|
||||
radio.setAttribute("toolid", id);
|
||||
|
||||
let ordinal = (typeof toolDefinition.ordinal == "number") ?
|
||||
toolDefinition.ordinal : MAX_ORDINAL;
|
||||
radio.setAttribute("ordinal", ordinal);
|
||||
|
||||
radio.addEventListener("command", function(id) {
|
||||
this.selectTool(id);
|
||||
}.bind(this, id));
|
||||
|
||||
let vbox = this.doc.createElement("vbox");
|
||||
vbox.className = "toolbox-panel";
|
||||
vbox.id = "toolbox-panel-" + id;
|
||||
|
||||
tabs.appendChild(radio);
|
||||
deck.appendChild(vbox);
|
||||
},
|
||||
|
||||
/**
|
||||
* Switch to the tool with the given id
|
||||
*
|
||||
* @param {string} id
|
||||
* The id of the tool to switch to
|
||||
*/
|
||||
selectTool: function TBOX_selectTool(id) {
|
||||
if (!this.isReady) {
|
||||
throw new Error("Can't select tool, wait for toolbox 'ready' event");
|
||||
}
|
||||
let tab = this.doc.getElementById("toolbox-tab-" + id);
|
||||
|
||||
if (!tab) {
|
||||
throw new Error("No tool found");
|
||||
}
|
||||
|
||||
let tabstrip = this.doc.getElementById("toolbox-tabs");
|
||||
|
||||
// select the right tab
|
||||
let index = -1;
|
||||
let tabs = tabstrip.childNodes;
|
||||
for (let i = 0; i < tabs.length; i++) {
|
||||
if (tabs[i] === tab) {
|
||||
index = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
tabstrip.selectedIndex = index;
|
||||
|
||||
// and select the right iframe
|
||||
let deck = this.doc.getElementById("toolbox-deck");
|
||||
deck.selectedIndex = index;
|
||||
|
||||
let definition = gDevTools.getToolDefinitions().get(id);
|
||||
|
||||
let iframe = this.doc.getElementById("toolbox-panel-iframe-" + id);
|
||||
if (!iframe) {
|
||||
iframe = this.doc.createElement("iframe");
|
||||
iframe.className = "toolbox-panel-iframe";
|
||||
iframe.id = "toolbox-panel-iframe-" + id;
|
||||
iframe.setAttribute("flex", 1);
|
||||
|
||||
let vbox = this.doc.getElementById("toolbox-panel-" + id);
|
||||
vbox.appendChild(iframe);
|
||||
|
||||
let boundLoad = function() {
|
||||
iframe.removeEventListener("DOMContentLoaded", boundLoad, true);
|
||||
let panel = definition.build(iframe.contentWindow, this);
|
||||
this._toolPanels.set(id, panel);
|
||||
|
||||
let panelReady = function() {
|
||||
this.emit(id + "-ready", panel);
|
||||
this.emit("select", id);
|
||||
this.emit(id + "-selected", panel);
|
||||
gDevTools.emit(id + "-ready", this, panel);
|
||||
}.bind(this);
|
||||
|
||||
if (panel.isReady) {
|
||||
panelReady();
|
||||
} else {
|
||||
panel.once("ready", panelReady);
|
||||
}
|
||||
}.bind(this);
|
||||
|
||||
iframe.addEventListener("DOMContentLoaded", boundLoad, true);
|
||||
iframe.setAttribute("src", definition.url);
|
||||
} else {
|
||||
let panel = this._toolPanels.get(id);
|
||||
// only emit 'select' event if the iframe has been loaded
|
||||
if (panel) {
|
||||
this.emit("select", id);
|
||||
this.emit(id + "-selected", panel);
|
||||
}
|
||||
}
|
||||
|
||||
Services.prefs.setCharPref(this._prefs.LAST_TOOL, id);
|
||||
|
||||
this._currentToolId = id;
|
||||
},
|
||||
|
||||
/**
|
||||
* Create a host object based on the given host type.
|
||||
*
|
||||
* @param {string} hostType
|
||||
* The host type of the new host object
|
||||
*
|
||||
* @return {Host} host
|
||||
* The created host object
|
||||
*/
|
||||
_createHost: function TBOX_createHost(hostType) {
|
||||
let hostTab = this._getHostTab();
|
||||
if (!Hosts[hostType]) {
|
||||
throw new Error('Unknown hostType: '+ hostType);
|
||||
}
|
||||
let newHost = new Hosts[hostType](hostTab);
|
||||
|
||||
// clean up the toolbox if its window is closed
|
||||
newHost.on("window-closed", this.destroy);
|
||||
|
||||
return newHost;
|
||||
},
|
||||
|
||||
/**
|
||||
* Switch to a new host for the toolbox UI. E.g.
|
||||
* bottom, sidebar, separate window.
|
||||
*
|
||||
* @param {string} hostType
|
||||
* The host type of the new host object
|
||||
*/
|
||||
_switchToHost: function TBOX_switchToHost(hostType) {
|
||||
if (hostType == this._host.type) {
|
||||
return;
|
||||
}
|
||||
|
||||
let newHost = this._createHost(hostType);
|
||||
|
||||
newHost.once("ready", function(event, iframe) {
|
||||
// change toolbox document's parent to the new host
|
||||
iframe.QueryInterface(Components.interfaces.nsIFrameLoaderOwner);
|
||||
iframe.swapFrameLoaders(this.frame);
|
||||
|
||||
this._host.off("window-closed", this.destroy);
|
||||
this._host.destroy();
|
||||
|
||||
this._host = newHost;
|
||||
|
||||
Services.prefs.setCharPref(this._prefs.LAST_HOST, this._host.type);
|
||||
|
||||
this._buildDockButtons();
|
||||
|
||||
this.emit("host-changed");
|
||||
}.bind(this));
|
||||
|
||||
newHost.open();
|
||||
},
|
||||
|
||||
/**
|
||||
* Get the most appropriate host tab, either the target or the current tab
|
||||
*/
|
||||
_getHostTab: function TBOX_getHostTab() {
|
||||
if (!this._target.isRemote && !this._target.isChrome) {
|
||||
return this._target.tab;
|
||||
} else {
|
||||
let win = Services.wm.getMostRecentWindow("navigator:browser");
|
||||
return win.gBrowser.selectedTab;
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Handler for the tool-registered event.
|
||||
* @param {string} event
|
||||
* Name of the event ("tool-registered")
|
||||
* @param {string} toolId
|
||||
* Id of the tool that was registered
|
||||
*/
|
||||
_toolRegistered: function TBOX_toolRegistered(event, toolId) {
|
||||
let defs = gDevTools.getToolDefinitions();
|
||||
let tool = defs.get(toolId);
|
||||
|
||||
this._buildTabForTool(tool);
|
||||
},
|
||||
|
||||
/**
|
||||
* Handler for the tool-unregistered event.
|
||||
* @param {string} event
|
||||
* Name of the event ("tool-unregistered")
|
||||
* @param {string} toolId
|
||||
* Id of the tool that was unregistered
|
||||
*/
|
||||
_toolUnregistered: function TBOX_toolUnregistered(event, toolId) {
|
||||
let radio = this.doc.getElementById("toolbox-tab-" + toolId);
|
||||
let panel = this.doc.getElementById("toolbox-panel-" + toolId);
|
||||
|
||||
if (this._currentToolId == toolId) {
|
||||
let nextToolName = null;
|
||||
if (radio.nextSibling) {
|
||||
nextToolName = radio.nextSibling.getAttribute("toolid");
|
||||
}
|
||||
if (radio.previousSibling) {
|
||||
nextToolName = radio.previousSibling.getAttribute("toolid");
|
||||
}
|
||||
if (nextToolName) {
|
||||
this.selectTool(nextToolName);
|
||||
}
|
||||
}
|
||||
|
||||
if (radio) {
|
||||
radio.parentNode.removeChild(radio);
|
||||
}
|
||||
|
||||
if (panel) {
|
||||
panel.parentNode.removeChild(panel);
|
||||
}
|
||||
|
||||
if (this._toolPanels.has(toolId)) {
|
||||
let instance = this._toolPanels.get(toolId);
|
||||
instance.destroy();
|
||||
this._toolPanels.delete(toolId);
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Get the toolbox's notification box
|
||||
*
|
||||
* @return The notification box element.
|
||||
*/
|
||||
getNotificationBox: function TBOX_getNotificationBox() {
|
||||
return this.doc.getElementById("toolbox-notificationbox");
|
||||
},
|
||||
|
||||
/**
|
||||
* Remove all UI elements, detach from target and clear up
|
||||
*/
|
||||
destroy: function TBOX_destroy() {
|
||||
if (this._destroyed) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Remote targets need to be notified that the toolbox is being torn down.
|
||||
if (this._target && this._target.isRemote) {
|
||||
this._target.destroy();
|
||||
}
|
||||
this._target = null;
|
||||
|
||||
for (let [id, panel] of this._toolPanels) {
|
||||
panel.destroy();
|
||||
}
|
||||
|
||||
this._host.destroy();
|
||||
|
||||
gDevTools.off("tool-registered", this._toolRegistered);
|
||||
gDevTools.off("tool-unregistered", this._toolUnregistered);
|
||||
|
||||
this._destroyed = true;
|
||||
this.emit("destroyed");
|
||||
}
|
||||
};
|
208
browser/devtools/framework/ToolboxHosts.jsm
Normal file
208
browser/devtools/framework/ToolboxHosts.jsm
Normal file
@ -0,0 +1,208 @@
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
const Cu = Components.utils;
|
||||
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource:///modules/devtools/EventEmitter.jsm");
|
||||
|
||||
this.EXPORTED_SYMBOLS = [ "Hosts" ];
|
||||
|
||||
/**
|
||||
* A toolbox host represents an object that contains a toolbox (e.g. the
|
||||
* sidebar or a separate window). Any host object should implement the
|
||||
* following functions:
|
||||
*
|
||||
* open() - create the UI and emit a 'ready' event when the UI is ready to use
|
||||
* destroy() - destroy the host's UI
|
||||
*/
|
||||
|
||||
this.Hosts = {
|
||||
"bottom": BottomHost,
|
||||
"side": SidebarHost,
|
||||
"window": WindowHost
|
||||
}
|
||||
|
||||
/**
|
||||
* Host object for the dock on the bottom of the browser
|
||||
*/
|
||||
function BottomHost(hostTab) {
|
||||
this.hostTab = hostTab;
|
||||
|
||||
new EventEmitter(this);
|
||||
}
|
||||
|
||||
BottomHost.prototype = {
|
||||
type: "bottom",
|
||||
|
||||
heightPref: "devtools.toolbox.footer.height",
|
||||
|
||||
/**
|
||||
* Create a box at the bottom of the host tab.
|
||||
*/
|
||||
open: function BH_open() {
|
||||
let gBrowser = this.hostTab.ownerDocument.defaultView.gBrowser;
|
||||
let ownerDocument = gBrowser.ownerDocument;
|
||||
|
||||
this._splitter = ownerDocument.createElement("splitter");
|
||||
this._splitter.setAttribute("class", "devtools-horizontal-splitter");
|
||||
|
||||
this.frame = ownerDocument.createElement("iframe");
|
||||
this.frame.id = "devtools-toolbox-bottom-iframe";
|
||||
this.frame.height = Services.prefs.getIntPref(this.heightPref);
|
||||
|
||||
this._nbox = gBrowser.getNotificationBox(this.hostTab.linkedBrowser);
|
||||
this._nbox.appendChild(this._splitter);
|
||||
this._nbox.appendChild(this.frame);
|
||||
|
||||
let frameLoad = function() {
|
||||
this.frame.removeEventListener("DOMContentLoaded", frameLoad, true);
|
||||
this.emit("ready", this.frame);
|
||||
}.bind(this);
|
||||
|
||||
this.frame.addEventListener("DOMContentLoaded", frameLoad, true);
|
||||
|
||||
// we have to load something so we can switch documents if we have to
|
||||
this.frame.setAttribute("src", "about:blank");
|
||||
|
||||
focusTab(this.hostTab);
|
||||
},
|
||||
|
||||
/**
|
||||
* Destroy the bottom dock.
|
||||
*/
|
||||
destroy: function BH_destroy() {
|
||||
if (this._destroyed) {
|
||||
return;
|
||||
}
|
||||
this._destroyed = true;
|
||||
Services.prefs.setIntPref(this.heightPref, this.frame.height);
|
||||
|
||||
this._nbox.removeChild(this._splitter);
|
||||
this._nbox.removeChild(this.frame);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Host object for the in-browser sidebar
|
||||
*/
|
||||
function SidebarHost(hostTab) {
|
||||
this.hostTab = hostTab;
|
||||
|
||||
new EventEmitter(this);
|
||||
}
|
||||
|
||||
SidebarHost.prototype = {
|
||||
type: "side",
|
||||
|
||||
widthPref: "devtools.toolbox.sidebar.width",
|
||||
|
||||
/**
|
||||
* Create a box in the sidebar of the host tab.
|
||||
*/
|
||||
open: function RH_open() {
|
||||
let gBrowser = this.hostTab.ownerDocument.defaultView.gBrowser;
|
||||
let ownerDocument = gBrowser.ownerDocument;
|
||||
|
||||
this._splitter = ownerDocument.createElement("splitter");
|
||||
this._splitter.setAttribute("class", "devtools-side-splitter");
|
||||
|
||||
this.frame = ownerDocument.createElement("iframe");
|
||||
this.frame.id = "devtools-toolbox-side-iframe";
|
||||
this.frame.width = Services.prefs.getIntPref(this.widthPref);
|
||||
|
||||
this._sidebar = gBrowser.getSidebarContainer(this.hostTab.linkedBrowser);
|
||||
this._sidebar.appendChild(this._splitter);
|
||||
this._sidebar.appendChild(this.frame);
|
||||
|
||||
let frameLoad = function() {
|
||||
this.frame.removeEventListener("DOMContentLoaded", frameLoad, true);
|
||||
this.emit("ready", this.frame);
|
||||
}.bind(this);
|
||||
|
||||
this.frame.addEventListener("DOMContentLoaded", frameLoad, true);
|
||||
this.frame.setAttribute("src", "about:blank");
|
||||
|
||||
focusTab(this.hostTab);
|
||||
},
|
||||
|
||||
/**
|
||||
* Destroy the sidebar.
|
||||
*/
|
||||
destroy: function RH_destroy() {
|
||||
Services.prefs.setIntPref(this.widthPref, this.frame.width);
|
||||
|
||||
this._sidebar.removeChild(this._splitter);
|
||||
this._sidebar.removeChild(this.frame);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Host object for the toolbox in a separate window
|
||||
*/
|
||||
function WindowHost() {
|
||||
this._boundUnload = this._boundUnload.bind(this);
|
||||
|
||||
new EventEmitter(this);
|
||||
}
|
||||
|
||||
WindowHost.prototype = {
|
||||
type: "window",
|
||||
|
||||
WINDOW_URL: "chrome://browser/content/devtools/framework/toolbox-window.xul",
|
||||
|
||||
/**
|
||||
* Create a new xul window to contain the toolbox.
|
||||
*/
|
||||
open: function WH_open() {
|
||||
let flags = "chrome,centerscreen,resizable,dialog=no";
|
||||
let win = Services.ww.openWindow(null, this.WINDOW_URL, "_blank",
|
||||
flags, null);
|
||||
|
||||
let frameLoad = function(event) {
|
||||
win.removeEventListener("load", frameLoad, true);
|
||||
this.frame = win.document.getElementById("toolbox-iframe");
|
||||
this.emit("ready", this.frame);
|
||||
}.bind(this);
|
||||
|
||||
win.addEventListener("load", frameLoad, true);
|
||||
win.addEventListener("unload", this._boundUnload);
|
||||
|
||||
win.focus();
|
||||
|
||||
this._window = win;
|
||||
},
|
||||
|
||||
/**
|
||||
* Catch the user closing the window.
|
||||
*/
|
||||
_boundUnload: function(event) {
|
||||
if (event.target.location != this.WINDOW_URL) {
|
||||
return;
|
||||
}
|
||||
this._window.removeEventListener("unload", this._boundUnload);
|
||||
|
||||
this.emit("window-closed");
|
||||
},
|
||||
|
||||
/**
|
||||
* Destroy the window.
|
||||
*/
|
||||
destroy: function WH_destroy() {
|
||||
this._window.removeEventListener("unload", this._boundUnload);
|
||||
this._window.close();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Switch to the given tab in a browser and focus the browser window
|
||||
*/
|
||||
function focusTab(tab) {
|
||||
let browserWindow = tab.ownerDocument.defaultView;
|
||||
browserWindow.focus();
|
||||
browserWindow.gBrowser.selectedTab = tab;
|
||||
}
|
87
browser/devtools/framework/connect/connect.css
Normal file
87
browser/devtools/framework/connect/connect.css
Normal file
@ -0,0 +1,87 @@
|
||||
html {
|
||||
background: url("chrome://browser/skin/newtab/noise.png");
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: Arial;
|
||||
padding: 20px;
|
||||
border-radius: 3px;
|
||||
max-width: 600px;
|
||||
min-height: 400px;
|
||||
margin: 10px auto 0;
|
||||
}
|
||||
|
||||
label {
|
||||
display: block;
|
||||
margin: 10px;
|
||||
font-size: 0;
|
||||
}
|
||||
|
||||
label > span {
|
||||
display: inline-block;
|
||||
min-width: 150px;
|
||||
font-size: 0.8rem;
|
||||
text-align: right;
|
||||
margin-right: 10px;
|
||||
}
|
||||
|
||||
#submit {
|
||||
margin-left: 160px;
|
||||
}
|
||||
|
||||
|
||||
#actors, #connection-form {
|
||||
margin: 20px;
|
||||
}
|
||||
|
||||
input {
|
||||
border: 1px solid grey;
|
||||
}
|
||||
|
||||
#connection-form,
|
||||
#connecting,
|
||||
#actors-list {
|
||||
display: none;
|
||||
}
|
||||
|
||||
body:not(.actors-mode):not(.connecting) > #connection-form {
|
||||
display: block;
|
||||
}
|
||||
|
||||
body.actors-mode > #actors-list {
|
||||
display: block;
|
||||
}
|
||||
|
||||
body.connecting > #connecting {
|
||||
display: block;
|
||||
}
|
||||
|
||||
#connecting {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
#throbber {
|
||||
height: 7px; width: 7px;
|
||||
border-radius: 50%;
|
||||
background: black;
|
||||
display: inline-block;
|
||||
animation-duration: 0.6s;
|
||||
animation-name: anim;
|
||||
animation-direction: alternate;
|
||||
animation-iteration-count: infinite;
|
||||
animation-timing-function: linear;
|
||||
}
|
||||
@keyframes anim {to {
|
||||
transform: scale(0.5) rotate(0.1deg);
|
||||
}}
|
||||
|
||||
#actors {
|
||||
padding-left: 0;
|
||||
font-size: 0.9rem;
|
||||
}
|
||||
|
||||
#actors > a {
|
||||
display: block;
|
||||
margin: 5px;
|
||||
padding: 5px;
|
||||
}
|
100
browser/devtools/framework/connect/connect.js
Normal file
100
browser/devtools/framework/connect/connect.js
Normal file
@ -0,0 +1,100 @@
|
||||
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* vim: set ft=javascript ts=2 et sw=2 tw=80: */
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
const Cu = Components.utils;
|
||||
Cu.import("resource:///modules/devtools/Target.jsm");
|
||||
Cu.import("resource:///modules/devtools/Toolbox.jsm");
|
||||
Cu.import("resource:///modules/devtools/gDevTools.jsm");
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource://gre/modules/devtools/dbg-client.jsm");
|
||||
|
||||
let gClient;
|
||||
|
||||
function submit() {
|
||||
document.body.classList.add("connecting");
|
||||
|
||||
let host = document.getElementById("host").value;
|
||||
let port = document.getElementById("port").value;
|
||||
if (!host) {
|
||||
host = Services.prefs.getCharPref("devtools.debugger.remote-host");
|
||||
} else {
|
||||
Services.prefs.setCharPref("devtools.debugger.remote-host", host);
|
||||
}
|
||||
if (!port) {
|
||||
port = Services.prefs.getIntPref("devtools.debugger.remote-port");
|
||||
} else {
|
||||
Services.prefs.setIntPref("devtools.debugger.remote-port", port);
|
||||
}
|
||||
|
||||
let transport = debuggerSocketConnect(host, port);
|
||||
let client = gClient = new DebuggerClient(transport);
|
||||
|
||||
client.connect(function(aType, aTraits) {
|
||||
client.listTabs(function(aResponse) {
|
||||
document.body.classList.remove("connecting");
|
||||
document.body.classList.add("actors-mode");
|
||||
|
||||
let parent = document.getElementById("actors");
|
||||
let focusSet = false;
|
||||
|
||||
// Add Global Process debugging...
|
||||
let globals = JSON.parse(JSON.stringify(aResponse));
|
||||
delete globals.tabs;
|
||||
delete globals.selected;
|
||||
// ...only if there are appropriate actors (a 'from' property will always
|
||||
// be there).
|
||||
if (Object.keys(globals).length > 1) {
|
||||
let a = document.createElement("a");
|
||||
a.onclick = function() {
|
||||
connect(globals, true);
|
||||
}
|
||||
|
||||
a.title = a.textContent = "Remote process";
|
||||
a.href = "#";
|
||||
|
||||
parent.appendChild(a);
|
||||
}
|
||||
|
||||
// Add one entry for each open tab.
|
||||
if (aResponse.tabs.length > 0) {
|
||||
let header = document.createElement("div");
|
||||
header.innerHTML = "Tabs:";
|
||||
parent.appendChild(header);
|
||||
}
|
||||
for (let i = 0; i < aResponse.tabs.length; i++) {
|
||||
let tab = aResponse.tabs[i];
|
||||
|
||||
let a = document.createElement("a");
|
||||
a.onclick = function() {
|
||||
connect(tab);
|
||||
}
|
||||
|
||||
a.title = a.textContent = tab.title;
|
||||
a.href = "#";
|
||||
|
||||
if (i == aResponse.selected) {
|
||||
a.title += " [*]";
|
||||
a.textContent = a.title;
|
||||
}
|
||||
|
||||
parent.appendChild(a);
|
||||
|
||||
if (!focusSet) {
|
||||
a.focus();
|
||||
focusSet = true;
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function connect(form, chrome=false) {
|
||||
let target = TargetFactory.forRemote(form, gClient, chrome);
|
||||
gDevTools.openToolbox(target, Toolbox.HostType.WINDOW, "webconsole");
|
||||
window.close();
|
||||
}
|
45
browser/devtools/framework/connect/connect.xhtml
Normal file
45
browser/devtools/framework/connect/connect.xhtml
Normal file
@ -0,0 +1,45 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- This Source Code Form is subject to the terms of the Mozilla Public
|
||||
- License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
- file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
|
||||
|
||||
<!DOCTYPE html [
|
||||
<!ENTITY % connectionDTD SYSTEM "chrome://browser/locale/devtools/connection-screen.dtd" >
|
||||
%connectionDTD;
|
||||
]>
|
||||
|
||||
<html xmlns="http://www.w3.org/1999/xhtml"
|
||||
xmlns:xul="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
|
||||
<head>
|
||||
<title>&title;</title>
|
||||
<link rel="stylesheet" href="chrome://browser/content/devtools/connect.css" type="text/css"/>
|
||||
<script type="application/javascript;version=1.8" src="connect.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<p>
|
||||
</p>
|
||||
<section id="connection-form">
|
||||
<form onsubmit="window.submit()" action="#">
|
||||
<label>
|
||||
<span>&host;</span>
|
||||
<input id="host" type="text" placeholder="localhost"></input>
|
||||
</label>
|
||||
<label>
|
||||
<span>&port;</span>
|
||||
<input id="port" type="number" placeholder="6000"></input>
|
||||
</label>
|
||||
<label>
|
||||
<input id="submit" type="submit" value="&connect;"></input>
|
||||
</label>
|
||||
</form>
|
||||
</section>
|
||||
<section id="actors-list">
|
||||
<p>&availability;</p>
|
||||
<ul id="actors"></ul>
|
||||
</section>
|
||||
<section id="connecting">
|
||||
<p>&connecting;</p>
|
||||
<div id="throbber"></div>
|
||||
</section>
|
||||
</body>
|
||||
</html>
|
543
browser/devtools/framework/gDevTools.jsm
Normal file
543
browser/devtools/framework/gDevTools.jsm
Normal file
@ -0,0 +1,543 @@
|
||||
/* This Source Code Form is subject to the terms of the Mozilla Public
|
||||
* License, v. 2.0. If a copy of the MPL was not distributed with this
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
"use strict";
|
||||
|
||||
this.EXPORTED_SYMBOLS = [ "gDevTools", "DevTools", "DevToolsXULCommands" ];
|
||||
|
||||
const Cu = Components.utils;
|
||||
const Ci = Components.interfaces;
|
||||
|
||||
Cu.import("resource://gre/modules/Services.jsm");
|
||||
Cu.import("resource:///modules/devtools/EventEmitter.jsm");
|
||||
Cu.import("resource:///modules/devtools/ToolDefinitions.jsm");
|
||||
Cu.import("resource:///modules/devtools/Toolbox.jsm");
|
||||
Cu.import("resource:///modules/devtools/Target.jsm");
|
||||
|
||||
const FORBIDDEN_IDS = new Set("toolbox", "");
|
||||
|
||||
/**
|
||||
* DevTools is a class that represents a set of developer tools, it holds a
|
||||
* set of tools and keeps track of open toolboxes in the browser.
|
||||
*/
|
||||
this.DevTools = function DevTools() {
|
||||
this._tools = new Map();
|
||||
this._toolboxes = new Map();
|
||||
|
||||
// destroy() is an observer's handler so we need to preserve context.
|
||||
this.destroy = this.destroy.bind(this);
|
||||
|
||||
this._trackedBrowserWindows = new Set();
|
||||
|
||||
// Bind _updateMenuCheckbox() to preserve context.
|
||||
this._updateMenuCheckbox = this._updateMenuCheckbox.bind(this);
|
||||
|
||||
new EventEmitter(this);
|
||||
|
||||
Services.obs.addObserver(this.destroy, "quit-application", false);
|
||||
|
||||
/**
|
||||
* Register the set of default tools
|
||||
*/
|
||||
for (let definition of defaultTools) {
|
||||
this.registerTool(definition);
|
||||
}
|
||||
}
|
||||
|
||||
DevTools.prototype = {
|
||||
/**
|
||||
* Register a new developer tool.
|
||||
*
|
||||
* A definition is a light object that holds different information about a
|
||||
* developer tool. This object is not supposed to have any operational code.
|
||||
* See it as a "manifest".
|
||||
* The only actual code lives in the build() function, which will be used to
|
||||
* start an instance of this tool.
|
||||
*
|
||||
* Each toolDefinition has the following properties:
|
||||
* - id: Unique identifier for this tool (string|required)
|
||||
* - killswitch: Property name to allow us to turn this tool on/off globally
|
||||
* (string|required) (TODO: default to devtools.{id}.enabled?)
|
||||
* - icon: URL pointing to a graphic which will be used as the src for an
|
||||
* 16x16 img tag (string|required)
|
||||
* - url: URL pointing to a XUL/XHTML document containing the user interface
|
||||
* (string|required)
|
||||
* - label: Localized name for the tool to be displayed to the user
|
||||
* (string|required)
|
||||
* - build: Function that takes an iframe, which has been populated with the
|
||||
* markup from |url|, and also the toolbox containing the panel.
|
||||
* And returns an instance of ToolPanel (function|required)
|
||||
*/
|
||||
registerTool: function DT_registerTool(toolDefinition) {
|
||||
let toolId = toolDefinition.id;
|
||||
|
||||
if (!toolId || FORBIDDEN_IDS.has(toolId)) {
|
||||
throw new Error("Invalid definition.id");
|
||||
}
|
||||
|
||||
toolDefinition.killswitch = toolDefinition.killswitch ||
|
||||
"devtools." + toolId + ".enabled";
|
||||
this._tools.set(toolId, toolDefinition);
|
||||
|
||||
this._addToolToWindows(toolDefinition);
|
||||
|
||||
this.emit("tool-registered", toolId);
|
||||
},
|
||||
|
||||
/**
|
||||
* Removes all tools that match the given |toolId|
|
||||
* Needed so that add-ons can remove themselves when they are deactivated
|
||||
*
|
||||
* @param {string} toolId
|
||||
* id of the tool to unregister
|
||||
*/
|
||||
unregisterTool: function DT_unregisterTool(toolId) {
|
||||
this._tools.delete(toolId);
|
||||
|
||||
this._removeToolFromWindows(toolId);
|
||||
|
||||
this.emit("tool-unregistered", toolId);
|
||||
},
|
||||
|
||||
/**
|
||||
* Allow ToolBoxes to get at the list of tools that they should populate
|
||||
* themselves with.
|
||||
*
|
||||
* @return {Map} tools
|
||||
* A map of the the tool definitions registered in this instance
|
||||
*/
|
||||
getToolDefinitions: function DT_getToolDefinitions() {
|
||||
let tools = new Map();
|
||||
|
||||
for (let [key, value] of this._tools) {
|
||||
let enabled;
|
||||
|
||||
try {
|
||||
enabled = Services.prefs.getBoolPref(value.killswitch);
|
||||
} catch(e) {
|
||||
enabled = true;
|
||||
}
|
||||
|
||||
if (enabled) {
|
||||
tools.set(key, value);
|
||||
}
|
||||
}
|
||||
return tools;
|
||||
},
|
||||
|
||||
/**
|
||||
* Create a toolbox to debug |target| using a window displayed in |hostType|
|
||||
* (optionally with |defaultToolId| opened)
|
||||
*
|
||||
* @param {Target} target
|
||||
* The target the toolbox will debug
|
||||
* @param {Toolbox.HostType} hostType
|
||||
* The type of host (bottom, top, side)
|
||||
* @param {string} defaultToolId
|
||||
* The id of the initial tool to show
|
||||
*
|
||||
* @return {Toolbox} toolbox
|
||||
* The toolbox that was opened
|
||||
*/
|
||||
openToolbox: function DT_openToolbox(target, hostType, defaultToolId) {
|
||||
if (this._toolboxes.has(target)) {
|
||||
// only allow one toolbox per target
|
||||
return this._toolboxes.get(target);
|
||||
}
|
||||
|
||||
let tb = new Toolbox(target, hostType, defaultToolId);
|
||||
|
||||
this._toolboxes.set(target, tb);
|
||||
tb.once("destroyed", function() {
|
||||
this._toolboxes.delete(target);
|
||||
this._updateMenuCheckbox();
|
||||
this.emit("toolbox-destroyed", target);
|
||||
}.bind(this));
|
||||
|
||||
tb.once("ready", function() {
|
||||
this.emit("toolbox-ready", tb);
|
||||
this._updateMenuCheckbox();
|
||||
}.bind(this));
|
||||
|
||||
tb.open();
|
||||
|
||||
return tb;
|
||||
},
|
||||
|
||||
/**
|
||||
* Close the toolbox for a given target
|
||||
*/
|
||||
closeToolbox: function DT_closeToolbox(target) {
|
||||
let toolbox = this._toolboxes.get(target);
|
||||
if (toolbox == null) {
|
||||
return;
|
||||
}
|
||||
toolbox.destroy();
|
||||
},
|
||||
|
||||
/**
|
||||
* Open the toolbox for a specific target (not tab).
|
||||
* FIXME: We should probably merge this function and openToolbox
|
||||
*
|
||||
* @param {Target} target
|
||||
* The target that the toolbox should be debugging
|
||||
* @param {String} toolId
|
||||
* The id of the tool to open
|
||||
*
|
||||
* @return {Toolbox} toolbox
|
||||
* The toolbox that has been opened
|
||||
*/
|
||||
openToolboxForTab: function DT_openToolboxForTab(target, toolId) {
|
||||
let tb = this.getToolboxForTarget(target);
|
||||
|
||||
if (tb) {
|
||||
tb.selectTool(toolId);
|
||||
} else {
|
||||
tb = this.openToolbox(target, null, toolId);
|
||||
}
|
||||
return tb;
|
||||
},
|
||||
|
||||
/**
|
||||
* This function is for the benefit of command#Tools:DevToolbox in
|
||||
* browser/base/content/browser-sets.inc and should not be used outside
|
||||
* of there
|
||||
*/
|
||||
toggleToolboxCommand: function(gBrowser, toolId=null) {
|
||||
let target = TargetFactory.forTab(gBrowser.selectedTab);
|
||||
this.toggleToolboxForTarget(target, toolId);
|
||||
},
|
||||
|
||||
/**
|
||||
* Toggle a toolbox for the given target.
|
||||
*
|
||||
* @param {Target} target
|
||||
* The target the toolbox is debugging
|
||||
* @param {string} toolId
|
||||
* The id of the tool to show in the toolbox, if it's to be opened.
|
||||
*/
|
||||
toggleToolboxForTarget: function DT_toggleToolboxForTarget(target, toolId) {
|
||||
let tb = this.getToolboxForTarget(target);
|
||||
|
||||
if (tb /* FIXME: && tool is showing */ ) {
|
||||
tb.destroy();
|
||||
} else {
|
||||
this.openToolboxForTab(target, toolId);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Return the toolbox for a given target.
|
||||
*
|
||||
* @param {object} target
|
||||
* Target value e.g. the target that owns this toolbox
|
||||
*
|
||||
* @return {Toolbox} toolbox
|
||||
* The toobox that is debugging the given target
|
||||
*/
|
||||
getToolboxForTarget: function DT_getToolboxForTarget(target) {
|
||||
return this._toolboxes.get(target);
|
||||
},
|
||||
|
||||
/**
|
||||
* Return a tool panel for a given tool and target.
|
||||
*
|
||||
* @param {String} toolId
|
||||
* The id of the tool to open.
|
||||
* @param {object} target
|
||||
* The toolbox's target.
|
||||
*
|
||||
* @return {ToolPanel} panel
|
||||
* Panel for the tool with the toolid
|
||||
*/
|
||||
getPanelForTarget: function DT_getPanelForTarget(toolId, target) {
|
||||
let toolbox = this.getToolboxForTarget(target);
|
||||
if (!toolbox) {
|
||||
return undefined;
|
||||
}
|
||||
return toolbox.getToolPanels().get(toolId);
|
||||
},
|
||||
|
||||
/**
|
||||
* Add this DevTools's presence to a browser window's document
|
||||
*
|
||||
* @param {XULDocument} doc
|
||||
* The document to which menuitems and handlers are to be added
|
||||
*/
|
||||
registerBrowserWindow: function DT_registerBrowserWindow(win) {
|
||||
this._trackedBrowserWindows.add(win);
|
||||
this._addAllToolsToMenu(win.document);
|
||||
|
||||
let tabContainer = win.document.getElementById("tabbrowser-tabs")
|
||||
tabContainer.addEventListener("TabSelect", this._updateMenuCheckbox, false);
|
||||
},
|
||||
|
||||
/**
|
||||
* Add the menuitem for a tool to all open browser windows.
|
||||
*
|
||||
* @param {object} toolDefinition
|
||||
* properties of the tool to add
|
||||
*/
|
||||
_addToolToWindows: function DT_addToolToWindows(toolDefinition) {
|
||||
for (let win of this._trackedBrowserWindows) {
|
||||
this._addToolToMenu(toolDefinition, win.document);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Add all tools to the developer tools menu of a window.
|
||||
*
|
||||
* @param {XULDocument} doc
|
||||
* The document to which the tool items are to be added.
|
||||
*/
|
||||
_addAllToolsToMenu: function DT_addAllToolsToMenu(doc) {
|
||||
let fragCommands = doc.createDocumentFragment();
|
||||
let fragKeys = doc.createDocumentFragment();
|
||||
let fragBroadcasters = doc.createDocumentFragment();
|
||||
let fragAppMenuItems = doc.createDocumentFragment();
|
||||
let fragMenuItems = doc.createDocumentFragment();
|
||||
|
||||
for (let [key, toolDefinition] of this._tools) {
|
||||
let frags = this._addToolToMenu(toolDefinition, doc, true);
|
||||
|
||||
if (!frags) {
|
||||
return;
|
||||
}
|
||||
|
||||
let [cmd, key, bc, appmenuitem, menuitem] = frags;
|
||||
|
||||
fragCommands.appendChild(cmd);
|
||||
if (key) {
|
||||
fragKeys.appendChild(key);
|
||||
}
|
||||
fragBroadcasters.appendChild(bc);
|
||||
fragAppMenuItems.appendChild(appmenuitem);
|
||||
fragMenuItems.appendChild(menuitem);
|
||||
}
|
||||
|
||||
let mcs = doc.getElementById("mainCommandSet");
|
||||
mcs.appendChild(fragCommands);
|
||||
|
||||
let mks = doc.getElementById("mainKeyset");
|
||||
mks.appendChild(fragKeys);
|
||||
|
||||
let mbs = doc.getElementById("mainBroadcasterSet");
|
||||
mbs.appendChild(fragBroadcasters);
|
||||
|
||||
let amp = doc.getElementById("appmenu_webDeveloper_popup");
|
||||
if (amp) {
|
||||
let amps = doc.getElementById("appmenu_devtools_separator");
|
||||
amp.insertBefore(fragAppMenuItems, amps);
|
||||
}
|
||||
|
||||
let mp = doc.getElementById("menuWebDeveloperPopup");
|
||||
let mps = doc.getElementById("menu_devtools_separator");
|
||||
mp.insertBefore(fragMenuItems, mps);
|
||||
},
|
||||
|
||||
/**
|
||||
* Add a menu entry for a tool definition
|
||||
*
|
||||
* @param {string} toolDefinition
|
||||
* Tool definition of the tool to add a menu entry.
|
||||
* @param {XULDocument} doc
|
||||
* The document to which the tool menu item is to be added.
|
||||
* @param {Boolean} [noAppend]
|
||||
* Return an array of elements instead of appending them to the
|
||||
* document. Default is false.
|
||||
*/
|
||||
_addToolToMenu: function DT_addToolToMenu(toolDefinition, doc, noAppend) {
|
||||
let id = toolDefinition.id;
|
||||
|
||||
// Prevent multiple entries for the same tool.
|
||||
if (doc.getElementById("Tools:" + id)) {
|
||||
return;
|
||||
}
|
||||
|
||||
let cmd = doc.createElement("command");
|
||||
cmd.id = "Tools:" + id;
|
||||
cmd.setAttribute("oncommand",
|
||||
'gDevTools.toggleToolboxCommand(gBrowser, "' + id + '");');
|
||||
|
||||
let key = null;
|
||||
if (toolDefinition.key) {
|
||||
key = doc.createElement("key");
|
||||
key.id = "key_" + id;
|
||||
|
||||
if (toolDefinition.key.startsWith("VK_")) {
|
||||
key.setAttribute("keycode", toolDefinition.key);
|
||||
} else {
|
||||
key.setAttribute("key", toolDefinition.key);
|
||||
}
|
||||
|
||||
key.setAttribute("oncommand",
|
||||
'gDevTools.toggleToolboxCommand(gBrowser, "' + id + '");');
|
||||
key.setAttribute("modifiers", toolDefinition.modifiers);
|
||||
}
|
||||
|
||||
let bc = doc.createElement("broadcaster");
|
||||
bc.id = "devtoolsMenuBroadcaster_" + id;
|
||||
bc.setAttribute("label", toolDefinition.label);
|
||||
bc.setAttribute("command", "Tools:" + id);
|
||||
|
||||
if (key) {
|
||||
bc.setAttribute("key", "key_" + id);
|
||||
}
|
||||
|
||||
let appmenuitem = doc.createElement("menuitem");
|
||||
appmenuitem.id = "appmenuitem_" + id;
|
||||
appmenuitem.setAttribute("observes", "devtoolsMenuBroadcaster_" + id);
|
||||
|
||||
let menuitem = doc.createElement("menuitem");
|
||||
menuitem.id = "menuitem_" + id;
|
||||
menuitem.setAttribute("observes", "devtoolsMenuBroadcaster_" + id);
|
||||
|
||||
if (toolDefinition.accesskey) {
|
||||
menuitem.setAttribute("accesskey", toolDefinition.accesskey);
|
||||
}
|
||||
|
||||
if (noAppend) {
|
||||
return [cmd, key, bc, appmenuitem, menuitem];
|
||||
} else {
|
||||
let mcs = doc.getElementById("mainCommandSet");
|
||||
mcs.appendChild(cmd);
|
||||
|
||||
if (key) {
|
||||
let mks = doc.getElementById("mainKeyset");
|
||||
mks.appendChild(key);
|
||||
}
|
||||
|
||||
let mbs = doc.getElementById("mainBroadcasterSet");
|
||||
mbs.appendChild(bc);
|
||||
|
||||
let amp = doc.getElementById("appmenu_webDeveloper_popup");
|
||||
if (amp) {
|
||||
let amps = doc.getElementById("appmenu_devtools_separator");
|
||||
amp.insertBefore(appmenuitem, amps);
|
||||
}
|
||||
|
||||
let mp = doc.getElementById("menuWebDeveloperPopup");
|
||||
let mps = doc.getElementById("menu_devtools_separator");
|
||||
mp.insertBefore(menuitem, mps);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Update the "Toggle Toolbox" checkbox in the developer tools menu. This is
|
||||
* called when a toolbox is created or destroyed.
|
||||
*/
|
||||
_updateMenuCheckbox: function DT_updateMenuCheckbox() {
|
||||
for (let win of this._trackedBrowserWindows) {
|
||||
|
||||
let hasToolbox = false;
|
||||
if (TargetFactory.isKnownTab(win.gBrowser.selectedTab)) {
|
||||
let target = TargetFactory.forTab(win.gBrowser.selectedTab);
|
||||
if (this._toolboxes.has(target)) {
|
||||
hasToolbox = true;
|
||||
}
|
||||
}
|
||||
|
||||
let broadcaster = win.document.getElementById("devtoolsMenuBroadcaster_DevToolbox");
|
||||
if (hasToolbox) {
|
||||
broadcaster.setAttribute("checked", "true");
|
||||
} else {
|
||||
broadcaster.removeAttribute("checked");
|
||||
}
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Remove the menuitem for a tool to all open browser windows.
|
||||
*
|
||||
* @param {object} toolId
|
||||
* id of the tool to remove
|
||||
*/
|
||||
_removeToolFromWindows: function DT_removeToolFromWindows(toolId) {
|
||||
for (let win of this._trackedBrowserWindows) {
|
||||
this._removeToolFromMenu(toolId, win.document);
|
||||
}
|
||||
},
|
||||
|
||||
/**
|
||||
* Remove a tool's menuitem from a window
|
||||
*
|
||||
* @param {string} toolId
|
||||
* Id of the tool to add a menu entry for
|
||||
* @param {XULDocument} doc
|
||||
* The document to which the tool menu item is to be removed from
|
||||
*/
|
||||
_removeToolFromMenu: function DT_removeToolFromMenu(toolId, doc) {
|
||||
let command = doc.getElementById("Tools:" + toolId);
|
||||
command.parentNode.removeChild(command);
|
||||
|
||||
let key = doc.getElementById("key_" + toolId);
|
||||
if (key) {
|
||||
key.parentNode.removeChild(key);
|
||||
}
|
||||
|
||||
let bc = doc.getElementById("devtoolsMenuBroadcaster_" + toolId);
|
||||
bc.parentNode.removeChild(bc);
|
||||
|
||||
/*
|
||||
// FIXME: item is null in testing. This is the only place to use
|
||||
// "appmenu_devToolbar" + toolId, so it seems clear that this is wrong
|
||||
let item = doc.getElementById("appmenu_devToolbar" + toolId);
|
||||
item.parentNode.removeChild(item);
|
||||
*/
|
||||
},
|
||||
|
||||
/**
|
||||
* Called on browser unload to remove menu entries, toolboxes and event
|
||||
* listeners from the closed browser window.
|
||||
*
|
||||
* @param {XULWindow} win
|
||||
* The window containing the menu entry
|
||||
*/
|
||||
forgetBrowserWindow: function DT_forgetBrowserWindow(win) {
|
||||
if (!this._tools) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._trackedBrowserWindows.delete(win);
|
||||
|
||||
// Destroy toolboxes for closed window
|
||||
for (let [target, toolbox] of this._toolboxes) {
|
||||
if (toolbox.frame.ownerDocument.defaultView == win) {
|
||||
toolbox.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
let tabContainer = win.document.getElementById("tabbrowser-tabs")
|
||||
tabContainer.removeEventListener("TabSelect",
|
||||
this._updateMenuCheckbox, false);
|
||||
},
|
||||
|
||||
/**
|
||||
* All browser windows have been closed, tidy up remaining objects.
|
||||
*/
|
||||
destroy: function() {
|
||||
Services.obs.removeObserver(this.destroy, "quit-application");
|
||||
|
||||
delete this._trackedBrowserWindows;
|
||||
delete this._tools;
|
||||
delete this._toolboxes;
|
||||
},
|
||||
};
|
||||
|
||||
/**
|
||||
* gDevTools is a singleton that controls the Firefox Developer Tools.
|
||||
*
|
||||
* It is an instance of a DevTools class that holds a set of tools. It has the
|
||||
* same lifetime as the browser.
|
||||
*/
|
||||
this.gDevTools = new DevTools();
|
||||
|
||||
/**
|
||||
* DevToolsXULCommands exposes methods used by browser's <command>s.
|
||||
*/
|
||||
this.DevToolsXULCommands = {
|
||||
openConnectScreen: function(gBrowser) {
|
||||
gBrowser.selectedTab = gBrowser.addTab("chrome://browser/content/devtools/connect.xhtml");
|
||||
},
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user