开发者问题收集

Electron Remote(关闭、最小化等)不起作用(无法读取未定义的属性‘getCurrentWindow’)

2020-08-30
11660

我试图在 Electron JS 应用程序中的无框窗口上添加关闭和最小化按钮。但无论如何它都不起作用。它总是显示“无法读取未定义的属性‘getCurrentWindow’”错误。这是我的代码:

const {remote} = require('electron');

document.getElementById('minimize').onclick = function() {
    var window = remote.getCurrentWindow();
    window.minimize();
}

document.getElementById('close').onclick = function() {
    var window = remote.getCurrentWindow();
    window.close();
}

我还在 main.js 中添加了 webPreferences:{nodeIntegration: true}。

win = new BrowserWindow({width: 990, height: 660, title: "Okkhor52 Tools", show: false, resizable: false, frame: false, webPreferences: {nodeIntegration: true}});

请给我一个解决方案,我尝试在很多地方找到这个问题的解决方案,但我没有得到确切的解决方案。

3个回答

解决方案非常简单。只需在 main.js 中的 BrowserWindow 中添加 webPreferences: {enableRemoteModule: true 即可。

win = new BrowserWindow({
    width: 990, 
    height: 660,
    title: "Okkhor52 Tools", 
    resizable: false, 
    frame: false, 
    webPreferences: {
        nodeIntegration: true, 
        enableRemoteModule: true
    }
}); 

除了 enableRemoteModule: true 之外,您还需要在 webPreference 中添加 nodeIntegration: true ,否则如果您从其他 javascript 调用 electron(像这样 const {remote} = require('electron'); ),它将不起作用。

Nurul Alam Ador
2020-08-30

如果您已将 enableRemoteModule 设置为 true,但仍然遇到此问题,则很可能是因为您需要 远程模块 ,或者需要一个在主进程中需要它的文件,至少对我来说是这样。远程模块在主进程中不是必需的,仅适用于渲染器进程。

如果您需要或需要另一个在主进程中使用 require("electron").remote.getCurrentWindow() 的 javascript 文件,那么您将收到此错误。

只需在主进程中不以任何方式包含该代码即可解决此问题。

avisk
2020-10-13

根据 这篇 文章,我们根本不应该使用“remote”。更好的方法是通过 发送消息 与渲染器进行通信。

首先,您需要 WindowNodeHandlers 类来调用 BrowserWindow 最大化/取消最大化操作并更新 isMaximized 标志:

class WindowNodeHandlers {
  ipcMain.on('maximize', () => {
    BrowserWindow.getFocusedWindow()?.maximize();
  });

  ipcMain.on('unmaximize', () => {
    BrowserWindow.getFocusedWindow()?.unmaximize();
  });

  ipcMain.on('isMaximized', (event) => {
    event.returnValue = BrowserWindow.getFocusedWindow()?.isMaximized();
  });
}

然后创建 ElectronWindowApi 类以在渲染器和主进程之间进行通信:

class ElectronWindowApi implements MainWindowApi {
  maximize(): void {
   ipcRenderer.send('maximize');
  }

  unmaximize(): void {
   ipcRenderer.send('unmaximize');
  }

  isMaximized(): boolean {
   return ipcRenderer.sendSync('isMaximized') as boolean;
  }
 }

之后,在您的 createWindow 函数中创建 WindowNodeHandlers 实例并为这些事件添加监听器,这些事件会将消息发送回渲染器进程:

const createWindow = async () => {
 ...
 new WindowNodeHandlers();

 mainWindow.on('maximize', () =>
   mainWindow?.webContents.send('window-maximized')
 );

 mainWindow.on('unmaximize', () =>
   mainWindow?.webContents.send('window-unmaximized')
 );
}

最后一件事 - 为这些添加处理程序消息并使用 ElectronWindowApi 在渲染器端调用最大化/取消最大化操作:

...
const windowApi = new ElectronWindowApi();
const [isMaximized, setIsMaximized] = useState(windowApi.isMaximized());
const onMaximized = () => setIsMaximized(true);
const onRestore = () => setIsMaximized(false);

const toggleMaximize = () => {
  isMaximized ? windowApi.unmaximize() : windowApi.maximize();
};

useEffect(() => {
  ipcRenderer.on('window-maximized', onMaximized);
  ipcRenderer.on('window-unmaximized', onRestore);
}, []);

return (
   <IconButton
      aria-label={isMaximized ? 'minimize' : 'maximize'}
      onClick={toggleMaximize}
    >
      {isMaximized ? (
        <SvgIcon
          component={MinimizeWindowIcon}
        />
      ) : (
        <SvgIcon
          component={MaximizeWindowIcon}
        />
      )}
    </IconButton>
)
...
Mihail Serikov
2021-09-14