diff --git a/public/electron.js b/public/electron.js index 4a6ba0fd5..9c7187c71 100755 --- a/public/electron.js +++ b/public/electron.js @@ -253,21 +253,42 @@ if (!gotTheLock) { }); }); - app.on('before-quit', () => { - const win = mainWindow.get(); - if (win) { - // https://github.com/atom/electron/issues/444#issuecomment-76492576 - win.forceClose = true; - win.setBrowserView(null); + app.on('before-quit', (e) => { + const handleBeforeQuit = () => { + const win = mainWindow.get(); + if (win) { + // https://github.com/atom/electron/issues/444#issuecomment-76492576 + win.forceClose = true; + win.setBrowserView(null); + } + + // https://github.com/webcatalog/webcatalog-app/issues/1141 + // the bug seems to only occur when there's BrowserView opened + // so destroy all BrowserViews before exiting + const views = BrowserView.getAllViews(); + views.forEach((view) => { + view.destroy(); + }); + }; + + const warnBeforeQuitting = getPreference('warnBeforeQuitting'); + if (warnBeforeQuitting) { + e.preventDefault(); + dialog.showMessageBox(mainWindow.get(), { + type: 'question', + buttons: ['Yes', 'No'], + message: 'Are you sure you want to quit the app?', + cancelId: 1, + defaultId: 1, + }).then(({ response }) => { + if (response === 0) { + handleBeforeQuit(); + } + }).catch(console.log); // eslint-disable-line + return; } - // https://github.com/webcatalog/webcatalog-app/issues/1141 - // the bug seems to only occur when there's BrowserView opened - // so destroy all BrowserViews before exiting - const views = BrowserView.getAllViews(); - views.forEach((view) => { - view.destroy(); - }); + handleBeforeQuit(); }); app.on('window-all-closed', () => { diff --git a/public/libs/menu.js b/public/libs/menu.js index d95d52bdf..e0765aa7b 100755 --- a/public/libs/menu.js +++ b/public/libs/menu.js @@ -14,6 +14,7 @@ const getViewBounds = require('./get-view-bounds'); const formatBytes = require('./format-bytes'); const { setPreference, + getPreference, } = require('./preferences'); const { @@ -126,6 +127,15 @@ const createMenu = async () => { }, ...macMenuItems, { type: 'separator' }, + { + label: 'Warn Before Quitting', + click: () => { + setPreference('warnBeforeQuitting', !getPreference('warnBeforeQuitting')); + createMenu(); + }, + type: 'checkbox', + checked: getPreference('warnBeforeQuitting'), + }, { role: 'quit' }, ], }, diff --git a/public/libs/preferences.js b/public/libs/preferences.js index 0a829bd41..30550debe 100755 --- a/public/libs/preferences.js +++ b/public/libs/preferences.js @@ -84,6 +84,7 @@ const defaultPreferences = { titleBar: !shouldShowSidebar, // if sidebar is shown, then hide titleBar unreadCountBadge: true, useHardwareAcceleration: true, + warnBeforeQuitting: false, }; let cachedPreferences = null; diff --git a/src/components/dialog-preferences/index.js b/src/components/dialog-preferences/index.js index e1f696e07..da8a8aa7c 100644 --- a/src/components/dialog-preferences/index.js +++ b/src/components/dialog-preferences/index.js @@ -201,6 +201,7 @@ const Preferences = ({ titleBar, unreadCountBadge, useHardwareAcceleration, + warnBeforeQuitting, }) => { const appJson = window.remote.getGlobal('appJson'); const utmSource = 'juli_app'; @@ -1311,7 +1312,7 @@ const Preferences = ({ onClick={requestCheckForUpdates} > @@ -1364,6 +1365,19 @@ const Preferences = ({ + + + + { + requestSetPreference('warnBeforeQuitting', e.target.checked); + }} + /> + + @@ -1436,6 +1450,7 @@ Preferences.propTypes = { titleBar: PropTypes.bool.isRequired, unreadCountBadge: PropTypes.bool.isRequired, useHardwareAcceleration: PropTypes.bool.isRequired, + warnBeforeQuitting: PropTypes.bool.isRequired, }; const mapStateToProps = (state) => ({ @@ -1481,6 +1496,7 @@ const mapStateToProps = (state) => ({ titleBar: state.preferences.titleBar, unreadCountBadge: state.preferences.unreadCountBadge, useHardwareAcceleration: state.preferences.useHardwareAcceleration, + warnBeforeQuitting: state.preferences.warnBeforeQuitting, }); const actionCreators = {