Electron——窗口
文章目录
- 一、渲染进程与主进程通信
- 二、主进程获取渲染进程发送的信息
- 三、创建窗口的一些参数选项
- 四、窗口拖拽
- 1、使用-webkit-app-region: drag
- 2、与主线程通信修改窗口大小
- 五、自定义实现关闭、最大化、最小化功能
一、渲染进程与主进程通信
// 渲染进程向主进程发送信息
window.electron.ipcRenderer.invoke('dialog:openFileWindow', {name: 'list'
})
二、主进程获取渲染进程发送的信息
import { app, shell, BrowserWindow, ipcMain } from 'electron'function createWindow(): void {// Create the browser window.const mainWindow = new BrowserWindow({width: 900,height: 670,show: false,autoHideMenuBar: true,...(process.platform === 'linux' ? { icon } : {}),webPreferences: {preload: join(__dirname, '../preload/index.js'),sandbox: false}})// 使用ipcMain处理渲染进程发送给主进程的消息ipcMain.handle('dialog:openFileWindow', async (_event, args) => {const listWindow = new BrowserWindow({width: 500,height: 300,show: false,autoHideMenuBar: true,...(process.platform === 'linux' ? { icon } : {}),webPreferences: {preload: join(__dirname, '../preload/index.js'),sandbox: false}})listWindow.on('ready-to-show', () => {listWindow.show()})if (is.dev && process.env['ELECTRON_RENDERER_URL']) {listWindow.loadURL(process.env['ELECTRON_RENDERER_URL'] + '/list')} else {listWindow.loadFile(join(__dirname, '../renderer/index.html'))}})mainWindow.on('ready-to-show', () => {mainWindow.show()})mainWindow.webContents.setWindowOpenHandler((details) => {shell.openExternal(details.url)return { action: 'deny' }})// HMR for renderer base on electron-vite cli.// Load the remote URL for development or the local html file for production.if (is.dev && process.env['ELECTRON_RENDERER_URL']) {mainWindow.loadURL(process.env['ELECTRON_RENDERER_URL'])} else {mainWindow.loadFile(join(__dirname, '../renderer/index.html'))}
}
三、创建窗口的一些参数选项
const windowOptions = {// 基本窗口尺寸和位置width: 800, // 窗口宽度,默认为 800pxheight: 600, // 窗口高度,默认为 600pxx: 0, // 窗口相对于屏幕的左上角 x 坐标y: 0, // 窗口相对于屏幕的左上角 y 坐标useContentSize: false, // 是否使用内容尺寸(不包括边框)来设置窗口大小// 窗口外观和行为center: false, // 是否在屏幕中心显示窗口minWidth: 0, // 窗口最小宽度minHeight: 0, // 窗口最小高度maxWidth: 0, // 窗口最大宽度maxHeight: 0, // 窗口最大高度resizable: true, // 窗口是否可以调整大小movable: true, // 窗口是否可以移动minimizable: true, // 窗口是否可以最小化maximizable: true, // 窗口是否可以最大化closable: true, // 窗口是否可以关闭focusable: true, // 窗口是否可以获取焦点alwaysOnTop: false, // 窗口是否总是在最前面fullscreen: false, // 窗口是否全屏fullscreenable: true, // 窗口是否可以进入全屏模式simpleFullscreen: false, // 在 macOS 上使用简单全屏模式skipTaskbar: false, // 是否在任务栏中隐藏窗口kiosk: false, // 是否启用 kiosk 模式// 窗口标题和图标title: '', // 窗口标题icon: null, // 窗口图标路径// Web 页面相关webPreferences: {nodeIntegration: false, // 是否启用 Node.js 集成contextIsolation: true, // 是否启用上下文隔离webSecurity: true, // 是否启用 web 安全特性allowRunningInsecureContent: false, // 是否允许在 HTTPS 页面中运行 HTTP 内容preload: '', // 预加载脚本路径zoomFactor: 1.0, // 页面默认缩放因子devTools: true, // 是否启用开发者工具sandbox: false, // 是否启用沙箱模式enableRemoteModule: false, // 是否启用 remote 模块(Electron 12+ 默认禁用)autoplayPolicy: 'no-user-gesture-required', // 自动播放策略spellcheck: true, // 是否启用拼写检查nativeWindowOpen: false, // 是否使用原生 window.open()webviewTag: false, // 是否启用 <webview> 标签plugins: false, // 是否启用插件experimentalFeatures: false, // 是否启用实验性功能scrollBounce: false, // 是否启用滚动弹性效果(macOS)enableWebSQL: true, // 是否启用 WebSQLdefaultFontFamily: {}, // 默认字体族defaultFontSize: 16, // 默认字体大小defaultMonospaceFontSize: 13, // 等宽字体默认大小minimumFontSize: 0, // 最小字体大小defaultEncoding: 'ISO-8859-1', // 默认编码offscreen: false, // 是否启用离屏渲染additionalArguments: [], // 传递给渲染进程的额外参数},// 窗口样式和框架frame: true, // 是否显示窗口边框和标题栏parent: null, // 父窗口modal: false, // 是否为模态窗口acceptFirstMouse: false, // 是否接受第一次鼠标事件disableAutoHideCursor: false, // 是否在输入时自动隐藏光标autoHideMenuBar: false, // 是否自动隐藏菜单栏enableLargerThanScreen: false, // 是否允许窗口大于屏幕backgroundColor: '#FFF', // 窗口背景颜色hasShadow: true, // 窗口是否有阴影opacity: 1.0, // 窗口透明度 (0.0-1.0)darkTheme: false, // 是否使用深色主题transparent: false, // 窗口是否透明type: 'desktop', // 窗口类型(平台特定)titleBarStyle: 'default', // 标题栏样式 ('default', 'hidden', 'hiddenInset')trafficLightPosition: null, // 交通灯按钮位置(macOS)roundedCorners: true, // 窗口是否有圆角thickFrame: true, // 是否使用厚边框(Windows)vibrancy: null, // 毛玻璃效果(macOS)visualEffectState: 'followWindow', // 视觉效果状态(macOS)// 显示相关show: true, // 窗口创建后是否立即显示paintWhenInitiallyHidden: true, // 是否在初始隐藏状态下绘制内容// 平台特定选项tabbingIdentifier: '', // 标签页标识符(macOS)webContents: null, // 使用现有的 webContents 而不是创建新的timeout: 30, // 等待页面加载的超时时间(秒)
}
四、窗口拖拽
当设置titleBarStyle: 'hidden’时,窗口无法移动
1、使用-webkit-app-region: drag
在需要移动窗口的元素上,添加这个样式,就可以移动窗口了,但是会导致其中的元素事件失效,需要在不需要移动窗口的元素上加上-webkit-app-region: no-drag;才可以使事件生效
2、与主线程通信修改窗口大小
- 1、渲染线程添加mousedown事件
<template><div class="main-container" @mousedown="onMouseDown"><router-view></router-view></div>
</template><script setup lang="ts">
import { ref } from 'vue'
const isKeyDown = ref(false)
const distanceX = ref(0)
const distanceY = ref(0)
const onMouseDown = (event): void => {isKeyDown.value = truedistanceX.value = event.xdistanceY.value = event.ywindow.electron.ipcRenderer.invoke('window:mouseDown')document.onmousemove = (ev): void => {if (isKeyDown.value) {const x = ev.screenX - distanceX.valueconst y = ev.screenY - distanceY.value// 给主进程传入坐标let data = {appX: x,appY: y}window.electron.ipcRenderer.invoke('window:custom-adsorption', data)}}document.onmouseup = (): void => {isKeyDown.value = false// 清理事件监听器document.onmousemove = nulldocument.onmouseup = null}
}
</script><style scoped>
.main-container {background-color: red;width: 100vw;height: 100vh;overflow: hidden;
}
</style>
- 2、主线程处理
// 这是因为window中,调用setPosition会修改窗口尺寸,所以我们这里每次获取一次窗口尺寸,在下面进行调用
ipcMain.handle('window:mouseDown', () => {currentWindowSize = mainWindow.getSize()})ipcMain.handle('window:custom-adsorption', async (_event, args) => {const x = args.appXconst y = args.appY// 因为window下设置窗口位置会导致窗口大小变化,所以如下处理const newBounds = {x,y,width: currentWindowSize[0],height: currentWindowSize[1]}mainWindow.setBounds(newBounds)})
五、自定义实现关闭、最大化、最小化功能
ipcMain.handle('window:closeApp', () => {// 退出程序app.quit()// 关闭窗口// mainWindow.close()})// 最小化ipcMain.handle('window:minWindow', () => {mainWindow.minimize()})// 最大化切换ipcMain.handle('window:maxWindow', () => {// 获取屏幕大小const screenSize = screen.getPrimaryDisplay().size// 设置为全屏if (!isFullscreen) {isFullscreen = true// 获取当前窗口位置大小信息currentWindowBounds = mainWindow.getBounds()mainWindow.setBounds({x: 0,y: 0,width: screenSize.width,height: screenSize.height},true)} else {isFullscreen = falsemainWindow.setBounds(currentWindowBounds, true)}})