browser-window.js 6.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195
  1. 'use strict';
  2. const electron = require('electron');
  3. const { WebContentsView, TopLevelWindow, deprecate } = electron;
  4. const { BrowserWindow } = process.electronBinding('window');
  5. Object.setPrototypeOf(BrowserWindow.prototype, TopLevelWindow.prototype);
  6. BrowserWindow.prototype._init = function () {
  7. // Call parent class's _init.
  8. TopLevelWindow.prototype._init.call(this);
  9. // Avoid recursive require.
  10. const { app } = electron;
  11. // Create WebContentsView.
  12. this.setContentView(new WebContentsView(this.webContents));
  13. const nativeSetBounds = this.setBounds;
  14. this.setBounds = (bounds, ...opts) => {
  15. bounds = {
  16. ...this.getBounds(),
  17. ...bounds
  18. };
  19. nativeSetBounds.call(this, bounds, ...opts);
  20. };
  21. // window.resizeTo(...)
  22. // window.moveTo(...)
  23. this.webContents.on('move', (event, size) => {
  24. this.setBounds(size);
  25. });
  26. // Hide the auto-hide menu when webContents is focused.
  27. this.webContents.on('activate', () => {
  28. if (process.platform !== 'darwin' && this.autoHideMenuBar && this.isMenuBarVisible()) {
  29. this.setMenuBarVisibility(false);
  30. }
  31. });
  32. // Change window title to page title.
  33. this.webContents.on('page-title-updated', (event, title, ...args) => {
  34. // Route the event to BrowserWindow.
  35. this.emit('page-title-updated', event, title, ...args);
  36. if (!this.isDestroyed() && !event.defaultPrevented) this.setTitle(title);
  37. });
  38. // Sometimes the webContents doesn't get focus when window is shown, so we
  39. // have to force focusing on webContents in this case. The safest way is to
  40. // focus it when we first start to load URL, if we do it earlier it won't
  41. // have effect, if we do it later we might move focus in the page.
  42. //
  43. // Though this hack is only needed on macOS when the app is launched from
  44. // Finder, we still do it on all platforms in case of other bugs we don't
  45. // know.
  46. this.webContents.once('load-url', function () {
  47. this.focus();
  48. });
  49. // Redirect focus/blur event to app instance too.
  50. this.on('blur', (event) => {
  51. app.emit('browser-window-blur', event, this);
  52. });
  53. this.on('focus', (event) => {
  54. app.emit('browser-window-focus', event, this);
  55. });
  56. // Subscribe to visibilityState changes and pass to renderer process.
  57. let isVisible = this.isVisible() && !this.isMinimized();
  58. const visibilityChanged = () => {
  59. const newState = this.isVisible() && !this.isMinimized();
  60. if (isVisible !== newState) {
  61. isVisible = newState;
  62. const visibilityState = isVisible ? 'visible' : 'hidden';
  63. this.webContents.emit('-window-visibility-change', visibilityState);
  64. }
  65. };
  66. const visibilityEvents = ['show', 'hide', 'minimize', 'maximize', 'restore'];
  67. for (const event of visibilityEvents) {
  68. this.on(event, visibilityChanged);
  69. }
  70. // Notify the creation of the window.
  71. const event = process.electronBinding('event').createEmpty();
  72. app.emit('browser-window-created', event, this);
  73. Object.defineProperty(this, 'devToolsWebContents', {
  74. enumerable: true,
  75. configurable: false,
  76. get () {
  77. return this.webContents.devToolsWebContents;
  78. }
  79. });
  80. };
  81. const isBrowserWindow = (win) => {
  82. return win && win.constructor.name === 'BrowserWindow';
  83. };
  84. BrowserWindow.fromId = (id) => {
  85. const win = TopLevelWindow.fromId(id);
  86. return isBrowserWindow(win) ? win : null;
  87. };
  88. BrowserWindow.getAllWindows = () => {
  89. return TopLevelWindow.getAllWindows().filter(isBrowserWindow);
  90. };
  91. BrowserWindow.getFocusedWindow = () => {
  92. for (const window of BrowserWindow.getAllWindows()) {
  93. if (window.isFocused() || window.isDevToolsFocused()) return window;
  94. }
  95. return null;
  96. };
  97. BrowserWindow.fromWebContents = (webContents) => {
  98. for (const window of BrowserWindow.getAllWindows()) {
  99. if (window.webContents && window.webContents.equal(webContents)) return window;
  100. }
  101. };
  102. BrowserWindow.fromBrowserView = (browserView) => {
  103. for (const window of BrowserWindow.getAllWindows()) {
  104. if (window.getBrowserView() === browserView) return window;
  105. }
  106. return null;
  107. };
  108. // Helpers.
  109. Object.assign(BrowserWindow.prototype, {
  110. loadURL (...args) {
  111. return this.webContents.loadURL(...args);
  112. },
  113. getURL (...args) {
  114. return this.webContents.getURL();
  115. },
  116. loadFile (...args) {
  117. return this.webContents.loadFile(...args);
  118. },
  119. reload (...args) {
  120. return this.webContents.reload(...args);
  121. },
  122. send (...args) {
  123. return this.webContents.send(...args);
  124. },
  125. openDevTools (...args) {
  126. return this.webContents.openDevTools(...args);
  127. },
  128. closeDevTools () {
  129. return this.webContents.closeDevTools();
  130. },
  131. isDevToolsOpened () {
  132. return this.webContents.isDevToolsOpened();
  133. },
  134. isDevToolsFocused () {
  135. return this.webContents.isDevToolsFocused();
  136. },
  137. toggleDevTools () {
  138. return this.webContents.toggleDevTools();
  139. },
  140. inspectElement (...args) {
  141. return this.webContents.inspectElement(...args);
  142. },
  143. inspectSharedWorker () {
  144. return this.webContents.inspectSharedWorker();
  145. },
  146. inspectServiceWorker () {
  147. return this.webContents.inspectServiceWorker();
  148. },
  149. showDefinitionForSelection () {
  150. return this.webContents.showDefinitionForSelection();
  151. },
  152. capturePage (...args) {
  153. return this.webContents.capturePage(...args);
  154. },
  155. setTouchBar (touchBar) {
  156. electron.TouchBar._setOnWindow(touchBar, this);
  157. },
  158. setBackgroundThrottling (allowed) {
  159. this.webContents.setBackgroundThrottling(allowed);
  160. }
  161. });
  162. // Deprecations
  163. deprecate.fnToProperty(BrowserWindow.prototype, 'autoHideMenuBar', '_isMenuBarAutoHide', '_setAutoHideMenuBar');
  164. deprecate.fnToProperty(BrowserWindow.prototype, 'minimizable', '_isMinimizable', '_setMinimizable');
  165. deprecate.fnToProperty(BrowserWindow.prototype, 'maximizable', '_isMaximizable', '_setMaximizable');
  166. deprecate.fnToProperty(BrowserWindow.prototype, 'resizable', '_isResizable', '_setResizable');
  167. deprecate.fnToProperty(BrowserWindow.prototype, 'fullScreenable', '_isFullScreenable', '_setFullScreenable');
  168. deprecate.fnToProperty(BrowserWindow.prototype, 'closable', '_isClosable', '_setClosable');
  169. deprecate.fnToProperty(BrowserWindow.prototype, 'movable', '_isMovable', '_setMovable');
  170. module.exports = BrowserWindow;