Thanks for the description. I had managed to edit things in the settings menu for already existing menus. My ultimate goal is to programmatically enable and disable my custom menu based on metadata in the currently focused notebook. I am first attempting the two following simpler operations, which I cannot get to work following any of the examples I have found, nor (so far) by digging through the code of JupyterLab:
- generating a custom menu using schemas. The extension example does not work. It only adds commands to the pallet. I think there is some missing settings registry boiler plate that I am not figuring out or a naming issue. I have tried the following code based on a couple of other extensions that seem to work. However, in my own extension pkg I am not getting it to work.
- pkg/package.json contains the following info about schemas:
[snip]
"jupyterlab": {
"extension": true,
"outputDir": "JPSLMenu2/labextension",
"schemaDir": "schema"
},
[snip]
{
"title": "JPSLMenu2",
"description": "Main Menu Example settings.",
"jupyter.lab.menus": {
"main": [
{
"id": "JPSLMenu2",
"label": "JPSL Tools",
"items": [
{
"command": "Item-1:JPSLMenu2:main-menu",
"args":{"label": "Item 1", "origin": "from the menu"}
},
{
"command": "help:open",
"args": {"text": "Gutow Homesite", "url":"https://cms.gutow.uwosh.edu/Gutow", "newBrowserTab":"true"}
}
],
"rank": 80
}
]
},
"additionalProperties": false,
"type": "object"
}
import {
JupyterFrontEnd,
JupyterFrontEndPlugin,
} from '@jupyterlab/application';
import { IMainMenu } from '@jupyterlab/mainmenu';
import { ICommandPalette } from '@jupyterlab/apputils';
import { ISettingRegistry } from '@jupyterlab/settingregistry';
/**
* Initialization data for a main menu extension.
*/
const extension: JupyterFrontEndPlugin<void> = {
id: 'JPSL2Menu:plugin',
autoStart: true,
requires: [IMainMenu, ICommandPalette, ISettingRegistry],
activate: (app: JupyterFrontEnd,
MainMenu: IMainMenu,
palette: ICommandPalette,
settingRegistry: ISettingRegistry) => {
const { commands } = app;
// Add a command
const command = 'Item-1:JPSLMenu2:main-menu';
commands.addCommand(command, {
label: 'Item 1',
caption: 'Item 1',
execute: (args: any) => {
console.log(
`Item 1 has been called ${args['origin']}.`
);
window.alert(
`Item 1 has been called ${args['origin']}.`
);
},
});
// Add the command to the command palette
const category = 'JPSL Tools';
palette.addItem({
command,
category,
args: { origin: 'from the palette' },
});
// Add a menu using the settings settingRegistry
settingRegistry.load(extension.id);
},
};
export default extension;
I get the following error from jupyter:
tornado.web.HTTPError: HTTP 404: Not Found (Schema not found: <my home directory>/.local/share/hatch/env/virtual/jpslmenu2/a-jj0_aW/jpslmenu2/share/jupyter/lab/schemas/JPSL2Menu/plugin.json)
This leads me to believe that something is wrong about the name I am giving the schema file or how it is referred to in the code. However, all the combinations I have tried do not work. The actual location of the schema for the built project is:
<my home directory>/.local/share/hatch/env/virtual/jpslmenu2/a-jj0_aW/jpslmenu2/share/jupyter/labextensions/JPSL2Menu/schemas/JPSL2Menu/plugin.json)
Which is accessed via a symlink in <my home directory>/.local/share/hatch/env/virtual/jpslmenu2/a-jj0_aW/jpslmenu2/share/jupyter/labextensions/
to the built project in my project directory. I did not set this up. It is what happens when I use jlpm build
in the project that was set up using the Copier template for extensions.
Looking at settings_utils.py, I am wondering if I need to set the path to labextensions somehow and if I need an extra colon in plugin.id
?
- taking a menu I have generated programmatically (which does work) I can hide the menu by directly accessing the DOM, but think it would be better to do it through JupyterLab. Through JupyterLab I can make the menu not show any items using
menu.hide()
and activate it again with menu.show()
. These only impact the menu popup, which appears to be a reuse of ContextMenu
, but leaves the menu visible in the menu bar. Is there a way to use the settings registry with programmatically defined menus?
For either of these am I making silly errors, or can you at least point me in the right direction?
Thanks.