From 1fb392ff4e447c748acef31ef1bbfb6c3dd98d54 Mon Sep 17 00:00:00 2001 From: Henry Heino <46334387+personalizedrefrigerator@users.noreply.github.com> Date: Tue, 18 Jun 2024 02:02:01 -0700 Subject: [PATCH] Mobile: Fix cmd-i no longer italicizes text (#10604) --- .../CodeMirror/CodeMirrorControl.test.ts | 27 +++++++ .../editor/CodeMirror/configFromSettings.ts | 2 +- packages/editor/CodeMirror/createEditor.ts | 70 ++++++++++--------- 3 files changed, 64 insertions(+), 35 deletions(-) diff --git a/packages/editor/CodeMirror/CodeMirrorControl.test.ts b/packages/editor/CodeMirror/CodeMirrorControl.test.ts index 3d35a8328..bc20d02c3 100644 --- a/packages/editor/CodeMirror/CodeMirrorControl.test.ts +++ b/packages/editor/CodeMirror/CodeMirrorControl.test.ts @@ -61,6 +61,33 @@ describe('CodeMirrorControl', () => { expect(command).toHaveBeenCalledTimes(1); }); + it.each([ + { + before: 'Test', + selection: EditorSelection.range(0, 4), + shortcut: { key: 'i', code: 'KeyI', ctrlKey: true }, + expected: '*Test*', + }, + { + before: 'Test', + selection: EditorSelection.range(0, 4), + shortcut: { key: 'b', code: 'KeyB', ctrlKey: true }, + expected: '**Test**', + }, + { + before: 'Testing', + selection: EditorSelection.range(0, 4), + shortcut: { key: 'b', code: 'KeyB', ctrlKey: true }, + expected: '**Test**ing', + }, + ])('markdown keyboard shortcuts should work (case %#)', ({ before, selection, shortcut, expected }) => { + const control = createEditorControl(before); + control.select(selection.anchor, selection.head); + + pressReleaseKey(control.editor, shortcut); + expect(control.getValue()).toBe(expected); + }); + it('should support overriding default keybindings', () => { const control = createEditorControl('test'); control.execCommand(EditorCommandType.SelectAll); diff --git a/packages/editor/CodeMirror/configFromSettings.ts b/packages/editor/CodeMirror/configFromSettings.ts index 40a409e7d..2e931df7c 100644 --- a/packages/editor/CodeMirror/configFromSettings.ts +++ b/packages/editor/CodeMirror/configFromSettings.ts @@ -63,7 +63,7 @@ const configFromSettings = (settings: EditorSettings) => { } if (!settings.ignoreModifiers) { - extensions.push(keymap.of(defaultKeymap)); + extensions.push(Prec.low(keymap.of(defaultKeymap))); } return extensions; diff --git a/packages/editor/CodeMirror/createEditor.ts b/packages/editor/CodeMirror/createEditor.ts index ff53d09e2..48a0d8684 100644 --- a/packages/editor/CodeMirror/createEditor.ts +++ b/packages/editor/CodeMirror/createEditor.ts @@ -181,11 +181,47 @@ const createEditor = ( const historyCompartment = new Compartment(); const dynamicConfig = new Compartment(); + // Give the default keymap low precedence so that it is overridden + // by extensions with default precedence. + const keymapConfig = Prec.low(keymap.of([ + // Custom mod-f binding: Toggle the external dialog implementation + // (don't show/hide the Panel dialog). + keyCommand('Mod-f', (_: EditorView) => { + if (searchVisible) { + hideSearchDialog(); + } else { + showSearchDialog(); + } + return true; + }), + // Markdown formatting keyboard shortcuts + keyCommand('Mod-b', toggleBolded), + keyCommand('Mod-i', toggleItalicized), + keyCommand('Mod-$', toggleMath), + keyCommand('Mod-`', toggleCode), + keyCommand('Mod-[', decreaseIndent), + keyCommand('Mod-]', increaseIndent), + keyCommand('Mod-k', (_: EditorView) => { + notifyLinkEditRequest(); + return true; + }), + keyCommand('Tab', insertOrIncreaseIndent, true), + keyCommand('Shift-Tab', decreaseIndent, true), + keyCommand('Mod-Enter', (_: EditorView) => { + insertLineAfter(_); + return true; + }, true), + + ...standardKeymap, ...historyKeymap, ...searchKeymap, + ])); + const editor = new EditorView({ state: EditorState.create({ // See https://github.com/codemirror/basic-setup/blob/main/src/codemirror.ts // for a sample configuration. extensions: [ + keymapConfig, + dynamicConfig.of(configFromSettings(props.settings)), historyCompartment.of(history()), @@ -238,40 +274,6 @@ const createEditor = ( notifySelectionChange(viewUpdate); notifySelectionFormattingChange(viewUpdate); }), - - // Give the default keymap low precedence so that it is overridden - // by extensions with default precedence. - Prec.low(keymap.of([ - // Custom mod-f binding: Toggle the external dialog implementation - // (don't show/hide the Panel dialog). - keyCommand('Mod-f', (_: EditorView) => { - if (searchVisible) { - hideSearchDialog(); - } else { - showSearchDialog(); - } - return true; - }), - // Markdown formatting keyboard shortcuts - keyCommand('Mod-b', toggleBolded), - keyCommand('Mod-i', toggleItalicized), - keyCommand('Mod-$', toggleMath), - keyCommand('Mod-`', toggleCode), - keyCommand('Mod-[', decreaseIndent), - keyCommand('Mod-]', increaseIndent), - keyCommand('Mod-k', (_: EditorView) => { - notifyLinkEditRequest(); - return true; - }), - keyCommand('Tab', insertOrIncreaseIndent, true), - keyCommand('Shift-Tab', decreaseIndent, true), - keyCommand('Mod-Enter', (_: EditorView) => { - insertLineAfter(_); - return true; - }, true), - - ...standardKeymap, ...historyKeymap, ...searchKeymap, - ])), ], doc: initialText, }),