个人网站做博客还是做论坛,开发公司安置房项目工程推进大会,自己建一个网站能过期吗,做签证的网站这里写自定义目录标题 安装electron第一种方式#xff1a;vue init electron-vue第二种方式#xff1a;vue add electron-builder 启动electron调试功能#xff1a;background操作和使用1、覆盖窗口的菜单上下文、右键菜单2、监听关闭事件、阻止默认行为3、创建悬浮窗口4、窗… 这里写自定义目录标题 安装electron第一种方式vue init electron-vue第二种方式vue add electron-builder 启动electron调试功能background操作和使用1、覆盖窗口的菜单上下文、右键菜单2、监听关闭事件、阻止默认行为3、创建悬浮窗口4、窗口置顶5、绑定全局快捷键 完整代码background.js打包问题1、electron-v12.2.3-win32-x64.zip2、winCodeSign-2.6.0.7z.zip3、nsis 和 nsis-resources 官方文档 https://www.electronjs.org/zh/docs/latest/api/menu
安装electron
安装electron有两种方式两种方式创建的项目结构大不相同
以下内容主要讲解第二种方式在现有的vue项目中使用electron
// 方式一基于electron-vue 创建新项目
vue init simulatedgreg/electron-vue 项目名 // 方式二在现有的vue项目中安装electron包
vue add electron-builder第一种方式vue init electron-vue
vue init simulatedgreg/electron-vue 项目名 整体结构如下 package.json大致的结构如下
{name: name,version: 0.0.1,author: jmyinjg jmyinjg163.com,description: An electron-vue project,license: null,main: ./dist/electron/main.js,scripts: {build: node .electron-vue/build.js electron-builder,build:dir: node .electron-vue/build.js electron-builder --dir,build:clean: cross-env BUILD_TARGETclean node .electron-vue/build.js,build:web: cross-env BUILD_TARGETweb node .electron-vue/build.js,dev: node .electron-vue/dev-runner.js,pack: npm run pack:main npm run pack:renderer,pack:main: cross-env NODE_ENVproduction webpack --progress --colors --config .electron-vue/webpack.main.config.js,pack:renderer: cross-env NODE_ENVproduction webpack --progress --colors --config .electron-vue/webpack.renderer.config.js,postinstall: },build: {productName: midtools,appId: com.jthe.midtools,directories: {output: build},files: [dist/electron/**/*],dmg: {contents: [{x: 410,y: 150,type: link,path: /Applications},{x: 130,y: 150,type: file}]},mac: {icon: build/icons/icon.icns},win: {icon: build/icons/icon.ico},linux: {icon: build/icons}},dependencies: {jmyinjg/topsdk: ^1.6.0,ali-oss: ^6.9.0,axios: ^0.18.0,cheerio: ^1.0.0-rc.3,iconv-lite: ^0.5.1,mysql: ^2.18.1,request: ^2.88.2,superagent: ^5.2.2,uuid: ^8.1.0,view-design: ^4.2.0,vue: ^2.5.16,vue-electron: ^1.0.6,vue-router: ^3.0.1,vuex: ^3.0.1,vuex-electron: ^1.0.0},devDependencies: {ajv: ^6.5.0,babel-core: ^6.26.3,babel-loader: ^7.1.4,babel-minify-webpack-plugin: ^0.3.1,babel-plugin-import: ^1.13.0,babel-plugin-transform-runtime: ^6.23.0,babel-preset-env: ^1.7.0,babel-preset-stage-0: ^6.24.1,babel-register: ^6.26.0,cfonts: ^2.1.2,chalk: ^2.4.1,copy-webpack-plugin: ^4.5.1,cross-env: ^5.1.6,css-loader: ^0.28.11,del: ^3.0.0,devtron: ^1.4.0,electron: ^2.0.4,electron-builder: ^20.19.2,electron-debug: ^1.5.0,electron-devtools-installer: ^2.2.4,file-loader: ^1.1.11,html-webpack-plugin: ^3.2.0,mini-css-extract-plugin: 0.4.0,multispinner: ^0.2.1,node-loader: ^0.6.0,style-loader: ^0.21.0,url-loader: ^1.0.1,vue-html-loader: ^1.2.4,vue-loader: ^15.2.4,vue-style-loader: ^4.1.0,vue-template-compiler: ^2.5.16,webpack: ^4.15.1,webpack-cli: ^3.0.8,webpack-dev-server: ^3.1.4,webpack-hot-middleware: ^2.22.2,webpack-merge: ^4.1.3}
}
第二种方式vue add electron-builder
vue add electron-builder整体结构如下 package.json大致的结构如下
{name: name,productName: 应用名称,version: 1.5.0,private: true,scripts: {serve: vue-cli-service serve,build: vue-cli-service build,lint: vue-cli-service lint,electron:build: vue-cli-service electron:build,electron:serve: vue-cli-service electron:serve,postinstall: electron-builder install-app-deps,postuninstall: electron-builder install-app-deps},main: background.js,dependencies: {axios: ~0.21.1,core-js: ~3.15.2,vue: ~3.1.5,vue-axios: ~3.2.4,vue-router: ~4.0.10,vuex: ~4.0.2,......},devDependencies: {vue/cli-plugin-babel: ~4.5.13,vue/cli-plugin-eslint: ~4.5.13,vue/cli-plugin-router: ~4.5.13,vue/cli-plugin-vuex: ~4.5.13,vue/cli-service: ~4.5.13,vue/compiler-sfc: ~3.1.5,babel-eslint: ~10.1.0,compression-webpack-plugin: ~6.1.1,electron: ^12.0.0,electron-devtools-installer: ^3.1.0,eslint: ~6.8.0,eslint-plugin-vue: ~7.13.0,postcss: ~8.3.5,vue-cli-plugin-electron-builder: ~2.1.1},browserslist: [ 1%,last 2 versions,not dead]
} 启动electron
安装完成后直接启动一下看看效果
npm run electron:serveReload CtrlR 刷新 Toggle Developer Tools CtrlShiftI 打开开发者工具 调试功能background操作和使用
use strictimport { app, protocol, BrowserWindow } from electron
import { createProtocol } from vue-cli-plugin-electron-builder/lib
import installExtension, { VUEJS_DEVTOOLS } from electron-devtools-installer
const isDevelopment process.env.NODE_ENV ! productionprotocol.registerSchemesAsPrivileged([{ scheme: app, privileges: { secure: true, standard: true } }
])// 创建主窗口
async function createWindow() {const win new BrowserWindow({width: 800, // 窗口的默认宽度height: 600, // 窗口的默认高度title: 当前窗口的标题,webPreferences: {nodeIntegration: process.env.ELECTRON_NODE_INTEGRATION,contextIsolation: !process.env.ELECTRON_NODE_INTEGRATION}})if (process.env.WEBPACK_DEV_SERVER_URL) {await win.loadURL(process.env.WEBPACK_DEV_SERVER_URL)// 开发环境下打开调试工具if (!process.env.IS_TEST) win.webContents.openDevTools()} else {createProtocol(app)// 主窗口创建完成后进入到win.loadURL(app://./index.html)}
}
// 监听整个应用的关闭操作
app.on(window-all-closed, () {if (process.platform ! darwin) {// 关闭应用app.quit()}
})app.on(activate, () {if (BrowserWindow.getAllWindows().length 0) createWindow()
})app.on(ready, async () {if (isDevelopment !process.env.IS_TEST) {try {await installExtension(VUEJS_DEVTOOLS)} catch (e) {console.error(Vue Devtools failed to install:, e.toString())}}createWindow()
})if (isDevelopment) {if (process.platform win32) {process.on(message, (data) {if (data graceful-exit) {app.quit()}})} else {process.on(SIGTERM, () {app.quit()})}
}
1、覆盖窗口的菜单上下文、右键菜单 import {BrowserWindow, Menu } from electron
let mainWin// 主窗口的顶栏菜单
const template [{label: 后退,click: () {// 判断 浏览器是否可以后退到前一页面。if (mainWin.webContents.canGoBack()) {// 使浏览器回退到上一个页面。mainWin.webContents.goBack();}}},{label: 前进,click: () {// 判断 浏览器是否可以前进到下一页面。if (mainWin.webContents.canGoForward()) {// 使浏览器前进到下一个页面。mainWin.webContents.goForward();}}},{label: 刷新,click: () {mainWin.webContents.reloadIgnoringCache();}},
];// 右键菜单
const contextMenu Menu.buildFromTemplate([{ label: 复制, role: copy },{ label: 粘贴, role: paste }
]);async function createWindow() {mainWin new BrowserWindow({...})// 部署顶栏菜单const menu Menu.buildFromTemplate(template);Menu.setApplicationMenu(menu);// 部署右键菜单mainWin.webContents.on(context-menu, () {contextMenu.popup({ window: mainWin }); // 在指定窗口上显示上下文菜单});
}2、监听关闭事件、阻止默认行为
dialog.showMessageBoxSync会返回buttons的索引值 例如点击了“否”则choice0点击了“是”则choice1 注意如果点击了右上角的叉则choice0所以“是”只能写在“否”后面 不理解为什么要这么设计 import { BrowserWindow, dialog } from electron
let mainWinasync function createWindow() {mainWin new BrowserWindow({...})// 监听 主窗口 右上角的关闭事件mainWin.on(close, (e) {e.preventDefault(); // 阻止窗口默认的关闭行为/*** 弹出 对话框询问用户是否真的想要退出* 这里的choice 值是buttons的索引* 例如点击了“否”则choice0点击了“是”则choice1* 注意如果点击了右上角的叉则choice0所以“是”只能写在“否”后面*/ const choice dialog.showMessageBoxSync(null, {type: info,buttons: [否, 是],title: 退出,message: 确定要退出吗再次开启需重新登录,});// 如果用户选择“是”则关闭窗口if (choice 1) {// 关闭窗口并释放内存mainWin.destroy(); // 关闭主窗口app.quit()}})
}3、创建悬浮窗口
创建第二个窗口——悬浮球透明背景点击悬浮球促使主窗口进入到某个页面
包含的知识点 1、多个窗口悬浮球窗口 2、其他窗口促使主窗口路由跳转 3、区分当前环境是electron还是浏览器 4、窗口的显示和隐藏
background.js
import { BrowserWindow, ipcMain, screen } from electronlet mainWinRoutePath /; // 主窗口的当前路由
let mainWin, ballWinasync function createSBallWindow() {mainWin new BrowserWindow({...})...
}// 创建 工具球窗口
async function createSBallWindow() {ballWin new BrowserWindow({width: 65, // 悬浮窗口的宽度 比实际DIV的宽度要多5px用于处理阴影height: 65, // 悬浮窗口的高度 比实际DIV的高度要多5px用于处理阴影type: toolbar, //创建的窗口类型为工具栏窗口frame: false, // 是否创建有边框的窗口(含最大化/最小化/关闭功能)false创建无边框窗口resizable: false, // 是否允许窗口大小缩放movable: true, // 是否可以移动show: true, // 是否在创建完成后让窗口显示如果希望在用户登录后再显示工具球则设置成false再通过消息来打开窗口transparent: true, // 设置透明只有在frame为false时才能生效hasShadow: false, // 是否显示阴影alwaysOnTop: true, // 窗口是否总是显示在其他窗口之前webPreferences: {// devTools: true, // 是否打开调试工具如果要打开调试最好把窗口的默认大小调大一些且不要设置初始位置nodeIntegration: true,contextIsolation: false,}})// 通过获取用户屏幕的宽高来设置悬浮球的初始位置最好把窗口的默认大小调大一些且不要设置初始位置const size screen.getPrimaryDisplay().workAreaSizeballWin.setPosition(size.width - 150, size.height - 200) // 设置悬浮球位置if (process.env.WEBPACK_DEV_SERVER_URL) {await ballWin.loadURL(${process.env.WEBPACK_DEV_SERVER_URL}ball)// ballWin.webContents.openDevTools(); // 打开调试工具} else {await ballWin.loadURL(app://./ball.html)}ballWin.on(close, () {ballWin null})
}// 监听 open-mainWin-window 消息 显示 主窗口
ipcMain.on(open-mainWin-window, () {if (!mainWin) {return}mainWin.maximize() // 窗口最大化
})// 显示 工具球窗口
ipcMain.on(open-ballWin-window, () {if (ballWin) {ballWin.show()} else {// 若窗口不存在则先创建窗口再显示createSBallWindow()ballWin.show()}
});// 隐藏 工具球窗口
ipcMain.on(hide-ballWin-window, () {ballWin.hide()
});// 保存主窗口的当前路由
ipcMain.on(route-change, (event, route) {mainWinRoutePath route;
});// 返回保存的路由信息
ipcMain.handle(get-mainWin-route, () {return mainWinRoutePath;
});// 进入 主窗口的某个页面
ipcMain.on(change-page, async (event, url) {if (process.env.WEBPACK_DEV_SERVER_URL) {// 去除url开头的/ 避免造成 http://localhost:8080//...await mainWin.loadURL(${process.env.WEBPACK_DEV_SERVER_URL}${url.replace(/^\//, )})} else {await mainWin.loadURL(app://.${url})}
})悬浮球页面 ball.vue
templatediv classball clickgoFast!-- dblclick双击 --span工具球/span/div
/templatescript
// 判断是否在 electron 平台的环境当中
let ipcRenderer null
const isElectron navigator.userAgent.toLowerCase().indexOf( electron/) 0
if (isElectron) {ipcRenderer require(electron).ipcRenderer
}export default {name: ball,data() {return {}},created() {},methods: {goFast() {if (isElectron) {ipcRenderer.invoke(get-mainWin-route).then((route) {if (route ! /moral/record) {// 消息名称、传参argipcRenderer.send(change-page, /ball)}// 发送 open-ballWin-window 消息ipcRenderer.send(open-mainWin-window)});}}},
}
/scriptstyle
body {background: transparent;display: flex;justify-content: center;height: 100%;// 这个是用于 移动窗口/* -webkit-app-region: drag; */
}.ball {width: 60px;height: 60px;line-height: 60px;border-radius: 50%;box-sizing: border-box;background: var(--primary-color);box-shadow: 0 3px 5px 0 rgba(0, 0, 0, 0.4);color: #fff;background: linear-gradient(#40a9ff, #096dd9);text-align: center;cursor: pointer;font-size: 14px;/* -webkit-app-region: no-drag; */
}
/stylerouter.js
import { createRouter, createWebHistory } from vue-router;
// 判断是否在 electron 平台的环境当中
const isElectron navigator.userAgent.toLowerCase().indexOf( electron/) 0
let ipcRenderer null
if (isElectron) {ipcRenderer require(electron).ipcRenderer
}const router createRouter({routes: [{path: /index,component: () import(/views/index),meta: { title: 首页 },},{path: /ball,component: () import(/views/ball),meta: { title: 工具球 }},...],history: createWebHistory()
});
// 路由守卫
router.beforeEach((to, from, next) {if (isElectron) {ipcRenderer.send(route-change, to.path)}next()
})export default router;注意如果使用了screen一定要引入否则会启动失败 4、窗口置顶
// 置顶并显示 主窗口
ipcMain.on(open-mainWin-window, () {if (!mainWin) {return}mainWin.maximize() // 窗口最大化// 当 ballWin 失去置顶状态时将 mainWin 的置顶级别设为较高值mainWin.setAlwaysOnTop(true, normal, 1);mainWin.focus(); // 让窗口获得焦点mainWin.setAlwaysOnTop(false); // 如果不希望它一直保持在最上层可以之后立即取消置顶即点击其他应用时当前窗口会下移一层
})5、绑定全局快捷键
这里会有个问题注册之后只要这个窗口没有隐藏快捷键响应后还是会触发事件 例如下方是F5假设你在QQ应用上点了F5当前这个应用也会刷新
import { globalShortcut } from electron
let mainWin, ballWin
...// 全局快捷键 刷新globalShortcut.register(F5, () {if (mainWin ballWin) {mainWin.webContents.reloadIgnoringCache();ballWin.webContents.reloadIgnoringCache();}})完整代码background.js
包含 1、窗口的菜单、右键菜单、全局快捷键 2、监听窗口的关闭事件阻止默认行为 3、创建悬浮窗口、窗口的隐藏/显示促使其他窗口路径跳转 4、窗口置顶事件 5、区分当前环境是electron还是浏览器
use strictimport { app, protocol, BrowserWindow, ipcMain, dialog, Menu, screen, globalShortcut } from electron
import { createProtocol } from vue-cli-plugin-electron-builder/lib
import installExtension, { VUEJS_DEVTOOLS } from electron-devtools-installerconst path require(path);
const isDevelopment process.env.NODE_ENV ! productionprotocol.registerSchemesAsPrivileged([{ scheme: app, privileges: { secure: true, standard: true } }
])let mainWinRoutePath /; // 主窗口的当前路由
let mainWin, ballWin// 主窗口的顶栏菜单
const template [{label: 后退,click: () {if (mainWin.webContents.canGoBack()) {mainWin.webContents.goBack();}}},{label: 前进,click: () {if (mainWin.webContents.canGoForward()) {mainWin.webContents.goForward();}}},{label: 刷新,click: () {mainWin.webContents.reloadIgnoringCache();}},
];// 右键菜单
const contextMenu Menu.buildFromTemplate([{ label: 复制, role: copy },{ label: 粘贴, role: paste }
]);async function createWindow() {mainWin new BrowserWindow({width: 800,height: 800,title: 智慧校园,icon: path.join(__dirname, process.env.VUE_APP_LOGO),webPreferences: {nodeIntegration: process.env.ELECTRON_NODE_INTEGRATION,contextIsolation: !process.env.ELECTRON_NODE_INTEGRATION}})const menu Menu.buildFromTemplate(template);Menu.setApplicationMenu(menu);mainWin.webContents.on(context-menu, () {contextMenu.popup({ window: mainWin }); // 在指定窗口上显示上下文菜单});if (process.env.WEBPACK_DEV_SERVER_URL) {await mainWin.loadURL(process.env.WEBPACK_DEV_SERVER_URL index)if (!process.env.IS_TEST) mainWin.webContents.openDevTools()} else {createProtocol(app)mainWin.loadURL(app://./index.html)}// 监听 主窗口 右上角的关闭事件mainWin.on(close, (e) {e.preventDefault(); // 阻止窗口默认的关闭行为// 显示一个对话框询问用户是否真的想要退出const choice dialog.showMessageBoxSync(null, {type: info,buttons: [否, 是],title: 退出,message: 确定要退出吗再次开启需重新登录,});// 如果用户选择“是”则关闭窗口if (choice 1) {// 关闭窗口并释放内存mainWin.destroy(); // 关闭主窗口app.quit()}})mainWin.once(ready-to-show, () {mainWin.show()})
}// 创建 工具球窗口
async function createSBallWindow() {ballWin new BrowserWindow({width: 65, // 悬浮窗口的宽度 比实际DIV的宽度要多5pxheight: 65, // 悬浮窗口的高度 比实际DIV的高度要多5pxtype: toolbar, //创建的窗口类型为工具栏窗口frame: false, // 是否创建有边框的窗口(含最大化/最小化/关闭功能)false创建无边框窗口resizable: false, // 是否允许窗口大小缩放movable: true, // 是否可以移动show: true, // 是否在创建完成后让窗口显示transparent: true, // 设置透明hasShadow: false, // 是否显示阴影alwaysOnTop: true, // 窗口是否总是显示在其他窗口之前webPreferences: {// devTools: true, // 是否打开调试工具打开调试则最好调整窗口的大小nodeIntegration: true,contextIsolation: false,}})// 通过获取用户屏幕的宽高来设置悬浮球的初始位置const size screen.getPrimaryDisplay().workAreaSizeballWin.setPosition(size.width - 150, size.height - 200) // 设置悬浮球位置if (process.env.WEBPACK_DEV_SERVER_URL) {await ballWin.loadURL(${process.env.WEBPACK_DEV_SERVER_URL}ball)// ballWin.webContents.openDevTools(); // 打开调试工具} else {await ballWin.loadURL(app://./ball.html)}ballWin.on(close, () {ballWin null})
}app.on(window-all-closed, () {if (process.platform ! darwin) {app.quit()}
})// 置顶并显示 主窗口
ipcMain.on(open-mainWin-window, () {if (!mainWin) {return}mainWin.maximize() // 窗口最大化if (ballWin) {ballWin.on(always-on-top-changed, (event, isAlwaysOnTop) {if (isAlwaysOnTop) {// 当 ballWin 处于最顶端时将 mainWin 的置顶级别设为较低值mainWin.setAlwaysOnTop(true, normal, -1);mainWin.focus(); // 让窗口获得焦点} else {// 当 ballWin 失去置顶状态时将 mainWin 的置顶级别设为较高值mainWin.setAlwaysOnTop(true, normal, 1);mainWin.focus();mainWin.setAlwaysOnTop(false); // 如果不希望它一直保持在最上层可以之后立即取消置顶}})ballWin.setAlwaysOnTop(true, normal, 1)} else {mainWin.setAlwaysOnTop(true);mainWin.focus();mainWin.setAlwaysOnTop(false);}
})// 隐藏 主窗口
ipcMain.on(hide-mainWin-window, () {mainWin.hide()
})// 显示 工具球窗口
ipcMain.on(open-ballWin-window, () {if (ballWin) {ballWin.show()} else {createSBallWindow()ballWin.show()}
});// 隐藏 工具球窗口
ipcMain.on(hide-ballWin-window, () {ballWin.hide()
});// 保存主窗口的当前路由
ipcMain.on(route-change, (event, route) {mainWinRoutePath route;
});// 返回保存的路由信息
ipcMain.handle(get-mainWin-route, () {return mainWinRoutePath;
});// 进入 主窗口的某个页面
ipcMain.on(change-page, async (event, url) {if (process.env.WEBPACK_DEV_SERVER_URL) {// 去除url开头的/ 避免造成 http://localhost:8080//...await mainWin.loadURL(${process.env.WEBPACK_DEV_SERVER_URL}${url.replace(/^\//, )})} else {await mainWin.loadURL(app://.${url})}
})app.on(activate, () {if (BrowserWindow.getAllWindows().length 0) createWindow()
})app.on(ready, async () {if (isDevelopment !process.env.IS_TEST) {try {await installExtension(VUEJS_DEVTOOLS)} catch (e) {console.error(Vue Devtools failed to install:, e.toString())}}//创建主窗口createWindow()//创建球形窗口createSBallWindow()// 注册 全局快捷键 刷新globalShortcut.register(F5, () {if (mainWin ballWin) {mainWin.webContents.reloadIgnoringCache();ballWin.webContents.reloadIgnoringCache();}})
})if (isDevelopment) {if (process.platform win32) {process.on(message, (data) {if (data graceful-exit) {app.quit()}})} else {process.on(SIGTERM, () {app.quit()})}
} 打包问题
electron-builder打包electron-v12.2.3-win32-x64.zip下载失败这种情况通常是有electron的4个包无法下载成功手动下载后放入到系统对应的文件夹中即可。 分别是 electron-v12.2.3-win32-x64.zip winCodeSign-2.6.0.7z.zip nsis-resources3.4.1 nsis-3.4.1 INFO Building app with electron-builder:• electron-builder version22.14.13 os10.0.22621• description is missed in the package.json appPackageFileD:\web\campus\wisdom-campus-desktop\dist_electron\bundled\package.json• author is missed in the package.json appPackageFileD:\web\campus\wisdom-campus-desktop\dist_electron\bundled\package.json• writing effective config filedist_electron\builder-effective-config.yaml• packaging platformwin32 archx64 electron12.2.3 appOutDirdist_electron\win-unpacked⨯ Get https://github.com/electron/electron/releases/download/v12.2.3/electron-v12.2.3-win32-x64.zip: proxyconnect tcp: dial tcp :0: connectex: The requested address is not valid in its context.按照错误提示是electron-v12.2.3-win32-x64.zip这个文件下载失败可以利用报错信息中的https://github.com/electron/electron/releases/download/v12.2.3/electron-v12.2.3-win32-x64.zip 这个地址进行下载或者到淘宝的镜像地址里去下载
1、electron-v12.2.3-win32-x64.zip
到淘宝的镜像地址里去下载https://registry.npmmirror.com/binary.html?pathelectron/依次找到 12.2.3版本下 - electron-v12.2.3-win32-x64.zip 通常系统会默认隐藏AppData关闭隐藏即可 下载后将压缩包解压到这个目录里 C:\Users\你的用户名\AppData\Local\electron\Cache 解压后的文件
2、winCodeSign-2.6.0.7z.zip
https://registry.npmmirror.com/binary.html?pathelectron-builder-binaries/winCodeSign-2.6.0/winCodeSign-2.6.0.7z
下载后将压缩包解压解压到这个目录里 C:\Users\你的用户名\AppData\Local\electron-builder\Cache\winCodeSign 注意这里最后一层是winCodeSign有的文章里显示的是在Cache文件里解压这样是错误的 解压后的
3、nsis 和 nsis-resources
https://registry.npmmirror.com/binary.html?pathelectron-builder-binaries/
下载后将2个压缩包都解压到nsis文件价中没有nsis文件夹就自己创建一个 C:\Users\你的用户名\AppData\Local\electron-builder\Cache\nsis 解压后的
最后再改一下镜像
用cnpm
npm install -g cnpm --registryhttps://registry.npm.taobao.org或者直接用npm
npm config set registry https://registry.npmmirror.comhttps://registry.npm.taobao.org 淘宝镜像在2024年1月份已经过期了目前虽然还能使用 但是可以观察到最终还是代理到了 https://registry.npmmirror.com所以不如直接用 ** https://registry.npmmirror.com**
再次打包electron 应该就没有什么问题了