panel.js 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118
  1. /* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
  2. /* This Source Code Form is subject to the terms of the Mozilla Public
  3. * License, v. 2.0. If a copy of the MPL was not distributed with this
  4. * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
  5. "use strict";
  6. const promise = require("promise");
  7. loader.lazyRequireGetter(this, "HUDService", "devtools/client/webconsole/hudservice", true);
  8. loader.lazyGetter(this, "EventEmitter", () => require("devtools/shared/event-emitter"));
  9. /**
  10. * A DevToolPanel that controls the Web Console.
  11. */
  12. function WebConsolePanel(iframeWindow, toolbox) {
  13. this._frameWindow = iframeWindow;
  14. this._toolbox = toolbox;
  15. EventEmitter.decorate(this);
  16. }
  17. exports.WebConsolePanel = WebConsolePanel;
  18. WebConsolePanel.prototype = {
  19. hud: null,
  20. /**
  21. * Called by the WebConsole's onkey command handler.
  22. * If the WebConsole is opened, check if the JSTerm's input line has focus.
  23. * If not, focus it.
  24. */
  25. focusInput: function () {
  26. this.hud.jsterm.focus();
  27. },
  28. /**
  29. * Open is effectively an asynchronous constructor.
  30. *
  31. * @return object
  32. * A promise that is resolved when the Web Console completes opening.
  33. */
  34. open: function () {
  35. let parentDoc = this._toolbox.doc;
  36. let iframe = parentDoc.getElementById("toolbox-panel-iframe-webconsole");
  37. // Make sure the iframe content window is ready.
  38. let deferredIframe = promise.defer();
  39. let win, doc;
  40. if ((win = iframe.contentWindow) &&
  41. (doc = win.document) &&
  42. doc.readyState == "complete") {
  43. deferredIframe.resolve(null);
  44. } else {
  45. iframe.addEventListener("load", function onIframeLoad() {
  46. iframe.removeEventListener("load", onIframeLoad, true);
  47. deferredIframe.resolve(null);
  48. }, true);
  49. }
  50. // Local debugging needs to make the target remote.
  51. let promiseTarget;
  52. if (!this.target.isRemote) {
  53. promiseTarget = this.target.makeRemote();
  54. } else {
  55. promiseTarget = promise.resolve(this.target);
  56. }
  57. // 1. Wait for the iframe to load.
  58. // 2. Wait for the remote target.
  59. // 3. Open the Web Console.
  60. return deferredIframe.promise
  61. .then(() => promiseTarget)
  62. .then((target) => {
  63. this._frameWindow._remoteTarget = target;
  64. let webConsoleUIWindow = iframe.contentWindow.wrappedJSObject;
  65. let chromeWindow = iframe.ownerDocument.defaultView;
  66. return HUDService.openWebConsole(this.target, webConsoleUIWindow,
  67. chromeWindow);
  68. })
  69. .then((webConsole) => {
  70. this.hud = webConsole;
  71. this._isReady = true;
  72. this.emit("ready");
  73. return this;
  74. }, (reason) => {
  75. let msg = "WebConsolePanel open failed. " +
  76. reason.error + ": " + reason.message;
  77. dump(msg + "\n");
  78. console.error(msg);
  79. });
  80. },
  81. get target() {
  82. return this._toolbox.target;
  83. },
  84. _isReady: false,
  85. get isReady() {
  86. return this._isReady;
  87. },
  88. destroy: function () {
  89. if (this._destroyer) {
  90. return this._destroyer;
  91. }
  92. this._destroyer = this.hud.destroy();
  93. this._destroyer.then(() => {
  94. this._frameWindow = null;
  95. this._toolbox = null;
  96. this.emit("destroyed");
  97. });
  98. return this._destroyer;
  99. },
  100. };