extension-examples
extension-examples copied to clipboard
Add example of toolbar button in text editor (+for particular file extension)
Problem
There is an excellent example on how to add a button to the notebook toolbar, which boils down to https://github.com/jupyterlab/extension-examples/blob/9c35013ce5da125f1b5865b3f7cbb301970d5970/toolbar-button/src/index.ts#L67
Now, I would like to do the same with other editors available in JupyterLab, in particular tailored for the specific file extension (think .py or .md or .tex). I played around with the example and reached the desired result. I thought the answer might be useful for someone else searching for the same functionality.
The first part (adding button to all text editors) is straightforward: change the name of the widget factory widgetName
in the addWidgetExtension
call from 'Notebook'
to 'Editor'
. The second part I achieved by checking the path ending:
// Limit the toolbar button for .tex files only
if (context.path.endsWith('.tex')) {
panel.toolbar.insertItem(10, 'clearOutputs', button);
}
I am not sure this is the best (or even valid) way to do this, but it gave the desired result. The full example is available in my fork: https://github.com/ktaletsk/extension-examples/blob/toolbar-button-editor/toolbar-button/src/index.ts
To summarize, I would like to:
- Ask community if the proposed solution is the way to go for buttons in specific file extension editors
- Add the accepted solution (either mine or better one from community) as part of
toolbar-button
example or posible a different example in this repo. I would be happy to create PR.
Proposed Solution
Add example of the toolbar button enabled only for specific file extension
Additional context
Proposed example in action:
Thank you for opening your first issue in this project! Engagement like this is essential for open source projects! :hugs:
If you haven't done so already, check out Jupyter's Code of Conduct. Also, please try to follow the issue template as it helps other other community members to contribute more effectively.
You can meet the other Jovyans by joining our Discourse forum. There is also an intro thread there where you can stop by and say Hi! :wave:
Welcome to the Jupyter community! :tada:
Hey @ktaletsk thanks for proposing.
This looks great. For information there is a simpler way coming in JLab 3.3 to add buttons from settings (see documentation).
In that method the command isEnabled
method is used but not the isVisible
.
But for the case you are targeting with conditions on whether the button should be added or not. This looks good (note that the type of the widget should be updated as you are not receiving a NotebookPanel
in the case of the file editor).
Happy to review a PR on this.
@fcollonval thanks for offering to review. Draft PR is now open. I added the new editor toolbar button alongside with the old notebook toolbar button in the index.ts
. I would be interested to also add the Toolbar Registry button example once 3.3 ships.
I have to admit, I do not understand the machinery of widgets/panels/registries very well, so bear with me here. What should be the equivalent of NotebookPanel
for the file editor? Also, my new example is compiling and working, even though I am passing NotebookPanel
there.
@fcollonval thanks for offering to review. Draft PR is now open. I added the new editor toolbar button alongside with the old notebook toolbar button in the
index.ts
. I would be interested to also add the Toolbar Registry button example once 3.3 ships.
:rocket:
I have to admit, I do not understand the machinery of widgets/panels/registries very well, so bear with me here. What should be the equivalent of
NotebookPanel
for the file editor? Also, my new example is compiling and working, even though I am passingNotebookPanel
there.
For the file editor, you will receive a IDocumentWidget<FileEditor>
.
This is hidden because TypeScript is only a static typer. It does not act at runtime (during which the browser is executing pure non-typed JavaScript). And it works because you are only using the common interface provided by IDocumentWidget
(that is both implemented by NotebookPanel
and the file editor.
More in-depth, the reason TypeScript is not complaining is that function
addWidgetExtension(
widgetName: string,
extension: DocumentRegistry.WidgetExtension
)
There the type of extension
is linked dynamically by the provided name. So you can provide any kind of extension
that provide the correct interface.