-
The following code (an extension I tried to use to hide the "Run" and "Terminal" menu), which works fine with V1.61.0, now breaks:
try {
const coreInversifyPath = require.resolve('@theia/core/shared/inversify');
console.log("CustomMenuHider: Path to '@theia/core/shared/inversify' resolved from extension:", coreInversifyPath);
} catch (e) {
console.error("CustomMenuHider: FAILED to resolve '@theia/core/shared/inversify' from extension", e);
}
import { ContainerModule as TheiaContainerModule, injectable, interfaces } from '@theia/core/shared/inversify';
console.log("CustomMenuHider: PlainTestClass CLASS DEFINITION ABOUT TO BE PARSED - v7-plain");
@injectable()
class PlainTestClass {
constructor() {
console.log("CustomMenuHider: PlainTestClass CONSTRUCTOR CALLED - v7-plain");
}
// It needs to implement the interface it's bound to if we are type-safe
// For CommandContribution:
registerCommands(registry: CommandRegistry): void {
console.log("CustomMenuHider: PlainTestClass registerCommands called (as CommandContribution) - v7-plain");
}
}
// Alias MenuContribution and use the alias
import { MenuContribution as TheiaMenuContribution, MenuModelRegistry } from '@theia/core/lib/common/menu';
import { MAIN_MENU_BAR } from '@theia/core/lib/common/menu/menu-types';
import { CommandContribution, CommandRegistry } from '@theia/core/lib/common/command';
import * as TheiaCore from '@theia/core'; // Import the whole module
import * as Inversify from 'inversify'; // Import the whole inversify module
// Add markers if possible
if (TheiaCore) { (TheiaCore as any).CASCADE_MARKER_THEIA_CORE = "Set in Extension v7"; }
if (Inversify) { (Inversify as any).CASCADE_MARKER_INVERSIFY = "Set in Extension v7"; }
console.log("CustomMenuHider: MODULE SCRIPT EXECUTING (top-level) - v7");
console.log("CustomMenuHider: TheiaCore Marker from Extension: ", (TheiaCore as any)?.CASCADE_MARKER_THEIA_CORE);
console.log("CustomMenuHider: Inversify Marker from Extension: ", (Inversify as any)?.CASCADE_MARKER_INVERSIFY);
// New log here
console.log("CustomMenuHider: ActualMenuHiderContribution CLASS DEFINITION ABOUT TO BE PARSED - v7-class");
@injectable()
class ActualMenuHiderContribution implements TheiaMenuContribution { // Use aliased interface
constructor() {
console.log("CustomMenuHider: ActualMenuHiderContribution CONSTRUCTOR called - v7");
}
registerMenus(menus: MenuModelRegistry): void {
console.log("CustomMenuHider: ActualMenuHiderContribution registerMenus called - v7 (Corrected Again)");
// ---- DIAGNOSTIC: Log existing menu paths ----
const mainMenuNode = menus.getMenuNode(MAIN_MENU_BAR);
if (mainMenuNode && mainMenuNode.children) {
const topLevelMenuPaths: string[] = [];
// The children here are MenuNodes or Actions
for (const child of mainMenuNode.children) {
// A top-level menu group (like File, Run) is itself a MenuNode
// and its 'id' is its path segment relative to its parent (MAIN_MENU_BAR)
if (child.id) {
topLevelMenuPaths.push(child.id);
}
}
console.log("CustomMenuHider: Existing top-level menu node IDs from MAIN_MENU_BAR:", topLevelMenuPaths);
} else {
console.warn("CustomMenuHider: Could not retrieve MAIN_MENU_BAR node or it has no children.");
}
// ---- END DIAGNOSTIC ----
// Corrected paths based on diagnostic logs
const debugMenuPathString = '6_debug';
const terminalMenuPathString = '7_terminal';
console.log(`CustomMenuHider: Attempting to unregister menu node: ${debugMenuPathString}`);
menus.unregisterMenuNode(debugMenuPathString);
console.log(`CustomMenuHider: Unregistration attempt for menu node path: ${debugMenuPathString} (Check UI)`);
console.log(`CustomMenuHider: Attempting to unregister menu node: ${terminalMenuPathString}`);
menus.unregisterMenuNode(terminalMenuPathString);
console.log(`CustomMenuHider: Unregistration attempt for menu node path: ${terminalMenuPathString} (Check UI)`);
}
}
console.log("CustomMenuHider: ActualCommandContribution CLASS DEFINITION ABOUT TO BE PARSED - v7-class");
@injectable()
class ActualCommandContribution implements CommandContribution {
constructor() {
console.log("CustomMenuHider: ActualCommandContribution CONSTRUCTOR called - v7");
}
registerCommands(registry: CommandRegistry): void {
console.log("CustomMenuHider: ActualCommandContribution registerCommands called - v7");
// No actual commands needed for this test
}
}
const myContainerModule = new TheiaContainerModule(
(
bind: interfaces.Bind,
unbind: interfaces.Unbind, // These are standard
isBound: interfaces.IsBound,
rebind: interfaces.Rebind
) => { // Simplified signature
console.log("CustomMenuHider: ContainerModule CALLBACK EXECUTING - v7");
// Bind using the aliased interface
bind(TheiaMenuContribution)
.to(ActualMenuHiderContribution); // Simplest form
// .inSingletonScope() // Removed for now
// .onActivation(...) // Removed for now
console.log("CustomMenuHider: Bindings completed for ActualMenuHiderContribution (SIMPLIFIED) - v7");
// ---- NEW DIAGNOSTIC using isBound ----
if (isBound(TheiaMenuContribution)) {
console.log("CustomMenuHider: isBound(TheiaMenuContribution) is TRUE from module callback - v7-isBound");
} else {
console.log("CustomMenuHider: isBound(TheiaMenuContribution) is FALSE from module callback - v7-isBound");
}
if (isBound(ActualMenuHiderContribution)) {
console.log("CustomMenuHider: isBound(ActualMenuHiderContribution) BEFORE SELF-BIND is TRUE - v7-isBoundConcretePre");
} else {
console.log("CustomMenuHider: isBound(ActualMenuHiderContribution) BEFORE SELF-BIND is FALSE - v7-isBoundConcretePre");
}
// ---- END NEW DIAGNOSTIC ----
// ---- SELF-BINDING TEST ----
bind(ActualMenuHiderContribution).toSelf();
console.log("CustomMenuHider: Self-binding completed for ActualMenuHiderContribution - v7-selfbind");
if (isBound(ActualMenuHiderContribution)) {
console.log("CustomMenuHider: isBound(ActualMenuHiderContribution) AFTER SELF-BIND is TRUE - v7-isBoundConcretePost");
} else {
console.log("CustomMenuHider: isBound(ActualMenuHiderContribution) AFTER SELF-BIND is FALSE - v7-isBoundConcretePost");
}
// ---- END SELF-BINDING TEST ----
bind(CommandContribution).to(ActualCommandContribution).inSingletonScope();
console.log("CustomMenuHider: Bindings completed for ActualCommandContribution - v7");
// ---- NEW TEST: Bind CommandContribution to PlainTestClass ----
bind(CommandContribution).to(PlainTestClass).inSingletonScope(); // Added .inSingletonScope() for consistency with other bindings
console.log("CustomMenuHider: Bindings completed for CommandContribution to PlainTestClass - v7-plain-test");
// ---- END NEW TEST ----
}
);
console.log("CustomMenuHider: MODULE SCRIPT - myContainerModule created - v7");
console.log(`CustomMenuHider: Typeof myContainerModule: ${typeof myContainerModule}, Is instance of TheiaContainerModule: ${myContainerModule instanceof TheiaContainerModule} - v7-typecheck`);
export default myContainerModule; So how do I customize the IDE menubar? |
Beta Was this translation helpful? Give feedback.
Replies: 1 comment 1 reply
-
Hey @Geeksfino, we've refactored the whole menu API in #14676, so breakage is expected. However, the fix for your issues is luckily very simple. The paths for the menu nodes you're trying to remove has changed.
You should use the following to remove the respective entries: menus.unregisterMenuAction('6_debug', MAIN_MENU_BAR);
menus.unregisterMenuAction('7_terminal', MAIN_MENU_BAR);
You should now use theia/packages/core/src/common/menu/menu-model-registry.ts Lines 329 to 335 in ae5ba43 theia/packages/core/src/common/menu/menu-types.ts Lines 122 to 123 in ae5ba43 |
Beta Was this translation helpful? Give feedback.
Hey @Geeksfino,
we've refactored the whole menu API in #14676, so breakage is expected. However, the fix for your issues is luckily very simple. The paths for the menu nodes you're trying to remove has changed.
You should use the following to remove the respective entries:
You should now use
getMenu
to get theCompoundMenuNode
, which contains thechildren
property:the…