Fix application menu exceptions (#1437)

This commit is contained in:
Felix Häusler 2019-10-04 15:59:47 +02:00 committed by Ran Luo
parent cc63cf87da
commit 2c15d516c3
14 changed files with 245 additions and 190 deletions

View File

@ -8,7 +8,6 @@ import { isChildOfDirectory } from 'common/filesystem/paths'
import { isLinux, isOsx } from '../config'
import parseArgs from '../cli/parser'
import { normalizeMarkdownPath } from '../filesystem/markdown'
import { getMenuItemById } from '../menu'
import { selectTheme } from '../menu/actions/theme'
import { dockMenu } from '../menu/templates'
import { watchers } from '../utils/imagePathAutoComplement'
@ -155,21 +154,15 @@ class App {
() => {
const preferences = this._accessor.preferences
const { theme } = preferences.getAll()
let setedTheme = null
if (systemPreferences.isDarkMode() && theme !== 'dark') {
// Application menu is automatically updated via preference manager.
if (systemPreferences.isDarkMode() && theme !== 'dark' &&
theme !== 'material-dark' && theme !== 'one-dark') {
selectTheme('dark')
setedTheme = 'dark'
}
if (!systemPreferences.isDarkMode() && theme === 'dark') {
if (!systemPreferences.isDarkMode() && theme !== 'light' &&
theme !== 'ulysses' && theme !== 'graphite') {
selectTheme('light')
setedTheme = 'light'
}
if (setedTheme) {
const themeMenu = getMenuItemById('themeMenu')
const menuItem = themeMenu.submenu.items.filter(item => (item.id === setedTheme))[0]
if (menuItem) {
menuItem.checked = true
}
}
}
)

View File

@ -429,7 +429,7 @@ class WindowManager extends EventEmitter {
ipcMain.on('window-toggle-always-on-top', win => {
const flag = !win.isAlwaysOnTop()
win.setAlwaysOnTop(flag)
this._appMenu.updateAlwaysOnTopMenu(flag)
this._appMenu.updateAlwaysOnTopMenu(win.id, flag)
})
ipcMain.on('broadcast-preferences-changed', prefs => {

View File

@ -1,7 +1,6 @@
import path from 'path'
import { ipcMain, BrowserWindow } from 'electron'
import log from 'electron-log'
import { updateLineEndingMenu } from '../../menu'
import { searchFilesAndDir } from '../../utils/imagePathAutoComplement'
ipcMain.on('mt::ask-for-image-auto-path', (e, { pathname, src, id }) => {
@ -22,10 +21,6 @@ ipcMain.on('mt::ask-for-image-auto-path', (e, { pathname, src, id }) => {
})
})
ipcMain.on('AGANI::update-line-ending-menu', (e, lineEnding) => {
updateLineEndingMenu(lineEnding)
})
export const edit = (win, type) => {
win.webContents.send('AGANI::edit', { type })
}

View File

@ -1,6 +1,3 @@
import { ipcMain } from 'electron'
import { getMenuItemById } from '../../menu'
const MENU_ID_FORMAT_MAP = {
strongMenuItem: 'strong',
emphasisMenuItem: 'em',
@ -11,17 +8,6 @@ const MENU_ID_FORMAT_MAP = {
mathMenuItem: 'inline_math'
}
const selectFormat = formats => {
const formatMenuItem = getMenuItemById('formatMenuItem')
formatMenuItem.submenu.items.forEach(item => (item.checked = false))
formatMenuItem.submenu.items
.forEach(item => {
if (item.id && formats.some(format => format.type === MENU_ID_FORMAT_MAP[item.id])) {
item.checked = true
}
})
}
export const format = (win, type) => {
// Fix #961
// TODO: This is not the best solution for fix #961, but we don't know how to reproduce this issue.
@ -31,6 +17,18 @@ export const format = (win, type) => {
win.webContents.send('AGANI::format', { type })
}
ipcMain.on('AGANI::selection-formats', (e, formats) => {
selectFormat(formats)
// --- IPC events -------------------------------------------------------------
// NOTE: Don't use static `getMenuItemById` here, instead request the menu by
// window id from `AppMenu` manager.
export const updateFormatMenu = (applicationMenu, formats) => {
const formatMenuItem = applicationMenu.getMenuItemById('formatMenuItem')
formatMenuItem.submenu.items.forEach(item => (item.checked = false))
formatMenuItem.submenu.items
.forEach(item => {
if (item.id && formats.some(format => format.type === MENU_ID_FORMAT_MAP[item.id])) {
item.checked = true
}
})
}

View File

@ -1,6 +1,3 @@
import { ipcMain } from 'electron'
import { getMenuItemById } from '../../menu'
const DISABLE_LABELS = [
// paragraph menu items
'heading1MenuItem', 'heading2MenuItem', 'heading3MenuItem', 'heading4MenuItem',
@ -29,21 +26,30 @@ const MENU_ID_MAP = {
frontMatterMenuItem: 'pre'
}
const setParagraphMenuItemStatus = bool => {
const paragraphMenuItem = getMenuItemById('paragraphMenuEntry')
export const paragraph = (win, type) => {
win.webContents.send('AGANI::paragraph', { type })
}
// --- IPC events -------------------------------------------------------------
// NOTE: Don't use static `getMenuItemById` here, instead request the menu by
// window id from `AppMenu` manager.
const setParagraphMenuItemStatus = (applicationMenu, bool) => {
const paragraphMenuItem = applicationMenu.getMenuItemById('paragraphMenuEntry')
paragraphMenuItem.submenu.items
.forEach(item => (item.enabled = bool))
}
const setMultipleStatus = (list, status) => {
const paragraphMenuItem = getMenuItemById('paragraphMenuEntry')
const setMultipleStatus = (applicationMenu, list, status) => {
const paragraphMenuItem = applicationMenu.getMenuItemById('paragraphMenuEntry')
paragraphMenuItem.submenu.items
.filter(item => item.id && list.includes(item.id))
.forEach(item => (item.enabled = status))
}
const setCheckedMenuItem = affiliation => {
const paragraphMenuItem = getMenuItemById('paragraphMenuEntry')
const setCheckedMenuItem = (applicationMenu, affiliation) => {
const paragraphMenuItem = applicationMenu.getMenuItemById('paragraphMenuEntry')
paragraphMenuItem.submenu.items.forEach(item => (item.checked = false))
paragraphMenuItem.submenu.items.forEach(item => {
if (!item.id) {
@ -86,36 +92,32 @@ const setCheckedMenuItem = affiliation => {
})
}
export const paragraph = (win, type) => {
win.webContents.send('AGANI::paragraph', { type })
}
ipcMain.on('AGANI::selection-change', (e, { start, end, affiliation }) => {
export const updateSelectionMenus = (applicationMenu, { start, end, affiliation }) => {
// format menu
const formatMenuItem = getMenuItemById('formatMenuItem')
const formatMenuItem = applicationMenu.getMenuItemById('formatMenuItem')
formatMenuItem.submenu.items.forEach(item => (item.enabled = true))
// handle menu checked
setCheckedMenuItem(affiliation)
setCheckedMenuItem(applicationMenu, affiliation)
// handle disable
setParagraphMenuItemStatus(true)
setParagraphMenuItemStatus(applicationMenu, true)
if (
(/th|td/.test(start.type) && /th|td/.test(end.type)) ||
(start.type === 'span' && start.block.functionType === 'codeLine') ||
(end.type === 'span' && end.block.functionType === 'codeLine')
) {
setParagraphMenuItemStatus(false)
setParagraphMenuItemStatus(applicationMenu, false)
if (start.block.functionType === 'codeLine' || end.block.functionType === 'codeLine') {
setMultipleStatus(['codeFencesMenuItem'], true)
setMultipleStatus(applicationMenu, ['codeFencesMenuItem'], true)
formatMenuItem.submenu.items.forEach(item => (item.enabled = false))
}
} else if (start.key !== end.key) {
formatMenuItem.submenu.items
.filter(item => item.id && DISABLE_LABELS.includes(item.id))
.forEach(item => (item.enabled = false))
setMultipleStatus(DISABLE_LABELS, false)
setMultipleStatus(applicationMenu, DISABLE_LABELS, false)
} else if (!affiliation.slice(0, 3).some(p => /ul|ol/.test(p.type))) {
setMultipleStatus(['looseListItemMenuItem'], false)
setMultipleStatus(applicationMenu, ['looseListItemMenuItem'], false)
}
}
})

View File

@ -1,7 +1,5 @@
import { ipcMain, BrowserWindow } from 'electron'
import { getMenuItemById } from '../../menu'
const sourceCodeModeMenuItemId = 'sourceCodeModeMenuItem'
const typewriterModeMenuItemId = 'typewriterModeMenuItem'
const focusModeMenuItemId = 'focusModeMenuItem'
@ -28,23 +26,14 @@ export const showTabBar = win => {
}
}
ipcMain.on('AGANI::ask-for-mode', e => {
const sourceCodeModeMenuItem = getMenuItemById(sourceCodeModeMenuItemId)
const typewriterModeMenuItem = getMenuItemById(typewriterModeMenuItemId)
const focusModeMenuItem = getMenuItemById(focusModeMenuItemId)
const modes = {
sourceCode: sourceCodeModeMenuItem.checked,
typewriter: typewriterModeMenuItem.checked,
focus: focusModeMenuItem.checked
}
const win = BrowserWindow.fromWebContents(e.sender)
win.webContents.send('AGANI::res-for-mode', modes)
})
// --- IPC events -------------------------------------------------------------
ipcMain.on('AGANI::set-view-layout', (e, { showSideBar, showTabBar }) => {
const sideBarMenuItem = getMenuItemById('sideBarMenuItem')
const tabBarMenuItem = getMenuItemById('tabBarMenuItem')
// NOTE: Don't use static `getMenuItemById` here, instead request the menu by
// window id from `AppMenu` manager.
export const viewLayoutChanged = (applicationMenu, { showSideBar, showTabBar }) => {
const sideBarMenuItem = applicationMenu.getMenuItemById('sideBarMenuItem')
const tabBarMenuItem = applicationMenu.getMenuItemById('tabBarMenuItem')
sideBarMenuItem.checked = showSideBar
tabBarMenuItem.checked = showTabBar
})
}

View File

@ -3,8 +3,11 @@ import path from 'path'
import { app, ipcMain, Menu } from 'electron'
import log from 'electron-log'
import { ensureDirSync, isDirectory, isFile } from 'common/filesystem'
import { isLinux } from '../config'
import { isLinux, isOsx, isWindows } from '../config'
import { parseMenu } from '../keyboard/shortcutHandler'
import { updateFormatMenu } from '../menu/actions/format'
import { updateSelectionMenus } from '../menu/actions/paragraph'
import { viewLayoutChanged } from '../menu/actions/view'
import configureMenu, { configSettingMenu } from '../menu/templates'
export const MenuType = {
@ -28,14 +31,19 @@ class AppMenu {
this._userDataPath = userDataPath
this.RECENTS_PATH = path.join(userDataPath, FILE_NAME)
this.isOsxOrWindows = /darwin|win32/.test(process.platform)
this.isOsx = process.platform === 'darwin'
this.isOsxOrWindows = isOsx || isWindows
this.isOsx = isOsx
this.activeWindowId = -1
this.windowMenus = new Map()
this._listenForIpcMain()
}
/**
* Add the file or directory path to the recently used documents.
*
* @param {string} filePath The file or directory full path.
*/
addRecentlyUsedDocument (filePath) {
const { isOsxOrWindows, isOsx, MAX_RECENTLY_USED_DOCUMENTS, RECENTS_PATH } = this
@ -66,6 +74,11 @@ class AppMenu {
}
}
/**
* Returns a list of all recently used documents and folders.
*
* @returns {string[]}
*/
getRecentlyUsedDocuments () {
const { RECENTS_PATH, MAX_RECENTLY_USED_DOCUMENTS } = this
if (!isFile(RECENTS_PATH)) {
@ -86,6 +99,9 @@ class AppMenu {
}
}
/**
* Clear recently used documents.
*/
clearRecentlyUsedDocuments () {
const { isOsxOrWindows, isOsx, RECENTS_PATH } = this
if (isOsxOrWindows) app.clearRecentDocuments()
@ -98,34 +114,46 @@ class AppMenu {
fs.writeFileSync(RECENTS_PATH, json, 'utf-8')
}
/**
* Add a default menu to the given window.
*
* @param {number} windowId The window id.
*/
addDefaultMenu (windowId) {
const { windowMenus } = this
const menu = this.buildSettingMenu() // Setting menu is also the fallback menu.
const menu = this._buildSettingMenu() // Setting menu is also the fallback menu.
windowMenus.set(windowId, menu)
}
/**
* Add the settings menu to the given window.
*
* @param {BrowserWindow} window The settings browser window.
*/
addSettingMenu (window) {
const { windowMenus } = this
const menu = this.buildSettingMenu()
const menu = this._buildSettingMenu()
windowMenus.set(window.id, menu)
}
/**
* Add the editor menu to the given window.
*
* @param {BrowserWindow} window The editor browser window.
* @param {[*]} options The menu options.
*/
addEditorMenu (window, options = {}) {
const isSourceMode = !!options.sourceCodeModeEnabled
const { windowMenus } = this
windowMenus.set(window.id, this.buildEditorMenu(true))
windowMenus.set(window.id, this._buildEditorMenu(true))
const { menu, shortcutMap } = windowMenus.get(window.id)
const currentMenu = Menu.getApplicationMenu() // the menu may be null
updateMenuItemSafe(currentMenu, menu, 'sourceCodeModeMenuItem', !!options.sourceCodeModeEnabled)
updateMenuItemSafe(currentMenu, menu, 'typewriterModeMenuItem', false)
// FIXME: Focus mode is being ignored when you open a new window - inconsistency.
// updateMenuItemSafe(currentMenu, menu, 'focusModeMenuItem', false)
// Set source-code editor if prefered.
const sourceCodeModeMenuItem = menu.getMenuItemById('sourceCodeModeMenuItem')
sourceCodeModeMenuItem.checked = isSourceMode
const { checked: isSourceMode } = menu.getMenuItemById('sourceCodeModeMenuItem')
if (isSourceMode) {
// BUG: When opening a file `typewriterMode` and `focusMode` will be reset by editor.
// If source code mode is set the editor must not change the values.
const typewriterModeMenuItem = menu.getMenuItemById('typewriterModeMenuItem')
const focusModeMenuItem = menu.getMenuItemById('focusModeMenuItem')
typewriterModeMenuItem.enabled = false
@ -134,6 +162,11 @@ class AppMenu {
this._keybindings.registerKeyHandlers(window, shortcutMap)
}
/**
* Remove menu from the given window.
*
* @param {number} windowId The window id.
*/
removeWindowMenu (windowId) {
// NOTE: Shortcut handler is automatically unregistered when window is closed.
const { activeWindowId } = this
@ -143,19 +176,35 @@ class AppMenu {
}
}
/**
* Returns the window menu.
*
* @param {number} windowId The window id.
* @returns {Electron.Menu} The menu.
*/
getWindowMenuById (windowId) {
const menu = this.windowMenus.get(windowId)
if (!menu) {
log.error(`getWindowMenuById: Cannot find window menu for id ${windowId}.`)
log.error(`getWindowMenuById: Cannot find window menu for window id ${windowId}.`)
throw new Error(`Cannot find window menu for id ${windowId}.`)
}
return menu.menu
}
/**
* Check whether the given window has a menu.
*
* @param {number} windowId The window id.
*/
has (windowId) {
return this.windowMenus.has(windowId)
}
/**
* Set the given window as last active.
*
* @param {number} windowId The window id.
*/
setActiveWindow (windowId) {
if (this.activeWindowId !== windowId) {
// Change application menu to the current window menu.
@ -164,36 +213,13 @@ class AppMenu {
}
}
buildEditorMenu (createShortcutMap, recentUsedDocuments = null) {
if (!recentUsedDocuments) {
recentUsedDocuments = this.getRecentlyUsedDocuments()
}
const menuTemplate = configureMenu(this._keybindings, this._preferences, recentUsedDocuments)
const menu = Menu.buildFromTemplate(menuTemplate)
let shortcutMap = null
if (createShortcutMap) {
shortcutMap = parseMenu(menuTemplate)
this._appendMiscShortcuts(shortcutMap)
}
return {
shortcutMap,
menu,
type: MenuType.EDITOR
}
}
buildSettingMenu () {
if (this.isOsx) {
const menuTemplate = configSettingMenu(this._keybindings)
const menu = Menu.buildFromTemplate(menuTemplate)
return { menu, type: MenuType.SETTINGS }
}
return { menu: null, type: MenuType.SETTINGS }
}
/**
* Updates all window menus.
*
* NOTE: We need this method to add or remove menu items at runtime.
*
* @param {[string[]]} recentUsedDocuments
*/
updateAppMenu (recentUsedDocuments) {
if (!recentUsedDocuments) {
recentUsedDocuments = this.getRecentlyUsedDocuments()
@ -208,7 +234,7 @@ class AppMenu {
const { menu: oldMenu, type } = value
if (type !== MenuType.EDITOR) return
const { menu: newMenu } = this.buildEditorMenu(false, recentUsedDocuments)
const { menu: newMenu } = this._buildEditorMenu(false, recentUsedDocuments)
// all other menu items are set automatically
updateMenuItem(oldMenu, newMenu, 'sourceCodeModeMenuItem')
@ -228,25 +254,50 @@ class AppMenu {
})
}
updateLineEndingMenu (lineEnding) {
updateLineEndingMenu(lineEnding)
/**
* Update line ending menu items.
*
* @param {number} windowId The window id.
* @param {string} lineEnding Either >lf< or >crlf<.
*/
updateLineEndingMenu (windowId, lineEnding) {
const menus = this.getWindowMenuById(windowId)
const crlfMenu = menus.getMenuItemById('crlfLineEndingMenuEntry')
const lfMenu = menus.getMenuItemById('lfLineEndingMenuEntry')
if (lineEnding === 'crlf') {
crlfMenu.checked = true
} else {
lfMenu.checked = true
}
}
updateAlwaysOnTopMenu (flag) {
const menus = Menu.getApplicationMenu()
/**
* Update always on top menu item.
*
* @param {number} windowId The window id.
* @param {boolean} lineEnding Always on top.
*/
updateAlwaysOnTopMenu (windowId, flag) {
const menus = this.getWindowMenuById(windowId)
const menu = menus.getMenuItemById('alwaysOnTopMenuItem')
menu.checked = flag
}
/**
* Update all theme entries from editor menus to the selected one.
*/
updateThemeMenu = theme => {
this.windowMenus.forEach((value, key) => {
this.windowMenus.forEach(value => {
const { menu, type } = value
if (type !== MenuType.EDITOR) return
if (type !== MenuType.EDITOR) {
return
}
const themeMenus = menu.getMenuItemById('themeMenu')
if (!themeMenus) {
return
}
themeMenus.submenu.items.forEach(item => (item.checked = false))
themeMenus.submenu.items
.forEach(item => {
@ -257,10 +308,15 @@ class AppMenu {
})
}
/**
* Update all auto save entries from editor menus to the given state.
*/
updateAutoSaveMenu = autoSave => {
this.windowMenus.forEach((value, key) => {
this.windowMenus.forEach(value => {
const { menu, type } = value
if (type !== MenuType.EDITOR) return
if (type !== MenuType.EDITOR) {
return
}
const autoSaveMenu = menu.getMenuItemById('autoSaveMenuItem')
if (!autoSaveMenu) {
@ -270,10 +326,15 @@ class AppMenu {
})
}
/**
* Update all aidou entries from editor menus to the given state.
*/
updateAidouMenu = bool => {
this.windowMenus.forEach((value, key) => {
this.windowMenus.forEach(value => {
const { menu, type } = value
if (type !== MenuType.EDITOR) return
if (type !== MenuType.EDITOR) {
return
}
const aidouMenu = menu.getMenuItemById('aidou')
if (!aidouMenu) {
@ -283,6 +344,11 @@ class AppMenu {
})
}
/**
* Append misc shortcuts the the given shortcut map.
*
* @param {*} lineEnding The shortcut map.
*/
_appendMiscShortcuts = shortcutMap => {
shortcutMap.push({
accelerator: this._keybindings.getAccelerator('tabsCycleForward'),
@ -314,6 +380,36 @@ class AppMenu {
})
}
_buildEditorMenu (createShortcutMap, recentUsedDocuments = null) {
if (!recentUsedDocuments) {
recentUsedDocuments = this.getRecentlyUsedDocuments()
}
const menuTemplate = configureMenu(this._keybindings, this._preferences, recentUsedDocuments)
const menu = Menu.buildFromTemplate(menuTemplate)
let shortcutMap = null
if (createShortcutMap) {
shortcutMap = parseMenu(menuTemplate)
this._appendMiscShortcuts(shortcutMap)
}
return {
shortcutMap,
menu,
type: MenuType.EDITOR
}
}
_buildSettingMenu () {
if (this.isOsx) {
const menuTemplate = configSettingMenu(this._keybindings)
const menu = Menu.buildFromTemplate(menuTemplate)
return { menu, type: MenuType.SETTINGS }
}
return { menu: null, type: MenuType.SETTINGS }
}
_setApplicationMenu (menu) {
if (isLinux && !menu) {
// WORKAROUND for Electron#16521: We cannot hide the (application) menu on Linux.
@ -328,6 +424,18 @@ class AppMenu {
ipcMain.on('mt::add-recently-used-document', (e, pathname) => {
this.addRecentlyUsedDocument(pathname)
})
ipcMain.on('mt::update-line-ending-menu', (e, windowId, lineEnding) => {
this.updateLineEndingMenu(windowId, lineEnding)
})
ipcMain.on('mt::update-format-menu', (e, windowId, formats) => {
updateFormatMenu(this.getWindowMenuById(windowId), formats)
})
ipcMain.on('mt::view-layout-changed', (e, windowId, viewSettings) => {
viewLayoutChanged(this.getWindowMenuById(windowId), viewSettings)
})
ipcMain.on('mt::editor-selection-changed', (e, windowId, changes) => {
updateSelectionMenus(this.getWindowMenuById(windowId), changes)
})
ipcMain.on('menu-add-recently-used', pathname => {
this.addRecentlyUsedDocument(pathname)
@ -356,18 +464,6 @@ const updateMenuItem = (oldMenus, newMenus, id) => {
newItem.checked = oldItem.checked
}
const updateMenuItemSafe = (oldMenus, newMenus, id, defaultValue) => {
let checked = defaultValue
if (oldMenus) {
const oldItem = oldMenus.getMenuItemById(id)
if (oldItem) {
checked = oldItem.checked
}
}
const newItem = newMenus.getMenuItemById(id)
newItem.checked = checked
}
// ----------------------------------------------
// HACKY: We have one application menu per window and switch the menu when
@ -384,15 +480,4 @@ export const getMenuItemById = menuId => {
return menus.getMenuItemById(menuId)
}
export const updateLineEndingMenu = lineEnding => {
const menus = Menu.getApplicationMenu()
const crlfMenu = menus.getMenuItemById('crlfLineEndingMenuEntry')
const lfMenu = menus.getMenuItemById('lfLineEndingMenuEntry')
if (lineEnding === 'crlf') {
crlfMenu.checked = true
} else {
lfMenu.checked = true
}
}
export default AppMenu

View File

@ -125,6 +125,7 @@ export default function (keybindings, userPreference) {
}, {
type: 'separator'
}, {
// TODO: Remove this menu entry and add it to the command palette (#1408).
label: 'Line Ending',
submenu: [{
id: 'crlfLineEndingMenuEntry',
@ -141,8 +142,6 @@ export default function (keybindings, userPreference) {
actions.lineEnding(browserWindow, 'lf')
}
}]
}, {
type: 'separator'
}]
}
}

View File

@ -81,7 +81,7 @@ class EditorWindow extends BaseWindow {
this.bringToFront()
const lineEnding = preferences.getPreferedEOL()
appMenu.updateLineEndingMenu(lineEnding)
appMenu.updateLineEndingMenu(this.id, lineEnding)
win.webContents.send('mt::bootstrap-editor', {
addBlankTab,

View File

@ -25,8 +25,13 @@ const parseUrlArgs = () => {
const theme = params.get('theme')
const titleBarStyle = params.get('tbs')
const userDataPath = params.get('udp')
const windowId = params.get('wid')
const windowId = Number(params.get('wid'))
const type = params.get('type')
if (Number.isNaN(windowId)) {
throw new Error('Error while parsing URL arguments: windowId!')
}
return {
type,
debug,

View File

@ -129,7 +129,6 @@ export default {
// module: editor
dispatch('LISTEN_SCREEN_SHOT')
dispatch('ASK_FOR_USER_PREFERENCE')
dispatch('ASK_FOR_MODE')
dispatch('LISTEN_FOR_CLOSE')
dispatch('LISTEN_FOR_SAVE_AS')
dispatch('LISTEN_FOR_MOVE_TO')

View File

@ -374,18 +374,12 @@ const actions = {
commit('EXCHANGE_TABS_BY_ID', tabIDs)
},
// need update line ending when change between windows.
LISTEN_FOR_LINEENDING_MENU ({ commit, state, dispatch }) {
ipcRenderer.on('AGANI::req-update-line-ending-menu', e => {
dispatch('UPDATE_LINEENDING_MENU')
})
},
// need update line ending when change between tabs
UPDATE_LINEENDING_MENU ({ commit, state }) {
// We need to update line endings menu when changing tabs.
UPDATE_LINE_ENDING_MENU ({ state }) {
const { lineEnding } = state.currentFile
if (lineEnding) {
ipcRenderer.send('AGANI::update-line-ending-menu', lineEnding)
const { windowId } = global.marktext.env
ipcRenderer.send('mt::update-line-ending-menu', windowId, lineEnding)
}
},
@ -597,6 +591,7 @@ const actions = {
if (!tabs.some(file => file.id === currentFile.id)) {
commit('ADD_FILE_TO_TABS', currentFile)
}
dispatch('UPDATE_LINE_ENDING_MENU')
},
// This events are only used during window creation.
@ -682,7 +677,7 @@ const actions = {
},
// Direction is a boolean where false is left and true right.
CYCLE_TABS ({ commit, state }, direction) {
CYCLE_TABS ({ commit, dispatch, state }, direction) {
const { tabs, currentFile } = state
if (tabs.length <= 1) {
return
@ -709,6 +704,7 @@ const actions = {
return
}
commit('SET_CURRENT_FILE', nextTab)
dispatch('UPDATE_LINE_ENDING_MENU')
},
/**
@ -915,11 +911,16 @@ const actions = {
})
}
ipcRenderer.send('AGANI::selection-change', changes)
// TODO: We should only send a map of booleans to improve performance and not send
// the full change with all block elements with every change.
const { windowId } = global.marktext.env
ipcRenderer.send('mt::editor-selection-changed', windowId, changes)
},
SELECTION_FORMATS ({ commit }, formats) {
ipcRenderer.send('AGANI::selection-formats', formats)
SELECTION_FORMATS (_, formats) {
const { windowId } = global.marktext.env
ipcRenderer.send('mt::update-format-menu', windowId, formats)
},
// listen for export from main process

View File

@ -25,19 +25,20 @@ const mutations = {
}
const actions = {
LISTEN_FOR_LAYOUT ({ commit }, layout) {
LISTEN_FOR_LAYOUT ({ commit }) {
ipcRenderer.on('AGANI::listen-for-view-layout', (e, layout) => {
commit('SET_LAYOUT', layout)
})
},
LISTEN_FOR_REQUEST_LAYOUT ({ commit, dispatch }) {
LISTEN_FOR_REQUEST_LAYOUT ({ dispatch }) {
ipcRenderer.on('AGANI::request-for-view-layout', () => {
dispatch('SET_LAYOUT_MENU_ITEM')
})
},
SET_LAYOUT_MENU_ITEM ({ commit, state }) {
SET_LAYOUT_MENU_ITEM ({ state }) {
const { windowId } = global.marktext.env
const { showTabBar, showSideBar } = state
ipcRenderer.send('AGANI::set-view-layout', { showTabBar, showSideBar })
ipcRenderer.send('mt::view-layout-changed', windowId, { showTabBar, showSideBar })
},
CHANGE_SIDE_BAR_WIDTH ({ commit }, width) {
commit('SET_SIDE_BAR_WIDTH', width)

View File

@ -99,18 +99,6 @@ const actions = {
})
},
ASK_FOR_MODE ({ commit }) {
ipcRenderer.send('AGANI::ask-for-mode')
ipcRenderer.on('AGANI::res-for-mode', (e, modes) => {
Object.keys(modes).forEach(type => {
commit('SET_MODE', {
type,
checked: modes[type]
})
})
})
},
SET_SINGLE_PREFERENCE ({ commit }, { type, value }) {
// save to electron-store
ipcRenderer.send('mt::set-user-preference', { [type]: value })