问题
I am using monaco-editor, i see that cut and copy is added in the context menu in later versions. i want to remove these two options from context menu. Please let me know how can i achieve it?
回答1:
Hide individual items with CSS
I tried this code in the browser and it worked.
// Hide from cut on
.context-view li.action-item:nth-child(n + 9) {
display: none !important;
}
// Show command palette
.context-view li.action-item:last-child {
display: flex !important;
}
Disable the entire menu with API
monacoOptions = {
// other options
contextmenu: false
}
See Docs on IEditorConstructionOptions > contextmenu
回答2:
Full Code
import * as actions from "monaco-editor/esm/vs/platform/actions/common/actions";
let menus = actions.MenuRegistry._menuItems
let contextMenuEntry = [...menus].find(entry => entry[0]._debugName == "EditorContext")
let contextMenuLinks = contextMenuEntry[1]
let removableIds = ["editor.action.clipboardCopyAction", "editor.action.clipboardPasteAction"]
let removeById = (list, ids) => {
let node = list._first
do {
let shouldRemove = ids.includes(node.element?.command?.id)
if (shouldRemove) { list._remove(node) }
} while ((node = node.next))
}
removeById(contextMenuLinks, removableIds)
Walkthrough
You can access the available menu functions from MenuRegistry
inside actions.js:
import * as actions from "monaco-editor/esm/vs/platform/actions/common/actions"
let menus = actions.MenuRegistry._menuItems
This will provide a list of all menu types: i.e.["MenubarEditMenu", "CommandPalette", "EditorContext", ...]
To access and modify the context menu specifically, we can find it in the menu map:
let contextMenuEntry = [...menus].find(entry => entry[0]._debugName == "EditorContext")
let contextMenuLinks = contextMenuEntry[1]
The menu items are of type LinkedList, where each node
contains an element
and a reference to the prev
and next
node, but it comes with some utility methods that make it easier to reason about.
So if you want to list all commands, you can do this:
let allCommandIds = [...contextMenuLinks].map(el => el.command?.id)
Using that, identify the list of commands you want to pluck out ahead of time - in our case:
let removableIds = [
"editor.action.clipboardCopyAction",
"editor.action.clipboardPasteAction",
]
Next we need to identify and remove the nodes with those ids. The iterator returns the node.element, but the _remove() function takes in the entire node, so we'll have to iterate a little different than before. Here's a function that loops through all nodes and removes each if
We'll then get all the nodes we want to remove:
let removeById = (list, ids) => {
let node = list._first;
do {
let shouldRemove = ids.includes(node.element?.command?.id)
if (shouldRemove) { list._remove(node) }
} while ((node = node.next))
}
And then call like this:
removeById(contextMenuLinks, removableIds)
Demo
Further Reading
- Remove 'context menu' items (not CSS) #1567
- How can I customize context menu? I want to delete 'Go to definition' #1280
- How to hide the “Command Palette” item from the list of actions in Monaco Editor
- How do I remove options from the contextmenu for monaco-editor?
来源:https://stackoverflow.com/questions/48745208/disable-cut-and-copy-in-context-menu-in-monaco-editor