Electron無(wú)邊框自定義窗口拖動(dòng)的問(wèn)題小結(jié)
最近使用了electron框架,發(fā)現(xiàn)如果自定義拖動(dòng)是比較實(shí)用的;特別是定制化比較高的項(xiàng)目,如果單純的使用-webkit-app-region: drag;會(huì)讓鼠標(biāo)事件無(wú)法觸發(fā);
過(guò)程中發(fā)現(xiàn)問(wèn)題:
1.windows縮放不是100%后設(shè)置偏移界面會(huì)縮放,感覺像吹起的氣球;
2.單純的添加css;-webkit-app-region: drag; 會(huì)讓鼠標(biāo)事件無(wú)法觸發(fā);
封裝核心方法
import { screen } from 'electron' /* 自定義窗口移動(dòng) */ export class AzCustomWindowMove { // 是否開啟 isOpen: boolean; // 傳入要處理的窗口 win: any; // 窗口偏移 winStartPosition: { x: number, y: number, width: number, height: number, } // 現(xiàn)在鼠標(biāo)所在位置 startPosition: { x: number, y: number, } constructor() { this.isOpen = false; this.win = null; this.winStartPosition = { x: 0, y: 0, width: 0, height: 0, } this.startPosition = { x: 0, y: 0, } } init(win: any) { this.win = win; } start() { this.isOpen = true; // 獲取當(dāng)前窗口偏移[x, y] const winPosition = this.win.getPosition(); // 獲取當(dāng)前縮放[width, height] const winSize = this.win.getSize(); this.winStartPosition.x = winPosition[0]; this.winStartPosition.y = winPosition[1]; this.winStartPosition.width = winSize[0]; this.winStartPosition.height = winSize[1]; // 獲取鼠標(biāo)絕對(duì)位置 const mouseStartPosition = screen.getCursorScreenPoint(); this.startPosition.x = mouseStartPosition.x; this.startPosition.y = mouseStartPosition.y; // 開啟刷新 this.move(); } move() { if (!this.isOpen) { return; }; console.log('this.win.isDestroyed()', this.win.isDestroyed(), this.win.isFocused()); // 如果窗口已銷毀 if (this.win.isDestroyed()) { this.end(); return; } // 判斷窗口是否聚焦 if (!this.win.isFocused()) { this.end(); return; } const cursorPosition = screen.getCursorScreenPoint(); const x = this.winStartPosition.x + cursorPosition.x - this.startPosition.x; const y = this.winStartPosition.y + cursorPosition.y - this.startPosition.y; // this.win.setPosition(120, 120, false); // this.win.setBounds({x: 120, y: 120}) // 更新位置的同時(shí)設(shè)置窗口原大小, windows上設(shè)置=>顯示設(shè)置=>文本縮放 不是100%時(shí),窗口會(huì)拖拽放大 this.win.setBounds({ x: x, y: y, width: this.winStartPosition.width, height: this.winStartPosition.height, }) setTimeout(() => { this.move(); }, 20) } end() { this.isOpen = false; } }
在main.js中引入
import { AzCustomWindowMove } from './util'; /* new 自定義窗口移動(dòng) */ const CustomWindowMove = new AzCustomWindowMove(); // 創(chuàng)建一個(gè)窗口 const mainWindow = new BrowserWindow({ frame: false, webPreferences: { preload: join(__dirname, '../preload/index.js'), sandbox: false } }) // 將窗口傳進(jìn)去 CustomWindowMove.init(mainWindow) // 通信監(jiān)聽 ipcMain.on("Main_Window_Operate", (event, info) => { const operateEvent = info.event || ''; switch(operateEvent) { // 拖拽窗口-開始 case 'homeDragWindowStart': { /* 如果別的窗口也想復(fù)用這個(gè)自定義拖拽方法可以這么用; const webContents = event.sender; const win = BrowserWindow.fromWebContents(webContents); CustomWindowMove.init(win); CustomWindowMove.start(); */ CustomWindowMove.start(); } break; // 拖拽窗口-結(jié)束 case 'homeDragWindowEnd': { CustomWindowMove.end(); } break; default: break; } })
preload.ts 預(yù)加載腳本
import { contextBridge, ipcRenderer } from 'electron' import { electronAPI } from '@electron-toolkit/preload' ... contextBridge.exposeInMainWorld('customAPI', { /** * 發(fā)布main窗口操作消息 * @param info {type: 操作類型, data: 參數(shù)} */ publishMainWindowOperateMessage: (info: {event: string, data: {}}) => { ipcRenderer.send("Main_Window_Operate", info); } }) ...
React綁定事件
const handleMouseDown = (e) => { (window as any).customAPI.publishMainWindowOperateMessage({event: 'homeDragWindowStart'}); } const handleMouseUp = (e) => { (window as any).customAPI.publishMainWindowOperateMessage({event: 'homeDragWindowEnd'}); } /*第二個(gè)思路, 當(dāng)按下后監(jiān)聽document的事件*/ const handleMouseDown = (e) => { // 通知開始 (window as any).customAPI.publishMainWindowOperateMessage({event: 'homeDragWindowStart'}); // 鼠標(biāo)抬起 document.onmouseup = function () { document.onmousemove = null; document.onmouseup = null; document.onselectstart = null; // 通知結(jié)束 (window as any).customAPI.publishMainWindowOperateMessage({event: 'homeDragWindowEnd'}); } } <div onMouseDown={handleMouseDown} onMouseUp={handleMouseUp} >自定義窗口移動(dòng)</div>
到此這篇關(guān)于Electron無(wú)邊框自定義窗口拖動(dòng)的文章就介紹到這了,更多相關(guān)Electron自定義窗口拖動(dòng)內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
D3.js實(shí)現(xiàn)散點(diǎn)圖和氣泡圖的方法詳解
這篇文章將會(huì)給大家介紹了另外兩種可視化圖表,利用D3.js實(shí)現(xiàn)散點(diǎn)圖和氣泡圖,文章通過(guò)多個(gè)方面介紹的非常詳細(xì),下面來(lái)一起看看吧。2016-09-09JS數(shù)組屬性去重并校驗(yàn)重復(fù)數(shù)據(jù)
這篇文章主要介紹了JS數(shù)組屬性去重并校驗(yàn)重復(fù)數(shù)據(jù),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-01-01style、 currentStyle、 runtimeStyle區(qū)別分析
style、 currentStyle、 runtimeStyle區(qū)別分析,需要的朋友可以參考下。2010-08-08原生JS實(shí)現(xiàn)網(wǎng)絡(luò)彩票投注效果
分享一個(gè)最近模仿市面彩票系統(tǒng)寫個(gè)小案例,沒有使用任何后臺(tái),從投注到開獎(jiǎng)再到返獎(jiǎng)都是用原生JS實(shí)現(xiàn)的。2016-09-09JavaScript的類型轉(zhuǎn)換(字符轉(zhuǎn)數(shù)字 數(shù)字轉(zhuǎn)字符)
不能把JavaScript中的類型轉(zhuǎn)換看作為強(qiáng)制類型轉(zhuǎn)換。2010-08-08JavaScript快速切換繁體中文和簡(jiǎn)體中文的方法及網(wǎng)站支持簡(jiǎn)繁體切換的絕招
這篇文章主要介紹了JavaScript快速切換繁體中文和簡(jiǎn)體中文方法的相關(guān)資料,需要的朋友可以參考下2016-03-03JavaScript單線程和任務(wù)隊(duì)列原理解析
這篇文章主要介紹了JavaScript單線程和任務(wù)隊(duì)列原理解析,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-02-02JavaScript 快捷鍵設(shè)置實(shí)現(xiàn)代碼
屏蔽Alt+F4等快捷鍵 IE Javascript快捷鍵操作2009-03-03