diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/index.js | 80 | ||||
-rw-r--r-- | src/models/Service.js | 13 | ||||
-rw-r--r-- | src/stores/ServicesStore.js | 17 | ||||
-rw-r--r-- | src/webview/recipe.js | 17 |
4 files changed, 89 insertions, 38 deletions
diff --git a/src/index.js b/src/index.js index 830166dcf..75da4ff88 100644 --- a/src/index.js +++ b/src/index.js | |||
@@ -46,35 +46,69 @@ if (isWindows) { | |||
46 | } | 46 | } |
47 | 47 | ||
48 | // Force single window | 48 | // Force single window |
49 | const isSecondInstance = app.makeSingleInstance((argv) => { | 49 | const gotTheLock = app.requestSingleInstanceLock(); |
50 | if (mainWindow) { | 50 | if (!gotTheLock) { |
51 | if (mainWindow.isMinimized()) mainWindow.restore(); | 51 | app.quit(); |
52 | mainWindow.focus(); | 52 | } else { |
53 | app.on('second-instance', (event, argv) => { | ||
54 | // Someone tried to run a second instance, we should focus our window. | ||
55 | if (mainWindow) { | ||
56 | if (mainWindow.isMinimized()) mainWindow.restore(); | ||
57 | mainWindow.focus(); | ||
53 | 58 | ||
54 | if (process.platform === 'win32') { | 59 | if (isWindows) { |
55 | // Keep only command line / deep linked arguments | 60 | // Keep only command line / deep linked arguments |
56 | const url = argv.slice(1); | 61 | const url = argv.slice(1); |
57 | 62 | ||
58 | if (url) { | 63 | if (url) { |
59 | handleDeepLink(mainWindow, url.toString()); | 64 | handleDeepLink(mainWindow, url.toString()); |
65 | } | ||
60 | } | 66 | } |
61 | } | ||
62 | } | ||
63 | 67 | ||
64 | if (argv.includes('--reset-window')) { | 68 | if (argv.includes('--reset-window')) { |
65 | // Needs to be delayed to not interfere with mainWindow.restore(); | 69 | // Needs to be delayed to not interfere with mainWindow.restore(); |
66 | setTimeout(() => { | 70 | setTimeout(() => { |
67 | debug('Resetting windows via Task'); | 71 | debug('Resetting windows via Task'); |
68 | mainWindow.setPosition(DEFAULT_WINDOW_OPTIONS.x + 100, DEFAULT_WINDOW_OPTIONS.y + 100); | 72 | mainWindow.setPosition(DEFAULT_WINDOW_OPTIONS.x + 100, DEFAULT_WINDOW_OPTIONS.y + 100); |
69 | mainWindow.setSize(DEFAULT_WINDOW_OPTIONS.width, DEFAULT_WINDOW_OPTIONS.height); | 73 | mainWindow.setSize(DEFAULT_WINDOW_OPTIONS.width, DEFAULT_WINDOW_OPTIONS.height); |
70 | }, 1); | 74 | }, 1); |
71 | } | 75 | } |
72 | }); | 76 | } |
77 | }); | ||
73 | 78 | ||
74 | if (isSecondInstance) { | 79 | // Create myWindow, load the rest of the app, etc... |
75 | console.log('An instance of Franz is already running. Exiting...'); | 80 | app.on('ready', () => { |
76 | app.exit(); | 81 | }); |
77 | } | 82 | } |
83 | // const isSecondInstance = app.makeSingleInstance((argv) => { | ||
84 | // if (mainWindow) { | ||
85 | // if (mainWindow.isMinimized()) mainWindow.restore(); | ||
86 | // mainWindow.focus(); | ||
87 | |||
88 | // if (process.platform === 'win32') { | ||
89 | // // Keep only command line / deep linked arguments | ||
90 | // const url = argv.slice(1); | ||
91 | |||
92 | // if (url) { | ||
93 | // handleDeepLink(mainWindow, url.toString()); | ||
94 | // } | ||
95 | // } | ||
96 | // } | ||
97 | |||
98 | // if (argv.includes('--reset-window')) { | ||
99 | // // Needs to be delayed to not interfere with mainWindow.restore(); | ||
100 | // setTimeout(() => { | ||
101 | // debug('Resetting windows via Task'); | ||
102 | // mainWindow.setPosition(DEFAULT_WINDOW_OPTIONS.x + 100, DEFAULT_WINDOW_OPTIONS.y + 100); | ||
103 | // mainWindow.setSize(DEFAULT_WINDOW_OPTIONS.width, DEFAULT_WINDOW_OPTIONS.height); | ||
104 | // }, 1); | ||
105 | // } | ||
106 | // }); | ||
107 | |||
108 | // if (isSecondInstance) { | ||
109 | // console.log('An instance of Franz is already running. Exiting...'); | ||
110 | // app.exit(); | ||
111 | // } | ||
78 | 112 | ||
79 | // Fix Unity indicator issue | 113 | // Fix Unity indicator issue |
80 | // https://github.com/electron/electron/issues/9046 | 114 | // https://github.com/electron/electron/issues/9046 |
diff --git a/src/models/Service.js b/src/models/Service.js index 4cc6102ff..84fded584 100644 --- a/src/models/Service.js +++ b/src/models/Service.js | |||
@@ -114,6 +114,13 @@ export default class Service { | |||
114 | }); | 114 | }); |
115 | } | 115 | } |
116 | 116 | ||
117 | @computed get shareWithWebview() { | ||
118 | return { | ||
119 | spellcheckerLanguage: this.spellcheckerLanguage, | ||
120 | isDarkModeEnabled: this.isDarkModeEnabled, | ||
121 | }; | ||
122 | } | ||
123 | |||
117 | @computed get url() { | 124 | @computed get url() { |
118 | if (this.recipe.hasCustomUrl && this.customUrl) { | 125 | if (this.recipe.hasCustomUrl && this.customUrl) { |
119 | let url; | 126 | let url; |
@@ -162,14 +169,14 @@ export default class Service { | |||
162 | return userAgent; | 169 | return userAgent; |
163 | } | 170 | } |
164 | 171 | ||
165 | initializeWebViewEvents(store) { | 172 | initializeWebViewEvents({ handleIPCMessage, openWindow }) { |
166 | this.webview.addEventListener('ipc-message', e => store.actions.service.handleIPCMessage({ | 173 | this.webview.addEventListener('ipc-message', e => handleIPCMessage({ |
167 | serviceId: this.id, | 174 | serviceId: this.id, |
168 | channel: e.channel, | 175 | channel: e.channel, |
169 | args: e.args, | 176 | args: e.args, |
170 | })); | 177 | })); |
171 | 178 | ||
172 | this.webview.addEventListener('new-window', (event, url, frameName, options) => store.actions.service.openWindow({ | 179 | this.webview.addEventListener('new-window', (event, url, frameName, options) => openWindow({ |
173 | event, | 180 | event, |
174 | url, | 181 | url, |
175 | frameName, | 182 | frameName, |
diff --git a/src/stores/ServicesStore.js b/src/stores/ServicesStore.js index 5b70ca271..b0a926d6a 100644 --- a/src/stores/ServicesStore.js +++ b/src/stores/ServicesStore.js | |||
@@ -1,5 +1,8 @@ | |||
1 | import { | 1 | import { |
2 | action, reaction, computed, observable, | 2 | action, |
3 | reaction, | ||
4 | computed, | ||
5 | observable, | ||
3 | } from 'mobx'; | 6 | } from 'mobx'; |
4 | import { debounce, remove } from 'lodash'; | 7 | import { debounce, remove } from 'lodash'; |
5 | 8 | ||
@@ -318,12 +321,17 @@ export default class ServicesStore extends Store { | |||
318 | } | 321 | } |
319 | 322 | ||
320 | @action _setWebviewReference({ serviceId, webview }) { | 323 | @action _setWebviewReference({ serviceId, webview }) { |
324 | debug('Set webview reference', serviceId, webview) | ||
321 | const service = this.one(serviceId); | 325 | const service = this.one(serviceId); |
322 | 326 | ||
323 | service.webview = webview; | 327 | service.webview = webview; |
324 | 328 | ||
325 | if (!service.isAttached) { | 329 | if (!service.isAttached) { |
326 | service.initializeWebViewEvents(this); | 330 | debug('Webview is not attached, initializing'); |
331 | service.initializeWebViewEvents({ | ||
332 | handleIPCMessage: this.actions.service.handleIPCMessage, | ||
333 | openWindow: this.actions.service.openWindow, | ||
334 | }); | ||
327 | service.initializeWebViewListener(); | 335 | service.initializeWebViewListener(); |
328 | } | 336 | } |
329 | 337 | ||
@@ -644,14 +652,15 @@ export default class ServicesStore extends Store { | |||
644 | const service = this.one(serviceId); | 652 | const service = this.one(serviceId); |
645 | 653 | ||
646 | if (service.webview) { | 654 | if (service.webview) { |
647 | service.webview.send('initialize-recipe', service); | 655 | debug('Initialize recipe', service.recipe.id, service.name); |
656 | service.webview.send('initialize-recipe', service.shareWithWebview, service.recipe); | ||
648 | } | 657 | } |
649 | } | 658 | } |
650 | 659 | ||
651 | _initRecipePolling(serviceId) { | 660 | _initRecipePolling(serviceId) { |
652 | const service = this.one(serviceId); | 661 | const service = this.one(serviceId); |
653 | 662 | ||
654 | const delay = 1000; | 663 | const delay = 2000; |
655 | 664 | ||
656 | if (service) { | 665 | if (service) { |
657 | if (service.timer !== null) { | 666 | if (service.timer !== null) { |
diff --git a/src/webview/recipe.js b/src/webview/recipe.js index 944883899..9aa89ce01 100644 --- a/src/webview/recipe.js +++ b/src/webview/recipe.js | |||
@@ -42,9 +42,9 @@ class RecipeController { | |||
42 | 42 | ||
43 | async initialize() { | 43 | async initialize() { |
44 | Object.keys(this.ipcEvents).forEach((channel) => { | 44 | Object.keys(this.ipcEvents).forEach((channel) => { |
45 | ipcRenderer.on(channel, (event, data) => { | 45 | ipcRenderer.on(channel, (...args) => { |
46 | debug('Received IPC event for channel', channel, 'with', data); | 46 | debug('Received IPC event for channel', channel, 'with', ...args); |
47 | this[this.ipcEvents[channel]](event, data); | 47 | this[this.ipcEvents[channel]](...args); |
48 | }); | 48 | }); |
49 | }); | 49 | }); |
50 | 50 | ||
@@ -62,17 +62,18 @@ class RecipeController { | |||
62 | autorun(() => this.update()); | 62 | autorun(() => this.update()); |
63 | } | 63 | } |
64 | 64 | ||
65 | loadRecipeModule(event, data) { | 65 | loadRecipeModule(event, config, recipe) { |
66 | debug('loadRecipeModule'); | 66 | debug('loadRecipeModule'); |
67 | const modulePath = path.join(data.recipe.path, 'webview.js'); | 67 | const modulePath = path.join(recipe.path, 'webview.js'); |
68 | debug('module path', modulePath); | ||
68 | // Delete module from cache | 69 | // Delete module from cache |
69 | delete require.cache[require.resolve(modulePath)]; | 70 | delete require.cache[require.resolve(modulePath)]; |
70 | try { | 71 | try { |
71 | // eslint-disable-next-line | 72 | // eslint-disable-next-line |
72 | require(modulePath)(new RecipeWebview(), data); | 73 | require(modulePath)(new RecipeWebview(), {...config, recipe,}); |
73 | debug('Initialize Recipe', data); | 74 | debug('Initialize Recipe', config, recipe); |
74 | 75 | ||
75 | this.settings.service = data; | 76 | this.settings.service = config; |
76 | } catch (err) { | 77 | } catch (err) { |
77 | console.error('Recipe initialization failed', err); | 78 | console.error('Recipe initialization failed', err); |
78 | } | 79 | } |