| 
									
										
										
										
											2024-02-18 12:19:09 +02:00
										 |  |  | import path = require('path'); | 
					
						
							|  |  |  | import url = require("url"); | 
					
						
							|  |  |  | import port = require('./port'); | 
					
						
							|  |  |  | import optionService = require('./options'); | 
					
						
							|  |  |  | import env = require('./env'); | 
					
						
							|  |  |  | import log = require('./log'); | 
					
						
							|  |  |  | import sqlInit = require('./sql_init'); | 
					
						
							|  |  |  | import cls = require('./cls'); | 
					
						
							|  |  |  | import keyboardActionsService = require('./keyboard_actions'); | 
					
						
							|  |  |  | import remoteMain = require("@electron/remote/main") | 
					
						
							|  |  |  | import { App, BrowserWindow, WebContents, ipcMain } from 'electron'; | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-06-30 11:18:34 +02:00
										 |  |  | // Prevent the window being garbage collected
 | 
					
						
							| 
									
										
										
										
											2024-02-18 12:19:09 +02:00
										 |  |  | let mainWindow: BrowserWindow | null; | 
					
						
							|  |  |  | let setupWindow: BrowserWindow | null; | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-02-18 12:19:09 +02:00
										 |  |  | async function createExtraWindow(extraWindowHash: string) { | 
					
						
							| 
									
										
										
										
											2022-01-02 21:35:02 +01:00
										 |  |  |     const spellcheckEnabled = optionService.getOptionBool('spellCheckEnabled'); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-04-02 23:00:04 +03:00
										 |  |  |     const { BrowserWindow } = require('electron'); | 
					
						
							| 
									
										
										
										
											2022-01-02 21:35:02 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-04-23 23:08:15 +02:00
										 |  |  |     const win = new BrowserWindow({ | 
					
						
							| 
									
										
										
										
											2020-04-27 22:29:39 +02:00
										 |  |  |         width: 1000, | 
					
						
							|  |  |  |         height: 800, | 
					
						
							| 
									
										
										
										
											2020-04-23 23:08:15 +02:00
										 |  |  |         title: 'Trilium Notes', | 
					
						
							|  |  |  |         webPreferences: { | 
					
						
							|  |  |  |             nodeIntegration: true, | 
					
						
							| 
									
										
										
										
											2021-03-10 20:02:23 +01:00
										 |  |  |             contextIsolation: false, | 
					
						
							| 
									
										
										
										
											2022-01-02 21:35:02 +01:00
										 |  |  |             spellcheck: spellcheckEnabled | 
					
						
							| 
									
										
										
										
											2020-04-23 23:08:15 +02:00
										 |  |  |         }, | 
					
						
							| 
									
										
										
										
											2020-06-20 12:31:38 +02:00
										 |  |  |         frame: optionService.getOptionBool('nativeTitleBarVisible'), | 
					
						
							| 
									
										
										
										
											2020-04-23 23:08:15 +02:00
										 |  |  |         icon: getIcon() | 
					
						
							|  |  |  |     }); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     win.setMenuBarVisibility(false); | 
					
						
							| 
									
										
										
										
											2023-04-11 21:41:55 +02:00
										 |  |  |     win.loadURL(`http://127.0.0.1:${port}/?extraWindow=1${extraWindowHash}`); | 
					
						
							| 
									
										
										
										
											2022-01-02 21:35:02 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  |     configureWebContents(win.webContents, spellcheckEnabled); | 
					
						
							| 
									
										
										
										
											2020-04-23 23:08:15 +02:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | ipcMain.on('create-extra-window', (event, arg) => { | 
					
						
							| 
									
										
										
										
											2023-04-11 21:41:55 +02:00
										 |  |  |     createExtraWindow(arg.extraWindowHash); | 
					
						
							| 
									
										
										
										
											2020-04-23 23:08:15 +02:00
										 |  |  | }); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-02-18 12:19:09 +02:00
										 |  |  | async function createMainWindow(app: App) { | 
					
						
							| 
									
										
										
										
											2019-12-25 19:38:28 +01:00
										 |  |  |     const windowStateKeeper = require('electron-window-state'); // should not be statically imported
 | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     const mainWindowState = windowStateKeeper({ | 
					
						
							| 
									
										
										
										
											2023-06-30 11:18:34 +02:00
										 |  |  |         // default window width & height, so it's usable on a 1600 * 900 display (including some extra panels etc.)
 | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |         defaultWidth: 1200, | 
					
						
							|  |  |  |         defaultHeight: 800 | 
					
						
							|  |  |  |     }); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-06-20 12:31:38 +02:00
										 |  |  |     const spellcheckEnabled = optionService.getOptionBool('spellCheckEnabled'); | 
					
						
							| 
									
										
										
										
											2020-02-28 22:07:08 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-04-02 23:00:04 +03:00
										 |  |  |     const { BrowserWindow } = require('electron'); // should not be statically imported
 | 
					
						
							| 
									
										
										
										
											2021-06-06 22:15:51 +02:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     mainWindow = new BrowserWindow({ | 
					
						
							|  |  |  |         x: mainWindowState.x, | 
					
						
							|  |  |  |         y: mainWindowState.y, | 
					
						
							|  |  |  |         width: mainWindowState.width, | 
					
						
							|  |  |  |         height: mainWindowState.height, | 
					
						
							|  |  |  |         title: 'Trilium Notes', | 
					
						
							|  |  |  |         webPreferences: { | 
					
						
							| 
									
										
										
										
											2020-02-28 22:07:08 +01:00
										 |  |  |             nodeIntegration: true, | 
					
						
							| 
									
										
										
										
											2021-03-09 22:36:41 +01:00
										 |  |  |             contextIsolation: false, | 
					
						
							| 
									
										
										
										
											2022-05-29 17:42:09 +02:00
										 |  |  |             spellcheck: spellcheckEnabled, | 
					
						
							|  |  |  |             webviewTag: true | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |         }, | 
					
						
							| 
									
										
										
										
											2020-06-20 12:31:38 +02:00
										 |  |  |         frame: optionService.getOptionBool('nativeTitleBarVisible'), | 
					
						
							| 
									
										
										
										
											2021-09-08 21:54:26 +02:00
										 |  |  |         icon: getIcon() | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     }); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     mainWindowState.manage(mainWindow); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     mainWindow.setMenuBarVisibility(false); | 
					
						
							| 
									
										
										
										
											2022-12-21 15:19:05 +01:00
										 |  |  |     mainWindow.loadURL(`http://127.0.0.1:${port}`); | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     mainWindow.on('closed', () => mainWindow = null); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2022-01-02 21:35:02 +01:00
										 |  |  |     configureWebContents(mainWindow.webContents, spellcheckEnabled); | 
					
						
							| 
									
										
										
										
											2022-08-02 22:53:06 +02:00
										 |  |  | 
 | 
					
						
							|  |  |  |     app.on('second-instance', () => { | 
					
						
							|  |  |  |         // Someone tried to run a second instance, we should focus our window.
 | 
					
						
							|  |  |  |         // see www.js "requestSingleInstanceLock" for the rest of this logic with explanation
 | 
					
						
							|  |  |  |         if (mainWindow) { | 
					
						
							|  |  |  |             if (mainWindow.isMinimized()) { | 
					
						
							|  |  |  |                 mainWindow.restore(); | 
					
						
							|  |  |  |             } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |             mainWindow.focus(); | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |     }); | 
					
						
							| 
									
										
										
										
											2022-01-02 21:35:02 +01:00
										 |  |  | } | 
					
						
							| 
									
										
										
										
											2020-02-28 22:07:08 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-02-18 12:19:09 +02:00
										 |  |  | function configureWebContents(webContents: WebContents, spellcheckEnabled: boolean) { | 
					
						
							|  |  |  |     if (!mainWindow) { | 
					
						
							|  |  |  |         return; | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     remoteMain.enable(webContents); | 
					
						
							| 
									
										
										
										
											2021-11-16 22:43:08 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2023-07-14 21:59:43 +02:00
										 |  |  |     mainWindow.webContents.setWindowOpenHandler((details) => { | 
					
						
							|  |  |  |         require("electron").shell.openExternal(details.url); | 
					
						
							|  |  |  |         return { action: 'deny' } | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     }); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     // prevent drag & drop to navigate away from trilium
 | 
					
						
							| 
									
										
										
										
											2020-02-28 22:07:08 +01:00
										 |  |  |     webContents.on('will-navigate', (ev, targetUrl) => { | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |         const parsedUrl = url.parse(targetUrl); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         // we still need to allow internal redirects from setup and migration pages
 | 
					
						
							| 
									
										
										
										
											2024-02-18 12:19:09 +02:00
										 |  |  |         if (!['localhost', '127.0.0.1'].includes(parsedUrl.hostname || "") || (parsedUrl.path && parsedUrl.path !== '/' && parsedUrl.path !== '/?')) { | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |             ev.preventDefault(); | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |     }); | 
					
						
							| 
									
										
										
										
											2020-02-28 22:07:08 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  |     if (spellcheckEnabled) { | 
					
						
							| 
									
										
										
										
											2020-06-20 12:31:38 +02:00
										 |  |  |         const languageCodes = (optionService.getOption('spellCheckLanguageCode')) | 
					
						
							| 
									
										
										
										
											2020-04-20 22:26:31 +02:00
										 |  |  |             .split(',') | 
					
						
							| 
									
										
										
										
											2020-02-28 22:07:08 +01:00
										 |  |  |             .map(code => code.trim()); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         webContents.session.setSpellCheckerLanguages(languageCodes); | 
					
						
							|  |  |  |     } | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | function getIcon() { | 
					
						
							| 
									
										
										
										
											2021-09-07 23:14:17 +02:00
										 |  |  |     return path.join(__dirname, '../../images/app-icons/png/256x256' + (env.isDev() ? '-dev' : '') + '.png'); | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | async function createSetupWindow() { | 
					
						
							| 
									
										
										
										
											2024-04-02 23:00:04 +03:00
										 |  |  |     const { BrowserWindow } = require('electron'); // should not be statically imported
 | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     setupWindow = new BrowserWindow({ | 
					
						
							|  |  |  |         width: 800, | 
					
						
							|  |  |  |         height: 800, | 
					
						
							|  |  |  |         title: 'Trilium Notes Setup', | 
					
						
							| 
									
										
										
										
											2019-12-27 20:22:46 +01:00
										 |  |  |         icon: getIcon(), | 
					
						
							|  |  |  |         webPreferences: { | 
					
						
							|  |  |  |             // necessary for e.g. utils.isElectron()
 | 
					
						
							|  |  |  |             nodeIntegration: true | 
					
						
							|  |  |  |         } | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     }); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |     setupWindow.setMenuBarVisibility(false); | 
					
						
							| 
									
										
										
										
											2022-12-21 15:19:05 +01:00
										 |  |  |     setupWindow.loadURL(`http://127.0.0.1:${port}`); | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     setupWindow.on('closed', () => setupWindow = null); | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | function closeSetupWindow() { | 
					
						
							|  |  |  |     if (setupWindow) { | 
					
						
							|  |  |  |         setupWindow.close(); | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-06-20 21:42:41 +02:00
										 |  |  | async function registerGlobalShortcuts() { | 
					
						
							| 
									
										
										
										
											2024-04-02 23:00:04 +03:00
										 |  |  |     const { globalShortcut } = require('electron'); | 
					
						
							| 
									
										
										
										
											2019-12-27 20:28:27 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-06-20 21:42:41 +02:00
										 |  |  |     await sqlInit.dbReady; | 
					
						
							| 
									
										
										
										
											2019-12-27 20:28:27 +01:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-06-20 12:31:38 +02:00
										 |  |  |     const allActions = keyboardActionsService.getKeyboardActions(); | 
					
						
							| 
									
										
										
										
											2019-12-27 20:28:27 +01:00
										 |  |  | 
 | 
					
						
							|  |  |  |     for (const action of allActions) { | 
					
						
							|  |  |  |         if (!action.effectiveShortcuts) { | 
					
						
							|  |  |  |             continue; | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |         for (const shortcut of action.effectiveShortcuts) { | 
					
						
							|  |  |  |             if (shortcut.startsWith('global:')) { | 
					
						
							|  |  |  |                 const translatedShortcut = shortcut.substr(7); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-06-20 12:31:38 +02:00
										 |  |  |                 const result = globalShortcut.register(translatedShortcut, cls.wrap(() => { | 
					
						
							| 
									
										
										
										
											2024-02-18 12:19:09 +02:00
										 |  |  |                     if (!mainWindow) { | 
					
						
							|  |  |  |                         return; | 
					
						
							|  |  |  |                     } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-12-27 20:28:27 +01:00
										 |  |  |                     // window may be hidden / not in focus
 | 
					
						
							|  |  |  |                     mainWindow.focus(); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |                     mainWindow.webContents.send('globalShortcut', action.actionName); | 
					
						
							|  |  |  |                 })); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |                 if (result) { | 
					
						
							|  |  |  |                     log.info(`Registered global shortcut ${translatedShortcut} for action ${action.actionName}`); | 
					
						
							|  |  |  |                 } | 
					
						
							|  |  |  |                 else { | 
					
						
							|  |  |  |                     log.info(`Could not register global shortcut ${translatedShortcut}`); | 
					
						
							|  |  |  |                 } | 
					
						
							|  |  |  |             } | 
					
						
							|  |  |  |         } | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-11-14 12:36:39 +00:00
										 |  |  | function getMainWindow() { | 
					
						
							|  |  |  |     return mainWindow; | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2024-02-18 12:19:09 +02:00
										 |  |  | export = { | 
					
						
							| 
									
										
										
										
											2019-12-24 14:42:03 +01:00
										 |  |  |     createMainWindow, | 
					
						
							|  |  |  |     createSetupWindow, | 
					
						
							| 
									
										
										
										
											2019-12-27 20:28:27 +01:00
										 |  |  |     closeSetupWindow, | 
					
						
							| 
									
										
										
										
											2021-11-14 12:36:39 +00:00
										 |  |  |     registerGlobalShortcuts, | 
					
						
							|  |  |  |     getMainWindow | 
					
						
							| 
									
										
										
										
											2020-06-20 12:31:38 +02:00
										 |  |  | }; |