Files
arduino-ide/arduino-ide-extension/src/browser/contributions/sketch-control.ts
Akos Kitta d68bc4abdb feat: rename, deletion, and validation support
Closes #1599
Closes #1825
Closes #649
Closes #1847
Closes #1882

Co-authored-by: Akos Kitta <a.kitta@arduino.cc>
Co-authored-by: per1234 <accounts@perglass.com>

Signed-off-by: Akos Kitta <a.kitta@arduino.cc>
2023-02-15 14:09:36 +01:00

197 lines
6.4 KiB
TypeScript

import { CommonCommands } from '@theia/core/lib/browser/common-frontend-contribution';
import { ContextMenuRenderer } from '@theia/core/lib/browser/context-menu-renderer';
import { ApplicationShell } from '@theia/core/lib/browser/shell/application-shell';
import {
Disposable,
DisposableCollection,
} from '@theia/core/lib/common/disposable';
import { nls } from '@theia/core/lib/common/nls';
import { inject, injectable } from '@theia/core/shared/inversify';
import { WorkspaceCommands } from '@theia/workspace/lib/browser/workspace-commands';
import { ArduinoMenus } from '../menu/arduino-menus';
import { CurrentSketch } from '../sketches-service-client-impl';
import {
Command,
CommandRegistry,
KeybindingRegistry,
MenuModelRegistry,
open,
SketchContribution,
TabBarToolbarRegistry,
URI,
} from './contribution';
@injectable()
export class SketchControl extends SketchContribution {
@inject(ApplicationShell)
private readonly shell: ApplicationShell;
@inject(MenuModelRegistry)
private readonly menuRegistry: MenuModelRegistry;
@inject(ContextMenuRenderer)
private readonly contextMenuRenderer: ContextMenuRenderer;
protected readonly toDisposeBeforeCreateNewContextMenu =
new DisposableCollection();
override registerCommands(registry: CommandRegistry): void {
registry.registerCommand(
SketchControl.Commands.OPEN_SKETCH_CONTROL__TOOLBAR,
{
isVisible: (widget) =>
this.shell.getWidgets('main').indexOf(widget) !== -1,
execute: async () => {
this.toDisposeBeforeCreateNewContextMenu.dispose();
let parentElement: HTMLElement | undefined = undefined;
const target = document.getElementById(
SketchControl.Commands.OPEN_SKETCH_CONTROL__TOOLBAR.id
);
if (target instanceof HTMLElement) {
parentElement = target.parentElement ?? undefined;
}
if (!parentElement) {
return;
}
const sketch = await this.sketchServiceClient.currentSketch();
if (!CurrentSketch.isValid(sketch)) {
return;
}
this.menuRegistry.registerMenuAction(
ArduinoMenus.SKETCH_CONTROL__CONTEXT__MAIN_GROUP,
{
commandId: WorkspaceCommands.FILE_RENAME.id,
label: nls.localize('vscode/fileActions/rename', 'Rename'),
order: '1',
}
);
this.toDisposeBeforeCreateNewContextMenu.push(
Disposable.create(() =>
this.menuRegistry.unregisterMenuAction(
WorkspaceCommands.FILE_RENAME
)
)
);
this.menuRegistry.registerMenuAction(
ArduinoMenus.SKETCH_CONTROL__CONTEXT__MAIN_GROUP,
{
commandId: WorkspaceCommands.FILE_DELETE.id,
label: nls.localize('vscode/fileActions/delete', 'Delete'),
order: '2',
}
);
this.toDisposeBeforeCreateNewContextMenu.push(
Disposable.create(() =>
this.menuRegistry.unregisterMenuAction(
WorkspaceCommands.FILE_DELETE
)
)
);
const { mainFileUri, rootFolderFileUris } = sketch;
const uris = [mainFileUri, ...rootFolderFileUris];
for (let i = 0; i < uris.length; i++) {
const uri = new URI(uris[i]);
// focus on the opened sketch
const command = {
id: `arduino-focus-file--${uri.toString()}`,
};
const handler = {
execute: () => open(this.openerService, uri),
};
this.toDisposeBeforeCreateNewContextMenu.push(
registry.registerCommand(command, handler)
);
this.menuRegistry.registerMenuAction(
ArduinoMenus.SKETCH_CONTROL__CONTEXT__RESOURCES_GROUP,
{
commandId: command.id,
label: this.labelProvider.getName(uri),
order: String(i).padStart(4),
}
);
this.toDisposeBeforeCreateNewContextMenu.push(
Disposable.create(() =>
this.menuRegistry.unregisterMenuAction(command)
)
);
}
const options = {
menuPath: ArduinoMenus.SKETCH_CONTROL__CONTEXT,
anchor: {
x: parentElement.getBoundingClientRect().left,
y:
parentElement.getBoundingClientRect().top +
parentElement.offsetHeight,
},
showDisabled: true,
};
this.contextMenuRenderer.render(options);
},
}
);
}
override registerMenus(registry: MenuModelRegistry): void {
registry.registerMenuAction(
ArduinoMenus.SKETCH_CONTROL__CONTEXT__MAIN_GROUP,
{
commandId: WorkspaceCommands.NEW_FILE.id,
label: nls.localize('vscode/menubar/mNewTab', 'New Tab'),
order: '0',
}
);
registry.registerMenuAction(
ArduinoMenus.SKETCH_CONTROL__CONTEXT__NAVIGATION_GROUP,
{
commandId: CommonCommands.PREVIOUS_TAB.id,
label: nls.localize('vscode/menubar/mShowPreviousTab', 'Previous Tab'),
order: '0',
}
);
registry.registerMenuAction(
ArduinoMenus.SKETCH_CONTROL__CONTEXT__NAVIGATION_GROUP,
{
commandId: CommonCommands.NEXT_TAB.id,
label: nls.localize('vscode/menubar/mShowNextTab', 'Next Tab'),
order: '0',
}
);
}
override registerKeybindings(registry: KeybindingRegistry): void {
registry.registerKeybinding({
command: WorkspaceCommands.NEW_FILE.id,
keybinding: 'CtrlCmd+Shift+N',
});
registry.registerKeybinding({
command: CommonCommands.PREVIOUS_TAB.id,
keybinding: 'CtrlCmd+Alt+Left',
});
registry.registerKeybinding({
command: CommonCommands.NEXT_TAB.id,
keybinding: 'CtrlCmd+Alt+Right',
});
}
override registerToolbarItems(registry: TabBarToolbarRegistry): void {
registry.registerItem({
id: SketchControl.Commands.OPEN_SKETCH_CONTROL__TOOLBAR.id,
command: SketchControl.Commands.OPEN_SKETCH_CONTROL__TOOLBAR.id,
});
}
}
export namespace SketchControl {
export namespace Commands {
export const OPEN_SKETCH_CONTROL__TOOLBAR: Command = {
id: 'arduino-open-sketch-control--toolbar',
iconClass: 'fa fa-arduino-sketch-tabs-menu',
};
}
}