Electron 安装以及搭建一个工程
安装Node.js
在使用Electron进行开发之前,需要安装 Node.js。 官方建议使用最新的LTS版本。
检查 Node.js 是否正确安装:
# 查看node版本
node -v
# 查看npm版本
npm -v
注意
开发者需要在开发环境安装 Node.js 才能编写 Electron 项目,但是 Electron 应用程序 不使用系统本地的 Node.js 环境来运行它的代码。
Electron 应用程序 使用它内置的 Node.js 运行时。 这意味着 终端用户 不需要安装 Node.js 环境也可以运行Electron 应用程序。
安装Electron
Electron 应用程序遵循与其他 Node.js 项目相同的结构。
首先创建一个文件夹my-electron-app并在vscode 编译器中打开文件夹。
初始化 npm 包:
npm init
init 初始化命令会提示开发者在项目初始化配置中设置一些值,有几条规则需要遵循:
entry point应为main.js。author与description可为任意值,但对于应用打包是必填项。
生成的 package.json 文件应该像这样:
{"name": "my-electron-app","version": "1.0.0","description": "一个测试用的electron项目","main": "main.js","author": "zhangSan", "license": "ISC"
}
在项目中安装electron:
npm install --save-dev electron# 可以简写
npm i electron -D
注意 :electron是开发依赖。
electron依赖非常难下载,总是下载到中途就失败了。
查看官方文档:
在运行 npm install electron 时,有些用户会偶尔遇到安装问题。
在大多数情况下,这些错误都是由网络问题导致,而不是因为 electron npm 包的问题。 如ELIFECYCLE、EAI_AGAIN、ECONNRESET和ETIMEDOUT等错误都是此类网络问题的标志。 最佳的解决方法是尝试切换网络,或是稍后再尝试安装。
fine,意思是网络问题咯,千M网下载不下来也是离谱啊…
解决方案
-
如果通过
npm安装失败,你也可以尝试通过从 electron/electron/release 直接下载 Electron -
如果安装失败并报错
EACCESS,可能需要修复npm权限。 -
如果上述报错持续出现,unsafe-perm 标志可能需要被设置为
true:
npm install electron --unsafe-perm=true
- 在较慢的网络上, 最好使用
--verbose标志来显示下载进度:
npm install --verbose electron
- 如果需要强制重新下载文件, 并且
SHASUM文件将force_no_cache环境变量设置为true。
我直接使用了第3点和第4点:
npm install electron -D --unsafe-perm=true --verbose
历时半个小时,这个依赖终于下载成功了! 感天动地!!
在 package.json 配置文件中的scripts字段下增加一条start命令:
{"scripts": {"start": "electron ."}
}
package.json 文件应该像这样:
{"name": "my-electron-app","version": "1.0.0","description": "一个测试用的electron项目","main": "main.js","scripts": {"start": "electron ."},"author": "zhangSan","license": "ISC","devDependencies": {"electron": "^32.1.2"}
}
执行start命令能在开发模式下打开应用:
npm start
执行命令直接就报错了:
没有找到模块main.js,请确认 package.json 中的 main 入口是合法的。

运行主进程
任何 Electron 应用程序的入口都是 main 文件。 这个文件控制了主进程,它运行在一个完整的Node.js环境中,负责控制应用的生命周期,显示原生界面,执行特殊操作并管理渲染器进程。
执行 npm start 期间,Electron 将依据应用中 package.json配置下main字段中配置的值查找此文件。
在项目的根目录下创建一个名为 main.js 的空文件。
再次执行 npm start ,不再报错,应用成功启动。但是,它不会做任何事,开发者也看不到启动的应用窗口,因为 main.js 是空白文件,没有添加任何代码!
在 main.js 中编写代码,创建⼀个基本窗⼝:
// main.js运⾏在应⽤的主进程上,⽆法访问Web相关API
// main.js主要负责:控制⽣命周期、显示界⾯、控制渲染进程等其他操作。
// 从electron中引入app、BrowserWindow
// app模块: 控制应用程序的事件生命周期。
// BrowserWindow模块: 创建和管理应用程序 窗口
const { app, BrowserWindow } = require('electron')function createWindow() {const win = new BrowserWindow({width: 500, // 窗口宽度height: 300 // 窗口高度})
}
// 在 Electron 中,只有在 app 模块的 ready 事件被激发后才能创建浏览器窗口。
app.on('ready', () => {// 当app准备好以后,创建窗口createWindow()
})
注意
可以通过使用 app.whenReady() API来监听 app 模块的 ready 事件:
app.whenReady().then(() => {createWindow()
})
再次执行 npm start ,应用启动成功,并且能看到应用窗口:

下图是应用自带的菜单:

如果不要菜单,需要在创建窗口时配置:autoHideMenuBar: true
修改 main.js,在窗口中展示一个远程页面:
const { app, BrowserWindow } = require('electron')function createWindow() {const win = new BrowserWindow({width: 500,height: 300,autoHideMenuBar: true})// 展示一个远程页面win.loadURL('https://lol.qq.com/main.shtml')// 可以在这里添加窗口的其他配置和事件处理
}
app.on('ready', () => {// 当app准备好的时候,创建窗口createWindow()
})
执行npm start,查看效果:

关于BrowserWindow的更多配置项,请参考官网:BrowserWindow实例属性
加载本地页面
在Electron中,各个窗口显示的内容可以是本地HTML文件,也可以是一个远程url。
创建 pages/index.html 编写内容::
<!DOCTYPE html>
<html lang="en"><head><meta charset="UTF-8"><!-- https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP --><metahttp-equiv="Content-Security-Policy"content="default-src 'self'; style-src 'self' 'unsafe-inline'; img-src 'self' data:;"/><title>Hello Electron!</title></head><body><h1>Hello Electron!</h1></body>
</html>
修改 mian.js 加载本地⻚⾯:
// 加载⼀个本地⻚⾯
win.loadFile('./pages/index.html')
执行npm start,查看效果:

可以通过快捷键ctrl+shift+i,打开控制台:

CSP配置说明
语法:
Content-Security-Policy: <policy-directive>; <policy-directive>
这是一个用于设置网页内容安全策略(Content Security Policy,简称 CSP)的 HTML 标签:
<metahttp-equiv="Content-Security-Policy"content="default-src 'self'; style-src 'self' 'unsafe-inline'; img-src 'self' data:;"
/>
上述配置的说明:
default-src 'self'default-src:配置加载策略,适⽤于所有未在其它指令中明确指定的资源类型。self:仅允许从同源的资源加载,禁⽌从不受信任的外部来源加载,提⾼安全性。
style-src 'self' 'unsafe-inline'style-src:指定样式表(CSS)的加载策略。self:仅允许从同源的资源加载,禁⽌从不受信任的外部来源加载,提⾼安全性。unsafe-inline:允许在HTML⽂档内使⽤内联样式。
img-src 'self' data:img-src:指定图像资源的加载策略。self:表示仅允许从同源加载图像。data::允许使⽤data: URI来嵌⼊图像。这种URI模式允许将图像数据直接嵌
⼊到HTML或CSS中,⽽不是通过外部链接引⽤。
HTTP 响应头 Content-Security-Policy 允许站点管理者控制用户代理能够为指定的页面加载哪些资源。除了少数例外情况,设置的政策主要涉及指定服务器的源和脚本结束点。
关于 CSP 的详细说明请参考:MDN-Content-Security-Policy、Electron Security
如果没有配置CSP,控制台会有⼀个安全警告:

管理窗口的生命周期
创建窗口
- 通常在主进程中创建窗口,可以使用
BrowserWindow类来创建窗口实例。
const { app, BrowserWindow } = require('electron')function createWindow() {const win = new BrowserWindow({width: 500,height: 300,autoHideMenuBar: true})// 展示一个远程页面win.loadURL('https://lol.qq.com/main.shtml')// 可以在这里添加窗口的其他配置和事件处理
}
app.on('ready', () => {// 当app准备好的时候,创建窗口createWindow()
})
窗口的显示与隐藏
win.show():显示窗口。通常在应用启动后或在特定事件触发时调用。win.hide():隐藏窗口。可以在需要隐藏窗口的情况下调用,比如最小化到系统托盘时。
窗口最小化、最大化、恢复
win.minimize():将窗口最小化到任务栏或 Dock。win.maximize():最大化窗口。win.unmaximize():如果窗口处于最大化状态,可以使用win.unmaximize()恢复到原始大小。
窗口事件监听
-
closed事件:- 当窗口关闭时触发。在这个事件处理函数中,可以进行一些清理工作,比如释放资源。
win.on('closed', () => { mainWindow = null; });
-
resize事件:
当窗口大小改变时触发。可以在这个事件处理函数中根据新的窗口大小调整应用的布局或进行其他相应的处理。 -
move事件:
当窗口位置改变时触发。可以用于记录窗口位置或进行与窗口位置相关的操作。
关闭所有窗口时退出应用 (Windows & Linux)
在Windows 和 Linux 系统:关闭所有窗口会完全退出应用程序。
为了实现这一点,需要监听 app 模块的 'window-all-closed' 事件。如果用户不是在 macOS(darwin) 上运行程序,则调用 app.quit()。
app.on('window-all-closed', () => {if (process.platform !== 'darwin') app.quit()
})
如果没有窗口打开则打开一个窗口 (macOS)
在 Linux 和 Windows 上,应用根本不存在是否被激活的说法,应用要么是有进程,要么是没进程。
但是,在 macOS 上,应用已经不运行了,但是应用处于未激活状态:应用在没有打开任何窗口的情况下也继续运行。
如果激活应用,则检查应用是否 有窗口,没有窗口就在激活应用时会打开新的窗口。
监听 app 模块的 activate 事件来实现:如果没有任何浏览器窗口是打开的,则调用 createWindow() 方法。
// 当app准备好后,执⾏createWindow创建窗⼝
app.on('ready', () => {createWindow();// 当应⽤被激活时app.on('activate', () => {// 如果当前应⽤没有窗⼝,则创建⼀个新的窗⼝if (BrowserWindow.getAllWindows().length === 0) createWindow();});
});
完整的 main.js 如下:
const { app, BrowserWindow } = require('electron');function createWindow() {const win = new BrowserWindow({width: 500, // 窗口宽度height: 300, // 窗口高度autoHideMenuBar: true // 隐藏菜单栏});// 在窗口中加载一个远程页面win.loadFile('./pages/index.html');
}
app.on('ready', () => {// 当app准备好的时候,创建窗口createWindow();// 在Windows & Linux,应用的所有窗口关闭时,退出应用程序app.on('window-all-closed', () => {if (process.platform !== 'darwin') app.quit()})// 在macOS,当应⽤被激活时app.on('activate', () => {// 如果当前应⽤没有窗⼝,则创建⼀个新的窗⼝if (BrowserWindow.getAllWindows().length === 0) createWindow();});
});
相关文章:
Electron 安装以及搭建一个工程
安装Node.js 在使用Electron进行开发之前,需要安装 Node.js。 官方建议使用最新的LTS版本。 检查 Node.js 是否正确安装: # 查看node版本 node -v # 查看npm版本 npm -v注意 开发者需要在开发环境安装 Node.js 才能编写 Electron 项目,但是…...
羽毛类型检测系统源码分享
羽毛类型检测检测系统源码分享 [一条龙教学YOLOV8标注好的数据集一键训练_70全套改进创新点发刊_Web前端展示] 1.研究背景与意义 项目参考AAAI Association for the Advancement of Artificial Intelligence 项目来源AACV Association for the Advancement of Computer Vis…...
Xiaojie雷达之路---doa估计(dbf、capon、music算法)
Hello,大家好,我是Xiaojie,欢迎大家能够和Xiaojie来一起学习毫米波雷达知识,本篇文章主要是介绍一下雷达信号处理中的dbf、capon、music测角算法,一起来看看吧!!! 前言 本文从信号模型、dbf原理、capon原理、music原理以及代码仿真进行展开描述。 信号模型 阵列接收到…...
十大排序算法总结
完整文档见 排序算法总结——语雀文档 比较类排序:通过比较来决定元素间的相对次序,由于其时间复杂度不能突破O(nlogn),因此也称为非线性时间比较类排序。 非比较类排序:不通过比较来决定元素间的相对次序,它可以突破…...
大厂AI必备数据结构与算法——链表(三)详细文档
冲冲冲!开干 神马!神马!神马,一向让我们学习起来抓耳挠腮的数据结构课程竟然也有教程?还那么详细??真的假的? 那么好,胡广告诉你是假的,哈哈哈哈哈哈哈哈哈…...
一键自动化配置OpenHarmony编译环境
一、概述 本工程旨在对Ubuntu一键初始化配置环境,解决OpenHarmony的编译依赖问题,基于本脚本配置后配合一键下载OpenHarmony代码便能轻松掌控OpenHarmony的下载、编译。 当前建议使用稳定分支Itopen-2.0-Release,该分支是经过多次测试OK的&…...
不同领域的常见 OOD(Out-of-Distribution)数据集例子
以下是几个来自不同领域的常见 OOD(Out-of-Distribution)数据集例子,这些数据集常用于测试和研究模型在分布变化或分布外数据上的泛化能力: 1. 计算机视觉领域 CIFAR-10 vs. CIFAR-10-C / CIFAR-100-C: 描述:CIFAR-10…...
gRPC协议简介
gRPC 是谷歌开源的一套 RPC 协议框架。主要做两件事情:一是数据编码,二是请求映射。 数据编码 数据编码顾名思义就是在将请求的内存对像转化成可以传输的字节流发给服务端,并将收到的字节流再转化成内存对像。方法有很多,常见的…...
[dp+dfs]砝码称重
题目描述 现有 n n n 个砝码,重量分别为 a 1 , a 2 , … , a n a_1, a_2, \ldots,a_n a1,a2,…,an ,在去掉 m m m 个砝码后,问最多能称量出多少不同的重量(不包括 0 0 0 )。 输入格式 第一行为有两个整数…...
MYSQL-查看表中字段属性语法(三)
查看表中字段全部信息 show full columns from database_name.table_name; show full columns from table_name;示例 mysql> show full columns from world.city; ----------------------------------------------------------------------------------------------------…...
第三讲 part 3:前端处理LINK3D - 代码解析 - 从main出发看总体流程(ROS1改为ROS2)
目录 1. ROS1 ->ROS21.1 包含头文件1.2 全局变量定义1.3 结构体定义1.4 点云容器定义1.5 图像处理相关变量1.6 ROS2发布者和订阅者定义1.7 全局变量,被不断更新1.8 点云处理相关变量1.9 图像描述符1.10 主函数1.10.1. 初始化ROS21.10.2. 创建节点1.10.3. 声明参数1.10.4. 设…...
移情别恋c++ ദ്ദി˶ー̀֊ー́ ) ——15.红黑树
1.红黑树的概念 红黑树,是一种二叉搜索树,但在每个结点上增加一个存储位表示结点的颜色,可以是Red或 Black。 通过对任何一条从根到叶子的路径上各个结点着色方式的限制,红黑树确保没有一条路 径会比其他路径长出俩倍,…...
【C++】Eclipse技巧汇总
Eclipse C/C调试无法输入 在debug C/C程序时,Eclipse自带的窗口,无法读取cin等输入 解决办法: 参考:https://blog.csdn.net/sagjhdj/article/details/123271383 思路是调用外部console: 依次点击Debug>Debug Conf…...
Golang | Leetcode Golang题解之第430题扁平化多级双向链表
题目: 题解: func dfs(node *Node) (last *Node) {cur : nodefor cur ! nil {next : cur.Next// 如果有子节点,那么首先处理子节点if cur.Child ! nil {childLast : dfs(cur.Child)next cur.Next// 将 node 与 child 相连cur.Next cur.Chi…...
Java实现找色和找图功能
某天,张三接到一个任务需求,将一个Excel表格里面的员工信息,录入到员工系统里面,由于数据量非常大,操作起来巨慢。经过一段时间的操作和观察,他发现这种操作,非常有规律,基本就是一些…...
linux脚本工具
目录 shell工具查看Nvidia GPU状态查看某个监听端口是否存在设置局部代理查找关键字相关进程根据日常所需,持续更新 shell工具 减少重复性工作,简化工作流程,提高工作效率 将所编写的shell脚本赋予可执行权限 chmod x <脚本文件> 在…...
MySQL之基础篇
数据库操作 1.查看当前的数据库版本 select version(); 2.显示所有数据库 show databases; 3.创建数据库 create [if not exists] database 数据库名 character set 字符编码集 collate 排序规则; 我们这里提前说一下 被方括号括起来的代码 表示可写可不写 示例…...
13年408计算机考研-计算机网络
第一题: 解析:OSI体系结构 OSI参考模型,由下至上依次是:物理层-数据链路层-网络层-运输层-会话层-表示层-应用层。 A.对话管理显然属于会话层, B.数据格式转换,是表示层要解决的问题,很显然答案…...
camera2 + MediaRecorder 实现的分段循环录像功能
硬件设备Android系统 8.1; 硬件设备上开发过程中的问题记录: 问题1. 长时间录像后发现保存的录像文件始终只有4G。 原因及解决:Android 11之前的系统有对保存的文件大小有限制,所以只能修改成分段保存,即录像文件3.…...
LeetCode 每日一题 2024/9/23-2024/9/29
记录了初步解题思路 以及本地实现代码;并不一定为最优 也希望大家能一起探讨 一起进步 目录 9/23 2414. 最长的字母序连续子字符串的长度9/24 2207. 字符串中最多数目的子序列9/25 2306. 公司命名9/26 2535. 数组元素和与数字和的绝对差9/27 2516. 每种字符至少取 K…...
进程地址空间(比特课总结)
一、进程地址空间 1. 环境变量 1 )⽤户级环境变量与系统级环境变量 全局属性:环境变量具有全局属性,会被⼦进程继承。例如当bash启动⼦进程时,环 境变量会⾃动传递给⼦进程。 本地变量限制:本地变量只在当前进程(ba…...
安宝特方案丨XRSOP人员作业标准化管理平台:AR智慧点检验收套件
在选煤厂、化工厂、钢铁厂等过程生产型企业,其生产设备的运行效率和非计划停机对工业制造效益有较大影响。 随着企业自动化和智能化建设的推进,需提前预防假检、错检、漏检,推动智慧生产运维系统数据的流动和现场赋能应用。同时,…...
线程同步:确保多线程程序的安全与高效!
全文目录: 开篇语前序前言第一部分:线程同步的概念与问题1.1 线程同步的概念1.2 线程同步的问题1.3 线程同步的解决方案 第二部分:synchronized关键字的使用2.1 使用 synchronized修饰方法2.2 使用 synchronized修饰代码块 第三部分ÿ…...
Go 语言接口详解
Go 语言接口详解 核心概念 接口定义 在 Go 语言中,接口是一种抽象类型,它定义了一组方法的集合: // 定义接口 type Shape interface {Area() float64Perimeter() float64 } 接口实现 Go 接口的实现是隐式的: // 矩形结构体…...
【HTTP三个基础问题】
面试官您好!HTTP是超文本传输协议,是互联网上客户端和服务器之间传输超文本数据(比如文字、图片、音频、视频等)的核心协议,当前互联网应用最广泛的版本是HTTP1.1,它基于经典的C/S模型,也就是客…...
Java多线程实现之Thread类深度解析
Java多线程实现之Thread类深度解析 一、多线程基础概念1.1 什么是线程1.2 多线程的优势1.3 Java多线程模型 二、Thread类的基本结构与构造函数2.1 Thread类的继承关系2.2 构造函数 三、创建和启动线程3.1 继承Thread类创建线程3.2 实现Runnable接口创建线程 四、Thread类的核心…...
C++使用 new 来创建动态数组
问题: 不能使用变量定义数组大小 原因: 这是因为数组在内存中是连续存储的,编译器需要在编译阶段就确定数组的大小,以便正确地分配内存空间。如果允许使用变量来定义数组的大小,那么编译器就无法在编译时确定数组的大…...
免费数学几何作图web平台
光锐软件免费数学工具,maths,数学制图,数学作图,几何作图,几何,AR开发,AR教育,增强现实,软件公司,XR,MR,VR,虚拟仿真,虚拟现实,混合现实,教育科技产品,职业模拟培训,高保真VR场景,结构互动课件,元宇宙http://xaglare.c…...
适应性Java用于现代 API:REST、GraphQL 和事件驱动
在快速发展的软件开发领域,REST、GraphQL 和事件驱动架构等新的 API 标准对于构建可扩展、高效的系统至关重要。Java 在现代 API 方面以其在企业应用中的稳定性而闻名,不断适应这些现代范式的需求。随着不断发展的生态系统,Java 在现代 API 方…...
uniapp 实现腾讯云IM群文件上传下载功能
UniApp 集成腾讯云IM实现群文件上传下载功能全攻略 一、功能背景与技术选型 在团队协作场景中,群文件共享是核心需求之一。本文将介绍如何基于腾讯云IMCOS,在uniapp中实现: 群内文件上传/下载文件元数据管理下载进度追踪跨平台文件预览 二…...
