# electron-project **Repository Path**: yan_guoping/electron ## Basic Information - **Project Name**: electron-project - **Description**: No description available - **Primary Language**: Unknown - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2024-03-25 - **Last Updated**: 2024-04-03 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README Electron-project 项目总结: 初始化vite项目 ```sh npm create vite@latest cd electron-project && yarn && yarn run dev yarn add electron -D 这里出现了安装过慢的情况,我直接使用cnpm来安装了 cnpm i electron -D 这个electron的版本是29.1.5 touch main.ts ``` 啊哈,居然报这个错:找不到名称“require”。是否需要安装 Node.js 的类型定义? 请尝试运行 `npm i --save-dev @types/node` ```js cnpm i -D @types/node ``` 安装了@types/node,不行啊,它还是建议我们使用import ES module的写法,算了吧,那我放弃commonJs的写法了 。。。 初始化主进程的代码 执行electron .命令的时候,遇到了两个问题,main.ts是typescript和ES module的语法问题,electron不支持 这个问题留着之后解决吧,那我还是使用commonJs的写法。。。 然后我把node_modules全删除了,使用cnpm i全部重新安装了,目前,main.ts改成了main.js, 此外在package.json新增加了electron的主进程的入口文件 package.json ```json "main": "main.js", ``` main.js ```js const { app, BrowserWindow } = require("electron"); // import { app, BrowserWindow } from "electron"; const path = require("path"); const createWindow = () => { const mainWindow = new BrowserWindow({ width: 1000, height: 800, webPreferences: { nodeIntegration: true, //集成node //预加载 preload: path.resolve(__dirname, "./preload/index.ts"), //必须是绝对路径,不能是相对路径 }, }); mainWindow.loadURL("http://localhost:5173/"); //打开开发者工具 mainWindow.webContents.openDevTools(); // 暂时关闭安全警告 // process.env["ELECTRON_DISABLE_SECURITY_WARNINGS"] = "true";//没有生效,算了,还是直接使用配置CSP }; app.whenReady().then(() => { createWindow(); }); ``` 安装nodemon ```sh cnpm i nodemon -D ``` package.json ```json //增加了一行脚本命令 --exec(执行)electron .命令, //--watch ./ --ext .js,.html,.vue,.ts,.css 监听./目录下的以.js,.html,.vue,.ts,.css结尾的所有文件 "scripts": { "dev": "vite", "build": "vue-tsc && vite build", "preview": "vite preview", "start": "nodemon --exec electron . --watch ./ --ext .js,.html,.vue,.ts,.css" }, ``` ```sh cnpm i nodemon -D 查看nodemon 的一些命令 npx nodemon --help ``` 关闭electron的警告 /src/index.html ```index.html //这里就img-src设置为*,允许使用外部的图片 // 暂时关闭安全警告 process.env['ELECTRON_DISABLE_SECURITY_WARNINGS'] = 'true' ``` 安装electron-win-state ```sh cnpm i electron-win-state ``` main.js ```js const WinState = require("electron-win-state").default; const winState = new WinState({ defaultWidth: 1000, defaultHeight: 800, }); const createWindow = () => { const mainWindow = new BrowserWindow({ ...winState.winOptions, // width: 1000, // height: 800, webPreferences: { nodeIntegration: true, //集成node //预加载 preload: path.resolve(__dirname, "./preload/index.ts"), //必须是绝对路径,不能是相对路径 }, }); ... //通过winState来记录管理窗口的大小和位置 winState.manage(mainWindow); } ``` Preload/index.ts 恼火,这里还是不能使用ES module的写法,但是ts可以使用 ```ts // import path from "path"; const path = require("path"); console.log(123, path); ``` 以上,基本完成了项目的初始化。。。 优雅的打开窗口,等页面加载完成再打开窗口 ```js //main.js const mainWindow = new BrowserWindow({ ...winState.winOptions, // width: 1000, // height: 800, webPreferences: { nodeIntegration: true, //集成node //预加载 preload: path.resolve(__dirname, "./preload/index.ts"), //必须是绝对路径,不能是相对路径 }, show:false }); ... mainWindow.on('ready-to-show',()=>{ mainWindow.show() }) ``` 安装stylus ```js yarn add stylus -S yarn add normalize.css -S ``` 引入normalize.css 去除一下元素默认的margin和padding ## 分析简富 package.json ```json ``` ```js //1、scripts分析 npm run start = npm run start:sit (简写) npm run start:sit 的实际命令: cross-env SERVER=sit electron-forge start //cross-env cross-env:运行跨平台设置和使用环境变量的脚本,说白了就是为了设置环境变量,解决兼容性的问题 安装:npm install --save-dev cross-env 打印process.env.SERVER === 'sit' //true //electron-forge //Create a new Electron app with webpack and TypeScript 创建模板新项目 npm init electron-app@latest my-new-app -- --template=webpack-typescript "scripts": { "start": "electron-forge start", "package": "electron-forge package", //打包 "make": "electron-forge make",//构建分发包 "publish": "electron-forge publish", "lint": "eslint --ext .ts,.tsx ." }, 简单对比一下,没有什么区别:无非就是在启动、打包、创建分发包的时候增加了一些环境变量。 ``` 关于electron-forge 可以结合这篇文章(https://www.kancloud.cn/a173512/node/2160998 )和官方文档(https://www.electronforge.io/)来看, 还有这篇博客(https://blog.csdn.net/qq_43220213/article/details/136467653?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522171194475416800182171310%2522%252C%2522scm%2522%253A%252220140713.130102334.pc%255Fblog.%2522%257D&request_id=171194475416800182171310&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~blog~first_rank_ecpm_v1~times_rank-1-136467653-null-null.nonecase&utm_term=electron-forge%E5%92%8Celectron%20builder&spm=1018.2226.3001.4450) ```js //electron-forge //Create a new Electron app with webpack and TypeScript 创建模板新项目 npm init electron-app@latest my-new-app -- --template=webpack-typescript //导入到已有项目 cd my-app npm install --save-dev @electron-forge/cli npm exec --package=@electron-forge/cli -c "electron-forge import" 这些包都是 Electron Forge 的组成部分,它们提供了不同的功能和插件,用于构建和打包 Electron 应用。下面是每个包的作用: @electron-forge/cli - Electron Forge 的命令行接口 (CLI),它提供了一组命令,如 start, package, make, publish 等,用于启动、打包、创建分发包和发布你的 Electron 应用。 @electron-forge/maker-deb - 一个 maker,用于创建 Debian (.deb) 格式的安装包,这些包通常用于 Debian 和 Ubuntu 等 Linux 发行版。 @electron-forge/maker-rpm - 一个 maker,用于创建 Red Hat Package Manager (.rpm) 格式的安装包,这些包通常用于 Red Hat、Fedora、CentOS 等 Linux 发行版。 @electron-forge/maker-squirrel - 一个 maker,用于创建 Squirrel.Windows (.msi, .exe) 格式的安装包,这些包用于 Windows 系统。 @electron-forge/maker-zip - 一个 maker,用于创建 zip 压缩包,通常用于分发没有特定安装程序的简单应用版本。 @electron-forge/plugin-auto-unpack-natives - 一个插件,用于自动解包原生 Node 模块,这样它们就可以在打包的应用中被正确加载。 @electron-forge/plugin-fuses - 一个插件,用于在打包过程中设置一些“熔丝”(fuses),这些熔丝可以控制应用的行为,比如禁用调试功能、防止应用被篡改等。 ———————————————— 版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。 原文链接:https://blog.csdn.net/qq_43220213/article/details/136467653 ``` 下面这些是简富的依赖包: 这个是通过electron的template=webpack-typescript生成的新项目的依赖包: 对比了一下,自动生成的少了一个dev依赖包:@electron-forge/maker-dmg ```js @electron-forge/maker-dmg 看起来像是为mac系统使用的,那就自己手动安装一下吧 yarn add -D @electron-forge/maker-dmg ``` 还有那些其他的依赖,等使用到的时候再详细讲。 对目录结构重新划分: forge.config.ts 是项目的最重要的配置入口,以前的main.js现在是./src/index.ts ```js //forge.config.ts import type { ForgeConfig } from '@electron-forge/shared-types'; import { MakerSquirrel } from '@electron-forge/maker-squirrel'; import { MakerZIP } from '@electron-forge/maker-zip'; import { MakerDeb } from '@electron-forge/maker-deb'; import { MakerRpm } from '@electron-forge/maker-rpm'; import { AutoUnpackNativesPlugin } from '@electron-forge/plugin-auto-unpack-natives'; import { WebpackPlugin } from '@electron-forge/plugin-webpack'; import { FusesPlugin } from '@electron-forge/plugin-fuses'; import { FuseV1Options, FuseVersion } from '@electron/fuses'; import { mainConfig } from './webpack.main.config'; import { rendererConfig } from './webpack.renderer.config'; const config: ForgeConfig = { packagerConfig: { asar: true, }, rebuildConfig: {}, makers: [new MakerSquirrel({}), new MakerZIP({}, ['darwin']), new MakerRpm({}), new MakerDeb({})], plugins: [ new AutoUnpackNativesPlugin({}), new WebpackPlugin({ mainConfig, renderer: { config: rendererConfig, entryPoints: [ { html: './src/index.html', js: './src/renderer.ts', name: 'main_window', preload: { js: './src/preload.ts', }, }, ], }, }), // Fuses are used to enable/disable various Electron functionality // at package time, before code signing the application new FusesPlugin({ version: FuseVersion.V1, [FuseV1Options.RunAsNode]: false, [FuseV1Options.EnableCookieEncryption]: true, [FuseV1Options.EnableNodeOptionsEnvironmentVariable]: false, [FuseV1Options.EnableNodeCliInspectArguments]: false, [FuseV1Options.EnableEmbeddedAsarIntegrityValidation]: true, [FuseV1Options.OnlyLoadAppFromAsar]: true, }), ], }; export default config; //这上面最重要的 plugins: [ new AutoUnpackNativesPlugin({}), new WebpackPlugin({ mainConfig, //webpack.main.config renderer: { config: rendererConfig,//webpack.renderer.config entryPoints: [ { html: './src/index.html', js: './src/renderer.ts', name: 'main_window', preload: { js: './src/preload.ts', }, }, ], }, }), ... ] ``` ```js 1、把所有的webpack的配置放到stable/webpack的目录下 2、修改forge.config.js对webpack的配置的引入 3、保留以前electron的builder风格,将./src/index.ts改成./src/main.ts。在webpack.main.config.ts里面的引入修改 //webpack.main.config.ts import type { Configuration } from "webpack"; import { rules } from "./webpack.rules"; import { plugins } from "./webpack.plugins"; export const mainConfig: Configuration = { /** * This is the main entry point for your application, it's the first file * that runs in the main process. */ entry: "./src/main.ts", //note:保留以前electron的builder风格 // Put your normal webpack config below here module: { rules, }, plugins, resolve: { extensions: [".js", ".ts", ".jsx", ".tsx", ".css", ".json"], }, }; 4、新建stable/renderer文件夹,这里主要是./src/main.ts要加载的url 5、将src/index.html和src/renderer.ts移入到stable/renderer文件夹里,同时要修改forge.config.ts里面的引入 plugins: [ new AutoUnpackNativesPlugin({}), new WebpackPlugin({ mainConfig, renderer: { config: rendererConfig, entryPoints: [ { html: "./stable/renderer/index.html", js: "./stable/renderer/renderer.ts", name: "main_window", preload: { js: "./src/preload.ts", }, }, ], }, }), 6、修改tsconfig.ts "include": ["src/**/*", "stable/webpack", "stable/renderer/renderer.ts"] ``` 好了,基本上目录结构的重新划分就到这里了。。 下面逐一对下面的配置修改: ```txt webpack.main.config.ts webpack.plugins.ts webpack.renderer.config.ts webpack.rules.ts forge.config.ts ``` ```js //webpack.config.ts //pre: import type { Configuration } from "webpack"; import { rules } from "./webpack.rules"; import { plugins } from "./webpack.plugins"; export const mainConfig: Configuration = { /** * This is the main entry point for your application, it's the first file * that runs in the main process. */ entry: "./src/main.ts", // Put your normal webpack config below here module: { rules, }, plugins, resolve: { extensions: [".js", ".ts", ".jsx", ".tsx", ".css", ".json"], }, }; //next: import path from "path"; import type { Configuration } from "webpack"; import { DefinePlugin } from "webpack"; import { rules } from "./webpack.rules"; import { plugins } from "./webpack.plugins"; const resolve = (dir: string) => path.resolve(__dirname, dir); export const mainConfig: Configuration = { /** * This is the main entry point for your application, it's the first file * that runs in the main process. */ entry: "./src/main.ts", // Put your normal webpack config below here module: { rules, }, plugins: [ ...plugins, //note:增配一些环境变量 new DefinePlugin({ "process.env.NODE_ENV": JSON.stringify( process.env.NODE_ENV || "development" ), "process.env.SERVER": JSON.stringify(process.env.SERVER), }), ], resolve: { extensions: [".js", ".ts", ".jsx", ".tsx", ".css", ".json"], //note:增加了别名 疑问:tsconfig.json增加过别名了,为什么这里还需要配置? alias: { "@utils": resolve("../../src/utils"), }, }, }; ``` ```js //webpack.plugins.ts //pre: import type IForkTsCheckerWebpackPlugin from 'fork-ts-checker-webpack-plugin'; // eslint-disable-next-line @typescript-eslint/no-var-requires const ForkTsCheckerWebpackPlugin: typeof IForkTsCheckerWebpackPlugin = require('fork-ts-checker-webpack-plugin'); export const plugins = [ new ForkTsCheckerWebpackPlugin({ logger: 'webpack-infrastructure', }), ]; //next: 有点奇怪,那个webpack.config.ts已经配置了DefinePlugin,又重新配置了一遍。。 import type IForkTsCheckerWebpackPlugin from "fork-ts-checker-webpack-plugin"; import { DefinePlugin } from "webpack"; // eslint-disable-next-line @typescript-eslint/no-var-requires const ForkTsCheckerWebpackPlugin: typeof IForkTsCheckerWebpackPlugin = require("fork-ts-checker-webpack-plugin"); export const plugins = [ new ForkTsCheckerWebpackPlugin({ logger: "webpack-infrastructure", }), //note:增配一些环境变量 new DefinePlugin({ "process.env.NODE_ENV": JSON.stringify( process.env.NODE_ENV || "development" ), "process.env.SERVER": JSON.stringify(process.env.SERVER), }), ]; ``` ```js //webpack.renderer.config.ts //pre: import type { Configuration } from 'webpack'; import { rules } from './webpack.rules'; import { plugins } from './webpack.plugins'; rules.push({ test: /\.css$/, use: [{ loader: 'style-loader' }, { loader: 'css-loader' }], }); export const rendererConfig: Configuration = { module: { rules, }, plugins, resolve: { extensions: ['.js', '.ts', '.jsx', '.tsx', '.css'], }, }; //next: import path from "path"; import type { Configuration } from "webpack"; import { rules } from "./webpack.rules"; import { plugins } from "./webpack.plugins"; rules.push({ test: /\.css$/, use: [{ loader: "style-loader" }, { loader: "css-loader" }], }); const resolve = (dir: string) => path.resolve(__dirname, dir); export const rendererConfig: Configuration = { module: { rules, }, plugins, resolve: { extensions: [".js", ".ts", ".jsx", ".tsx", ".css"], //note:增加了别名 疑问:tsconfig.json增加过别名了,为什么这里还需要配置? alias: { "@utils": resolve("../../src/utils"), }, }, //note:如果渲染进程用到electron,编译时先忽略 externals: { electron: 'require("electron")', }, }; ``` ```js //webpack.rules.ts 没做修改,无需改动 import type { ModuleOptions } from 'webpack'; export const rules: Required['rules'] = [ // Add support for native node modules { // We're specifying native_modules in the test because the asset relocator loader generates a // "fake" .node file which is really a cjs file. test: /native_modules[/\\].+\.node$/, use: 'node-loader', }, { test: /[/\\]node_modules[/\\].+\.(m?js|node)$/, parser: { amd: false }, use: { loader: '@vercel/webpack-asset-relocator-loader', options: { outputAssetBase: 'native_modules', }, }, }, { test: /\.tsx?$/, exclude: /(node_modules|\.webpack)/, use: { loader: 'ts-loader', options: { transpileOnly: true, }, }, }, ]; ``` ```js //forge.config.ts //pre: import type { ForgeConfig } from "@electron-forge/shared-types"; import { MakerSquirrel } from "@electron-forge/maker-squirrel"; import { MakerZIP } from "@electron-forge/maker-zip"; import { MakerDeb } from "@electron-forge/maker-deb"; import { MakerRpm } from "@electron-forge/maker-rpm"; import { AutoUnpackNativesPlugin } from "@electron-forge/plugin-auto-unpack-natives"; import { WebpackPlugin } from "@electron-forge/plugin-webpack"; import { FusesPlugin } from "@electron-forge/plugin-fuses"; import { FuseV1Options, FuseVersion } from "@electron/fuses"; import { mainConfig } from "./stable/webpack/webpack.main.config"; import { rendererConfig } from "./stable/webpack/webpack.renderer.config"; const config: ForgeConfig = { packagerConfig: { asar: true, }, rebuildConfig: {}, makers: [ new MakerSquirrel({}), new MakerZIP({}, ["darwin"]), new MakerRpm({}), new MakerDeb({}), ], plugins: [ new AutoUnpackNativesPlugin({}), new WebpackPlugin({ mainConfig, renderer: { config: rendererConfig, entryPoints: [ { html: "./stable/renderer/index.html", js: "./stable/renderer/renderer.ts", name: "main_window", preload: { js: "./src/preload.ts", }, }, ], }, }), // Fuses are used to enable/disable various Electron functionality // at package time, before code signing the application new FusesPlugin({ version: FuseVersion.V1, [FuseV1Options.RunAsNode]: false, [FuseV1Options.EnableCookieEncryption]: true, [FuseV1Options.EnableNodeOptionsEnvironmentVariable]: false, [FuseV1Options.EnableNodeCliInspectArguments]: false, [FuseV1Options.EnableEmbeddedAsarIntegrityValidation]: true, [FuseV1Options.OnlyLoadAppFromAsar]: true, }), ], }; export default config; //next: //关键点: //note: packagerConfig: { icon: path.join(__dirname, "./src/icon/logo"), // appBundleId: "xxx", // osxSign: {}, // osxNotarize: { // tool: "notraytool", // appleId: "xxx", // appleIdPassword: "xxx", // teamId: "xxx", // }, extraResource: [ path.join(__dirname, "./src/icon/logo.ico"), path.join(__dirname, "./src/icon/logo.png"), ], executableName: "GuoPing", name: "国萍·GuoPing", }, //note: //不同平台的打包选项 makers: [ new MakerSquirrel({ setupExe: "yan.exe", setupIcon: "./src/icon/logo.ico", loadingGif: "./src/icon/setup.gif", skipUpdateIcon: true, }), //加上macUpdateManifestBaseUrl,才会生成升级mac的releases.json new MakerZIP({ macUpdateManifestBaseUrl: "https://xxx" }, ["darwin"]), new MakerRpm({}), new MakerDMG({ icon: "./src/icon/logon.icns", name: "guoping" }, [ "darwin", ]), new MakerDeb({}), ], ``` package.json中的script修改 ```js yarn add -D cross-env //pre: "scripts": { "start": "electron-forge start", "package": "electron-forge package", "make": "electron-forge make --arch-universal", "publish": "electron-forge publish", "lint": "eslint --ext .ts,.tsx ." }, //next: "scripts": { "start": "npm run start:sit", "start:sit": "cross-env SERVER=sit electron-forge start", "start:uat": "cross-env SERVER=uat electron-forge start", "package": "npm run package:sit", "package:sit": "cross-env NODE_ENV=development SERVER=sit electron-forge package", "package:uat": "cross-env NODE_ENV=development SERVER=uat electron-forge package", "package:prod": "cross-env NODE_ENV=production SERVER=prod electron-forge package", "make": "npm run make:sit:win", "make:sit:win": "cross-env NODE_ENV=production SERVER=sit electron-forge make", "make:sit:mac": "cross-env NODE_ENV=production SERVER=sit electron-forge make --arch-universal", "make:uat:win": "cross-env NODE_ENV=production SERVER=uat electron-forge make", "make:uat:mac": "cross-env NODE_ENV=production SERVER=uat electron-forge make --arch-universal", "make:prod:win": "cross-env NODE_ENV=production SERVER=prod electron-forge make", "make:prod:mac": "cross-env NODE_ENV=production SERVER=prod electron-forge make --arch-universal", "publish": "electron-forge publish", "lint": "eslint --ext .ts,.tsx ." }, --arch-universal 不知道这个是啥。。。 ``` renderer/renderer.ts 通过当前的环境变量来配置修改window.location.href来展示显示页面: ```js //pre: import './index.css'; console.log('👋 This message is being logged by "renderer.js", included via webpack'); //next: const getCurrentHref = () => { console.log(process.env.NODE_ENV, "process.env.NODE_ENV"); console.log(process.env.SERVER, "process.env.SERVER"); if (process.env.NODE_ENV === "development") { return "http://localhost:8000/#/"; } else if (process.env.SERVER === "sit") { return "http://xxx-sit:8000/xxx/index.html"; } else if (process.env.SERVER === "uat") { return "http://xxx-uat:8000/xxx/index.html"; } else if (process.env.NODE_ENV === "production") { return "https://xxx:14443/xxx/index.html"; } else { return "http://xxx-sit:8000/xxx/index.html"; } }; setTimeout(() => { window.location.href = getCurrentHref(); }, 0); ``` 下面开始啃比较难啃的骨头,electron的主入口src/main.ts,以及预加载src/preload.ts main.ts ```js //src/main.ts //pre: import { app, BrowserWindow } from 'electron'; // This allows TypeScript to pick up the magic constants that's auto-generated by Forge's Webpack // plugin that tells the Electron app where to look for the Webpack-bundled app code (depending on // whether you're running in development or production). declare const MAIN_WINDOW_WEBPACK_ENTRY: string; declare const MAIN_WINDOW_PRELOAD_WEBPACK_ENTRY: string; // Handle creating/removing shortcuts on Windows when installing/uninstalling. if (require('electron-squirrel-startup')) { app.quit(); } const createWindow = (): void => { // Create the browser window. const mainWindow = new BrowserWindow({ height: 600, width: 800, webPreferences: { preload: MAIN_WINDOW_PRELOAD_WEBPACK_ENTRY, }, }); // and load the index.html of the app. mainWindow.loadURL(MAIN_WINDOW_WEBPACK_ENTRY); // Open the DevTools. mainWindow.webContents.openDevTools(); }; // This method will be called when Electron has finished // initialization and is ready to create browser windows. // Some APIs can only be used after this event occurs. app.on('ready', createWindow); // Quit when all windows are closed, except on macOS. There, it's common // for applications and their menu bar to stay active until the user quits // explicitly with Cmd + Q. app.on('window-all-closed', () => { if (process.platform !== 'darwin') { app.quit(); } }); app.on('activate', () => { // On OS X it's common to re-create a window in the app when the // dock icon is clicked and there are no other windows open. if (BrowserWindow.getAllWindows().length === 0) { createWindow(); } }); // In this file you can include the rest of your app's specific main process // code. You can also put them in separate files and import them here. ``` 遇到别名的问题,到时候要看一下。 别名的问题解决了,可以看csdn收藏的博客 ```json { "env": { "browser": true, "es6": true, "node": true }, "extends": [ "eslint:recommended", "plugin:@typescript-eslint/eslint-recommended", "plugin:@typescript-eslint/recommended", "plugin:import/recommended", "plugin:import/electron", "plugin:import/typescript" ], "parser": "@typescript-eslint/parser", //note:直接不报警 "rules": { "import/no-unresolved": [2, { "ignore": ["@common", "@utils"] }] } } ``` 打印乱码的问题: chcp 65001 一个简单的主进程和渲染进程通信 ```js //main.ts ipcMain.handle("desktop-capturer", (event) => { return desktopCapturer .getSources({ types: ["window", "screen"], thumbnailSize: { width: 1920, height: 1080, }, }) .then(async (sources) => { return sources; }); }); //preload.ts const getSources = async (msg: any) => { console.log(msg, "msg"); const res = await ipcRenderer.invoke("desktop-capturer"); console.log(res, "res"); return res; }; contextBridge.exposeInMainWorld("myAPI", { desktop: true, getSources, }); //renderer.ts console.log((window as any).myAPI.desktop, "window.myAPI.desktop "); (window as any).myAPI.getSources(); ``` 主进程和渲染进程通信的核心: ```js 在Electron中的通信中,我们经常会用到ipcRender.invoke和ipvRender.send 接下来简要说明下这两个方法的区别 ipcMain.on(channel, listener) 这是 Electron 的主进程(main process)监听来自渲染进程(renderer process)的消息的方式。 当渲染进程通过 ipcRenderer.send 或 ipcRenderer.sendSync 发送消息时,主进程可以使用 ipcMain.on 来监听并处理这些消息。 listener 是一个回调函数,当收到匹配 channel 的消息时,这个函数会被调用。 这种方式是异步的,主进程不会等待渲染进程的响应。 ipcMain.handle(channel, listener) ipcMain.handle 是 Electron 5.0.0 之后引入的新特性。 它允许主进程注册一个处理函数来响应来自渲染进程的同步消息请求。 当渲染进程使用 ipcRenderer.invoke 发送一个同步消息请求时,主进程可以使用 ipcMain.handle 来处理这个请求,并返回一个响应。 listener 是一个处理函数,当收到匹配 channel 的同步消息请求时,这个函数会被调用。 与 ipcMain.on 不同,ipcMain.handle 是同步的,主进程会等待渲染进程的响应。 总结: ipcMain.on 主要用于处理渲染进程发送的异步消息。 ipcMain.handle 主要用于处理渲染进程发送的同步消息请求,并返回响应。 ``` crypto-js加密和解密 https://blog.csdn.net/qq_34707272/article/details/121857485?ops_request_misc=%257B%2522request%255Fid%2522%253A%2522171210847616800186579074%2522%252C%2522scm%2522%253A%252220140713.130102334..%2522%257D&request_id=171210847616800186579074&biz_id=0&utm_medium=distribute.pc_search_result.none-task-blog-2~all~top_positive~default-1-121857485-null-null.142^v100^pc_search_result_base5&utm_term=crypto-js&spm=1018.2226.3001.4187 ```js npm install crypto-js ``` 日志打印 ```js yarn add electron-log ``` axios 网络请求 ```js yarn add axios ``` 最新版本的electron遇到两个已经被废弃的 1、 ipcRenderer.sendTo(id, BROWSERWINDOW_SEND_MESSAGE, msg); 2、const srcId = event.senderId 已弃用了 //todo yan 先版本降级吧,之后看看最新的api 29.1.2=>26.6.6 别名配置很多遍的原因找到了,tsconfig.json是针对开发的时候用的,webpack里面针对是webpack编译后要使用的