'Call quickFix by keyboard shortcuts
I have an editor built by Monaco Editor. For certain texts, it returns certain code actions and quick fix.
However, the shortcut Command + . does not work in Mac and Chrome; Ctrl + . does not work in Windows and Chrome either (I use French keyboard). (This is a working sample of quickFix provided by someone else, where shortcuts don't work either.)
Does anyone know what may be the reason?
I then tried to overwrite the shortcuts. I have the following code in index.tsx:
handleEditorDidMount(editor, monaco) {
// I tried to follow `updateKeyBinding` of https://github.com/microsoft/monaco-editor/issues/102#issuecomment-822981429
const id = "editor.action.quickFix"
const newKeyBinding = monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyP
const { handler, when } = CommandsRegistry.getCommand(id) ?? {}
editor._standaloneKeybindingService.addDynamicKeybinding(id, newKeyBinding, handler)
//@ts-ignore
editor._standaloneKeybindingService.addDynamicKeybinding('write-command' , monaco.KeyMod.Alt | monaco.KeyMod.Shift | monaco.KeyCode.KeyS , this.writeShortcutKey.bind(this));
}
writeShortcutKey can be called by Alt+Shift+S, whereas quickFix cannot be called by Command+P
Does anyone know what's the correct way to assign a shortcut to editor.action.quickFix?
(* Link on Github: https://github.com/microsoft/monaco-editor/issues/3055 *)
Solution 1:[1]
The keyboard shortcuts worked ok for me using this code in the Monaco Playground. One thing to note is that when you load the Monaco playground, paste the code snippet and press > Run, the editor on the right hand side does not have focus (although hovering over the error underline in the editor will bring up the marker). For the keyboard shortcuts to work, you will need to place the cursor so the editor has focus and the cursor is flashing.
If you click where the underlined text is (line 1, column 3) then press the keyboard shortcut, it will bring up the list of quick fixes (a single suggestion named My quickfix in this example).
If your cursor is not positioned on a bit of text in error (e.g. the cursor is at the end of line 1), pressing the shortcut will result in the message No code actions available being displayed.
If you do want to rebind any existing shortcuts, you can use the following code in the Monaco Playground to unbind an existing keyboard shortcut and bind a new one:
monaco.languages.register({ id: 'myLanguage' });
monaco.editor.onDidCreateModel(function(model) {
function validate() {
var textToValidate = model.getValue();
var markers = [{
severity: monaco.MarkerSeverity.Error,
startLineNumber: 1,
startColumn: 3,
endLineNumber: 1,
endColumn: 5,
message: 'Lets correct it'
}];
monaco.editor.setModelMarkers(model, 'myLanguage', markers);
}
var handle = null;
model.onDidChangeContent(() => {
// debounce
clearTimeout(handle);
handle = setTimeout(() => validate(), 500);
});
validate();
});
monaco.languages.registerCodeActionProvider("myLanguage", {
provideCodeActions: (model, range, context, token) => {
const actions = context.markers.map(error => {
return {
title: `My quickfix`, // Name of quickfix
diagnostics: [error],
kind: "quickfix",
edit: {
edits: [
{
resource: model.uri,
edit: {
range: error,
text: "replacement text" // text to replace with
}
}
]
},
isPreferred: true
};
});
return {
actions: actions,
dispose: () => {}
}
}
});
var ed = monaco.editor.create(document.getElementById("container"), {
value: "cont foo = 1;",
language: "myLanguage",
lightbulb: { enabled: false },
});
/**
* Code to rebind the keyboard shortcut to quickFix
*/
// Get access to CommandsRegistry
const CommandsRegistry = require('vs/platform/commands/common/commands').CommandsRegistry;
// Get the handler and when properties for editor.action.quickFix
const { handler, when } = CommandsRegistry.getCommand("editor.action.quickFix") ?? {};
// Unbind the current keyboard shortcut
ed._standaloneKeybindingService.addDynamicKeybinding("-editor.action.quickFix", undefined, () => {});
// Add the new keyboard shortcut (bound to CtrlCmd+P)
const newKeyBinding = monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyP;
ed._standaloneKeybindingService.addDynamicKeybinding("editor.action.quickFix", newKeyBinding, handler, when);
This line of code will unbind the current shortcut:
ed._standaloneKeybindingService.addDynamicKeybinding("-editor.action.quickFix", undefined, () => {});
And these lines binds the new one to Ctrl+P:
const newKeyBinding = monaco.KeyMod.CtrlCmd | monaco.KeyCode.KeyP;
ed._standaloneKeybindingService.addDynamicKeybinding("editor.action.quickFix", newKeyBinding, handler, when);
As mentioned on this comment in the Github link you posted in your question, this solution uses unofficial APIs (as there doesn't yet seem to be a public API for this).
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | Ian A |

