electron.js 6.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243
  1. const electron = require('electron')
  2. const { app, ipcMain, BrowserWindow } = electron
  3. const path = require('path')
  4. const isDev = require('electron-is-dev')
  5. const { autoUpdater } = require("electron-updater")
  6. const appIcon = path.join(__dirname, 'assets', 'appicons', 'ico', 'icon.ico')
  7. let mainWindow = null
  8. let launchEvents = {
  9. songs: {
  10. details: [],
  11. download: []
  12. },
  13. playlists: {
  14. details: [],
  15. download: []
  16. },
  17. mods: {
  18. details: [],
  19. install: [],
  20. uninstall: []
  21. }
  22. }
  23. ipcMain.on('launch-events', (_, event, message) => {
  24. switch(event) {
  25. case 'check-launch-events':
  26. mainWindow.webContents.send('launch-events', 'launch-events', launchEvents)
  27. launchEvents = {
  28. songs: {
  29. details: [],
  30. download: [],
  31. delete: []
  32. },
  33. playlists: {
  34. details: [],
  35. download: [],
  36. delete: []
  37. },
  38. mods: {
  39. details: [],
  40. install: [],
  41. uninstall: []
  42. }
  43. }
  44. return
  45. default:
  46. return
  47. }
  48. })
  49. const gotTheLock = app.requestSingleInstanceLock()
  50. if (process.defaultApp) {
  51. if (process.argv.length >= 2) {
  52. app.setAsDefaultProtocolClient('beatdrop', process.execPath, [path.resolve(process.argv[1])])
  53. }
  54. } else {
  55. app.setAsDefaultProtocolClient('beatdrop')
  56. }
  57. if (!gotTheLock) {
  58. app.quit()
  59. } else {
  60. app.on('second-instance', (event, argv, workingDirectory) => {
  61. if(!isDev) handleArgs(argv, true)
  62. if (mainWindow) {
  63. if (mainWindow.isMinimized()) mainWindow.restore()
  64. mainWindow.focus()
  65. }
  66. })
  67. app.on('ready', () => {
  68. autoUpdater.autoDownload = false
  69. autoUpdater.autoInstallOnAppQuit = false
  70. ipcMain.on('electron-updater', (_, event, message) => {
  71. switch(event) {
  72. case 'download-update':
  73. autoUpdater.downloadUpdate()
  74. return
  75. case 'check-for-updates':
  76. try {
  77. autoUpdater.checkForUpdates()
  78. } catch(err) {
  79. main.webContents.send('electron-updater', 'error')
  80. }
  81. return
  82. case 'set-update-channel':
  83. autoUpdater.channel = message
  84. autoUpdater.allowPrerelease = (message !== 'latest')
  85. autoUpdater.allowDowngrade = (message === 'latest')
  86. return
  87. default:
  88. return
  89. }
  90. })
  91. let loading = new BrowserWindow({ width: 400, height: 400, show: false, frame: false, resizable: false, webPreferences: { webSecurity: false } })
  92. if(!isDev) handleArgs(process.argv)
  93. loading.once('show', () => {
  94. let main = createWindow()
  95. autoUpdater.on('checking-for-update', () => {
  96. main.webContents.send('electron-updater', 'checking-for-update')
  97. })
  98. autoUpdater.on('update-available', info => {
  99. main.webContents.send('electron-updater', 'update-available', info)
  100. })
  101. autoUpdater.on('update-not-available', () => {
  102. main.webContents.send('electron-updater', 'update-not-available')
  103. })
  104. autoUpdater.on('error', () => {
  105. main.webContents.send('electron-updater', 'error')
  106. })
  107. autoUpdater.on('download-progress', (progress) => {
  108. main.webContents.send('electron-updater', 'download-progress', progress.percent)
  109. })
  110. autoUpdater.on('update-downloaded', () => {
  111. autoUpdater.quitAndInstall()
  112. })
  113. main.once('ready-to-show', () => {
  114. main.show()
  115. loading.hide()
  116. loading.close()
  117. })
  118. })
  119. loading.loadURL(`file://${path.join(__dirname, '../build/loading.html')}`)
  120. loading.once('ready-to-show', () => loading.show())
  121. if(isDev) {
  122. const { default: installExtension, REACT_DEVELOPER_TOOLS, REDUX_DEVTOOLS } = require('electron-devtools-installer')
  123. let extensions = [REACT_DEVELOPER_TOOLS, REDUX_DEVTOOLS]
  124. for(let i = 0; i < extensions.length; i++) {
  125. installExtension(extensions[i]).then((name) => {
  126. console.log(`Added Extension: ${name}`)
  127. })
  128. .catch((err) => {
  129. console.log('An error occurred: ', err)
  130. })
  131. }
  132. }
  133. })
  134. }
  135. function handleArgs(argv, sendImmediately) {
  136. if(argv.length < 2 || !argv[1].startsWith('beatdrop')) return
  137. let args = argv[1].split(/beatdrop:\/\/|beatdrop:%5C%5C|beatdrop:\/|beatdrop:%5C|beatdrop:/i)[1].split(/\/|%5C/)
  138. switch(args[0].toLowerCase()) {
  139. case 'songs':
  140. if(args.length < 3) return
  141. let songs = args[2].split(',')
  142. switch(args[1].toLowerCase()) {
  143. case 'download':
  144. for(let i = 0; i < songs.length; i++) {
  145. launchEvents.songs.download.push(songs[i])
  146. }
  147. break
  148. case 'details':
  149. launchEvents.songs.details.push(args[2])
  150. break
  151. default:
  152. break
  153. }
  154. break
  155. case 'playlists':
  156. // Planned for future...
  157. case 'mods':
  158. if(args.length < 3) return
  159. let mods = args[2].split(',')
  160. switch(args[1].toLowerCase()) {
  161. case 'details':
  162. launchEvents.mods.details.push(decodeURIComponent(args[2]))
  163. return
  164. case 'install':
  165. for(let i = 0; i < songs.length; i++) {
  166. launchEvents.mods.install.push(decodeURIComponent(mods[i]))
  167. }
  168. return
  169. default:
  170. return
  171. }
  172. return
  173. default:
  174. break
  175. }
  176. if(sendImmediately) {
  177. mainWindow.webContents.send('launch-events', 'launch-events', launchEvents)
  178. launchEvents = {
  179. songs: {
  180. details: [],
  181. download: [],
  182. delete: []
  183. },
  184. playlists: {
  185. details: [],
  186. download: [],
  187. delete: []
  188. },
  189. mods: {
  190. details: [],
  191. install: [],
  192. uninstall: []
  193. }
  194. }
  195. }
  196. }
  197. function createWindow() {
  198. mainWindow = new BrowserWindow({
  199. width: 1015,
  200. height: 615,
  201. minWidth: 1015,
  202. minHeight: 615,
  203. resizable: true,
  204. frame: false,
  205. webPreferences: {
  206. webSecurity: false
  207. },
  208. title: 'BeatDrop',
  209. icon: appIcon,
  210. show: false
  211. })
  212. mainWindow.loadURL(isDev ? 'http://localhost:3000' : `file://${path.join(__dirname, '../build/index.html')}`)
  213. mainWindow.on('closed', () => mainWindow = null)
  214. return mainWindow
  215. }
  216. app.on('window-all-closed', () => {
  217. if (process.platform !== 'darwin') {
  218. app.quit()
  219. }
  220. })
  221. app.on('activate', () => {
  222. if (mainWindow === null) {
  223. createWindow()
  224. }
  225. })