main.js 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149
  1. const { app, BrowserWindow, Menu, ipcMain, globalShortcut, dialog, screen, Tray } = require('electron');
  2. const { join } = require('path');
  3. const { fork } = require('child_process');
  4. const { platform } = require('process');
  5. const sleep = (ms) => new Promise(res => setTimeout(res, ms));
  6. class MainSerivce {
  7. constructor() {
  8. Menu.setApplicationMenu(null) // 去掉菜单栏
  9. app.commandLine.appendSwitch('wm-window-animations-disabled') // 拖动闪屏
  10. app.commandLine.appendSwitch('autoplay-policy', 'no-user-gesture-required');
  11. this.loadingWin = null
  12. this.mainWin = null
  13. this.icon = join(__dirname, './icon/playGame.png')
  14. this.contrlEvent = null
  15. app.on('ready', this.onRead.bind(this))
  16. app.on('activate', (e, isVisible) => {
  17. if (!isVisible && this.mainWin) {
  18. // 兼容Mac dock 栏点击
  19. this.mainWin.show()
  20. }
  21. })
  22. app.on('window-all-closed', () => app.quit())
  23. }
  24. createLoading() {
  25. const { size: { width, height } } = screen.getPrimaryDisplay()
  26. this.loadingWin = new BrowserWindow({
  27. frame: false, // 无边框(窗口、工具栏等),只包含网页内容
  28. width,
  29. height,
  30. resizable: false,
  31. center: true,
  32. icon: this.icon,
  33. alwaysOnTop: true,
  34. transparent: true // 窗口是否支持透明,如果想做高级效果最好为true
  35. })
  36. this.loadingWin.loadFile('loading.html')
  37. this.loadingWin.on('close', () => {
  38. this.loadingWin = null
  39. })
  40. }
  41. createWindow() {
  42. this.mainWin = new BrowserWindow({
  43. minWidth: 1300,
  44. minHeight: 760,
  45. width: 1300,
  46. height: 760,
  47. frame: false,
  48. transparent: true,
  49. icon: this.icon,
  50. webPreferences: {
  51. contextIsolation: true,
  52. nodeIntegration: true,
  53. webSecurity: false, // 去掉跨越
  54. nodeIntegrationInWorker: true,
  55. preload: join(__dirname, './preload.js')
  56. },
  57. show: false
  58. })// 创建一个窗口
  59. // 不同环境加载不同文件
  60. if (app.isPackaged) {
  61. this.mainWin.loadFile('dist/index.html')
  62. } else {
  63. this.mainWin.loadURL('http://localhost:6547/')
  64. }
  65. // 事件监听
  66. this.mainWin.on('close', () => { this.mainWin = null })
  67. }
  68. onRead() {
  69. this.createLoading()
  70. this.createWindow()
  71. // 图标
  72. const tray = new Tray(this.icon)
  73. const contextMenu = Menu.buildFromTemplate([
  74. {
  75. label: '退出',
  76. click: () => {
  77. this.mainWin.close()
  78. app.quit()
  79. }
  80. }
  81. ])
  82. tray.setToolTip('控制端')
  83. tray.on('click', () => this.mainWin.show())
  84. // 注册调试模式
  85. globalShortcut.register('Control+F12', () => {
  86. this.mainWin.webContents.toggleDevTools()
  87. })
  88. // 系统环境
  89. if (platform === 'win32') {
  90. // 右键
  91. tray.setContextMenu(contextMenu)
  92. // 禁用右键
  93. this.mainWin.hookWindowMessage(278, () => {
  94. this.mainWin.setEnabled(false);//窗口禁用
  95. setTimeout(() => {
  96. this.mainWin.setEnabled(true);
  97. }, 100) //延时太快会立刻启动,太慢会妨碍窗口其他操作,可自行测试最佳时间
  98. return true
  99. })
  100. } else if (platform === 'darwin') {
  101. app.dock.setIcon(join(__dirname, './icon/playGame@2x.png'))
  102. }
  103. // 通信
  104. ipcMain.on('signal', (_, evt, data) => {
  105. if (evt === 'close-loading') {
  106. if (this.loadingWin) this.loadingWin.close()
  107. this.mainWin.show()
  108. if (this.mainWin.isVisible()) this.connectLogi()
  109. } else if (evt === 'minWin') {
  110. this.mainWin.minimize()
  111. } else if (evt === 'closeWin') {
  112. this.mainWin.close()
  113. } else if (evt === 'maxWin') {
  114. const { width, height } = screen.getPrimaryDisplay().size
  115. if (data) { this.mainWin.setBounds({ x: 0, y: 0, width, height }) } else {
  116. this.mainWin.setBounds({ width: 1300, height: 760 })
  117. this.mainWin.center()
  118. }
  119. }
  120. })
  121. }
  122. connectLogi() {
  123. this.contrlEvent = fork(join(__dirname, './logiControl.js'));
  124. this.contrlEvent.on('message', msg => {
  125. if (msg.type === 'err') {
  126. this.contrlEvent.kill(msg.pid)
  127. this.contrlEvent = null
  128. dialog.showMessageBox(this.mainWin, { message: '请尝试旋转方向或重新插入USB!', type: 'error', title: '连接错误' }).then(async ({ response }) => {
  129. if (!response) {
  130. await sleep(2000)
  131. this.connectLogi()
  132. }
  133. })
  134. } else {
  135. if (this.mainWin && !this.mainWin.isDestroyed() && this.contrlEvent) this.mainWin?.webContents.send('contrlData', msg.data)
  136. }
  137. })
  138. }
  139. };
  140. new MainSerivce()