Electron 在 Windows 环境下启用 webContents.openDevTools 不生效

2,345 阅读2分钟

前言

最近一直在进行 Electron 桌面客户端的开发,但是总是能遇到一些玄学问题,标题所说就是其中一个。

问题

编写以下代码能在 macOS 环境下正常打开开发者工具,而在 Windows 环境下则莫名其妙失效了

import { app, BrowserWindow } from 'electron'
let win: BrowserWindow | undefined;
function createWindow() {
    win = new BrowserWindow()
    win.loadURL('http://localhost:3001');
    // 打开开发者工具
    win.webContents.openDevTools({ mode: 'detach' });
    
    // 解决 Windows 窗口不出现的问题 
    win.once('ready-to-show', () => {
        win.show();
    });
    
    // 当 window 被关闭,这个事件会被触发
    win.on('closed', () => {
        // 取消引用 window 对象,如果你的应用支持多窗口的话, 
        // 通常会把多个 window 对象存放在一个数组里面, 
        // 与此同时,你应该删除相应的元素。
        win = null;
    })
}

// 这段程序将会在 Electron 结束初始化
// 和创建浏览器窗口的时候调用
// 部分 API 在 ready 事件触发后才能使用。
app.whenReady().then(() => {
    // 创建窗口
    createWindow();
    
    app.on('activate', () => { 
        // 在macOS上,当单击dock图标并且没有其他窗口打开时, 
        // 通常在应用程序中重新创建一个窗口。 
        if (win === null) { 
            createWindow() 
        } 
    })
})

// 除了 macOS 外,当所有窗口都被关闭的时候退出程序。 因此,通常对程序和它们在
// 任务栏上的图标来说,应当保持活跃状态,直到用户使用 Cmd + Q 退出。
app.on('window-all-closed', () => { 
    // 在 macOS 上,除非用户用 Cmd + Q 确定地退出, 
    // 否则绝大部分应用及其菜单栏会保持激活。 
    if (process.platform !== 'darwin') { 
        app.quit() 
    } 
});


解决方案

import { app, BrowserWindow } from 'electron'
let win: BrowserWindow | undefined;
let devtools: BrowserWindow | undefined;
function createWindow() {
    win = new BrowserWindow();
    devtools = new BrowserWindow();
    win.loadURL('http://localhost:3001');
    
    // 解决 Windows 无法正常打开开发者工具的问题 ↓
    win.webContents.setDevToolsWebContents(devtools.webContents)
    // 打开开发者工具
    win.webContents.openDevTools({ mode: 'detach' });
    
    // 解决 Windows 窗口不出现的问题 
    win.once('ready-to-show', () => {
        win.show();
    });
    
    // 当 window 被关闭,这个事件会被触发
    win.on('closed', () => {
        // 取消引用 window 对象,如果你的应用支持多窗口的话, 
        // 通常会把多个 window 对象存放在一个数组里面, 
        // 与此同时,你应该删除相应的元素。
        win = null;
    })
}

// 这段程序将会在 Electron 结束初始化
// 和创建浏览器窗口的时候调用
// 部分 API 在 ready 事件触发后才能使用。
app.whenReady().then(() => {
    // 创建窗口
    createWindow();
    
    app.on('activate', () => { 
        // 在macOS上,当单击dock图标并且没有其他窗口打开时, 
        // 通常在应用程序中重新创建一个窗口。 
        if (win === null) { 
            createWindow() 
        } 
    })
})

// 除了 macOS 外,当所有窗口都被关闭的时候退出程序。 因此,通常对程序和它们在
// 任务栏上的图标来说,应当保持活跃状态,直到用户使用 Cmd + Q 退出。
app.on('window-all-closed', () => { 
    // 在 macOS 上,除非用户用 Cmd + Q 确定地退出, 
    // 否则绝大部分应用及其菜单栏会保持激活。 
    if (process.platform !== 'darwin') { 
        app.quit() 
    } 
});