实现效果

image-20240404205840117

实现无边框窗口

在创建窗口时,参数中加上:

titleBarStyle: 'hidden',

顺便如果要禁止对窗口大小进行更改,再加上:

resizable:false,
maximizable:false,

禁用滚动条

在全局css中,body处加上:

overflow: hidden;

拖拽窗口

  • 在 CSS 中指定 -webkit-app-region: drag 来告诉 Electron 哪些区域是可拖拽的
  • 在可拖拽区域内部使用 -webkit-app-region: no-drag 则可以将其中部分区域排除

自定义最小化、关闭

主要是靠 Electron 的 ipc 通信,但是我跟网上的教程很多都不行(理论上他们的方法都是没问题的),最后发现竟然是因为……

此处需要使用preload,因为Electron在(忘了哪个版本)不给直接调用ipcRenderer了(网上很多教程都过时了,我在这上面也卡了很久((

前期准备

新建一个preload.ts,放哪看个人:

const { contextBridge,ipcRenderer } = require('electron');

contextBridge.exposeInMainWorld('myApi', {
// 这里注意避免将ipcRenderer等致命api直接挂载在window上,可能会导致安全问题
sendMsg: (msg:string) => ipcRenderer.send(msg)
})

然后在创建窗口处的webPreferences加上(路径按个人实际改):

// 预加载脚本
preload: path.join(__dirname, 'preload.js'),

同时将contextIsolation改为true

然后在创建完窗口代码后面加上(其中win就是创建的窗口)(别忘了import):

// 关闭窗口
ipcMain.on('close', () => {
win.close();
});

// 最小化窗口
ipcMain.on('minimize', () => {
win.minimize();
});

引号之间的字可以根据个人习惯改~

使用

在组件中负责最小化/关闭的函数中,直接使用:

window.myApi.sendMsg('minimize');

个人踩坑

好了,网上大部分教程到这里就结束了(至少我看了那么那么多都是这样的),但是我个人怎么样都无法成功通信,搜了一堆又一堆,也没有找到解决方法,甚至看视频教程,别人用起来也是丝般顺滑,到底是为什么呢?小编也很好奇

看看vue页面的控制台有没有什么信息。点击按钮,可以看到这个报错:

QQ截图20240404120810

说是sendMsg没有定义,但是window.myApi.sendMsg('minimize');,说明myApi应该能读到(其实并不能)

再看Electron的dev tool,发现他的报错竟然不太一样:

QQ截图20240404120751

看一眼,这下破案了,他读的是dist目录下的`preload.js``

解决

这不就简单了,直接在vite.electron.dev.ts还有vite.electron.build.ts里面的buildBackground()加上:

require('esbuild').buildSync({
entryPoints:['src/preload.ts'],
bundle:true,
outfile:'dist/preload.js',
platform:'node',
target:'node12',
external:['electron']
})

这下就没问题了!

就这么一个小小的功能,真的卡了我很久,感觉把这路上能踩的坑都踩了一遍(((

下一篇精彩继续(没错又卡了很久((

参考链接

自定义窗口 | Electron (electronjs.org)

Electron常见问题 14 - 窗口禁用滚动条_electron 滚动条-CSDN博客

Electron无边框窗口(最小化、最大化、关闭、拖动)以及动态改变窗口大小_electron ,动态配置应用参数-CSDN博客

【electron】无边框窗口_哔哩哔哩_bilibili