Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions src/vs/platform/actions/common/actions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,7 @@ export class MenuId {
static readonly EditorTitle = new MenuId('EditorTitle');
static readonly EditorTitleRun = new MenuId('EditorTitleRun');
static readonly EditorTitleContext = new MenuId('EditorTitleContext');
static readonly EmptyEditorGroup = new MenuId('EmptyEditorGroup');
static readonly EmptyEditorGroupContext = new MenuId('EmptyEditorGroupContext');
static readonly ExplorerContext = new MenuId('ExplorerContext');
static readonly ExtensionContext = new MenuId('ExtensionContext');
Expand Down
32 changes: 21 additions & 11 deletions src/vs/workbench/browser/contextkeys.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ import { Event } from 'vs/base/common/event';
import { Disposable } from 'vs/base/common/lifecycle';
import { IContextKeyService, IContextKey, RawContextKey } from 'vs/platform/contextkey/common/contextkey';
import { InputFocusedContext, IsMacContext, IsLinuxContext, IsWindowsContext, IsWebContext, IsMacNativeContext, IsDevelopmentContext, IsIOSContext } from 'vs/platform/contextkey/common/contextkeys';
import { ActiveEditorContext, EditorsVisibleContext, TextCompareEditorVisibleContext, TextCompareEditorActiveContext, ActiveEditorGroupEmptyContext, MultipleEditorGroupsContext, TEXT_DIFF_EDITOR_ID, SplitEditorsVertically, InEditorZenModeContext, IsCenteredLayoutContext, ActiveEditorGroupIndexContext, ActiveEditorGroupLastContext, ActiveEditorReadonlyContext, EditorAreaVisibleContext, ActiveEditorAvailableEditorIdsContext, EditorInputCapabilities, ActiveEditorCanRevertContext } from 'vs/workbench/common/editor';
import { ActiveEditorContext, EditorsVisibleContext, TextCompareEditorVisibleContext, TextCompareEditorActiveContext, ActiveEditorGroupEmptyContext, MultipleEditorGroupsContext, TEXT_DIFF_EDITOR_ID, SplitEditorsVertically, InEditorZenModeContext, IsCenteredLayoutContext, ActiveEditorGroupIndexContext, ActiveEditorGroupLastContext, ActiveEditorReadonlyContext, EditorAreaVisibleContext, ActiveEditorAvailableEditorIdsContext, EditorInputCapabilities, ActiveEditorCanRevertContext, ActiveEditorGroupLockedContext } from 'vs/workbench/common/editor';
import { trackFocus, addDisposableListener, EventType, WebFileSystemAccess } from 'vs/base/browser/dom';
import { preferredSideBySideGroupDirection, GroupDirection, IEditorGroupsService } from 'vs/workbench/services/editor/common/editorGroupsService';
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
Expand Down Expand Up @@ -54,6 +54,7 @@ export class WorkbenchContextKeysHandler extends Disposable {
private activeEditorGroupEmpty: IContextKey<boolean>;
private activeEditorGroupIndex: IContextKey<number>;
private activeEditorGroupLast: IContextKey<boolean>;
private activeEditorGroupLocked: IContextKey<boolean>;
private multipleEditorGroupsContext: IContextKey<boolean>;

private editorsVisibleContext: IContextKey<boolean>;
Expand Down Expand Up @@ -124,6 +125,7 @@ export class WorkbenchContextKeysHandler extends Disposable {
this.activeEditorGroupEmpty = ActiveEditorGroupEmptyContext.bindTo(this.contextKeyService);
this.activeEditorGroupIndex = ActiveEditorGroupIndexContext.bindTo(this.contextKeyService);
this.activeEditorGroupLast = ActiveEditorGroupLastContext.bindTo(this.contextKeyService);
this.activeEditorGroupLocked = ActiveEditorGroupLockedContext.bindTo(this.contextKeyService);
this.multipleEditorGroupsContext = MultipleEditorGroupsContext.bindTo(this.contextKeyService);

// Working Copies
Expand Down Expand Up @@ -205,6 +207,9 @@ export class WorkbenchContextKeysHandler extends Disposable {
this._register(this.editorGroupService.onDidRemoveGroup(() => this.updateEditorContextKeys()));
this._register(this.editorGroupService.onDidChangeGroupIndex(() => this.updateEditorContextKeys()));

this._register(this.editorGroupService.onDidChangeActiveGroup(() => this.updateEditorGroupContextKeys()));
this._register(this.editorGroupService.onDidChangeGroupLocked(() => this.updateEditorGroupContextKeys()));

this._register(addDisposableListener(window, EventType.FOCUS_IN, () => this.updateInputContextKeys(), true));

this._register(this.contextService.onDidChangeWorkbenchState(() => this.updateWorkbenchStateContextKey()));
Expand Down Expand Up @@ -237,7 +242,6 @@ export class WorkbenchContextKeysHandler extends Disposable {
}

private updateEditorContextKeys(): void {
const activeGroup = this.editorGroupService.activeGroup;
const activeEditorPane = this.editorService.activeEditorPane;
const visibleEditorPanes = this.editorService.visibleEditorPanes;

Expand All @@ -256,15 +260,7 @@ export class WorkbenchContextKeysHandler extends Disposable {
this.activeEditorGroupEmpty.reset();
}

const groupCount = this.editorGroupService.count;
if (groupCount > 1) {
this.multipleEditorGroupsContext.set(true);
} else {
this.multipleEditorGroupsContext.reset();
}

this.activeEditorGroupIndex.set(activeGroup.index + 1); // not zero-indexed
this.activeEditorGroupLast.set(activeGroup.index === groupCount - 1);
this.updateEditorGroupContextKeys();

if (activeEditorPane) {
this.activeEditorContext.set(activeEditorPane.getId());
Expand All @@ -282,6 +278,20 @@ export class WorkbenchContextKeysHandler extends Disposable {
}
}

private updateEditorGroupContextKeys(): void {
const groupCount = this.editorGroupService.count;
if (groupCount > 1) {
this.multipleEditorGroupsContext.set(true);
} else {
this.multipleEditorGroupsContext.reset();
}

const activeGroup = this.editorGroupService.activeGroup;
this.activeEditorGroupIndex.set(activeGroup.index + 1); // not zero-indexed
this.activeEditorGroupLast.set(activeGroup.index === groupCount - 1);
this.activeEditorGroupLocked.set(activeGroup.isLocked);
}

private updateInputContextKeys(): void {

function activeElementIsInput(): boolean {
Expand Down
23 changes: 20 additions & 3 deletions src/vs/workbench/browser/parts/editor/editor.contribution.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import { URI } from 'vs/base/common/uri';
import { IEditorPaneRegistry, EditorPaneDescriptor } from 'vs/workbench/browser/editor';
import {
IEditorFactoryRegistry, TextCompareEditorActiveContext, ActiveEditorPinnedContext, EditorExtensions, EditorGroupEditorsCountContext,
ActiveEditorStickyContext, ActiveEditorAvailableEditorIdsContext, MultipleEditorGroupsContext, ActiveEditorDirtyContext
ActiveEditorStickyContext, ActiveEditorAvailableEditorIdsContext, MultipleEditorGroupsContext, ActiveEditorDirtyContext, ActiveEditorGroupLockedContext
} from 'vs/workbench/common/editor';
import { SideBySideEditorInput, SideBySideEditorInputSerializer } from 'vs/workbench/common/editor/sideBySideEditorInput';
import { TextResourceEditor } from 'vs/workbench/browser/parts/editor/textResourceEditor';
Expand Down Expand Up @@ -42,7 +42,7 @@ import {
CLOSE_EDITORS_AND_GROUP_COMMAND_ID, CLOSE_EDITORS_IN_GROUP_COMMAND_ID, CLOSE_EDITORS_TO_THE_RIGHT_COMMAND_ID, CLOSE_EDITOR_COMMAND_ID, CLOSE_EDITOR_GROUP_COMMAND_ID,
CLOSE_OTHER_EDITORS_IN_GROUP_COMMAND_ID, CLOSE_PINNED_EDITOR_COMMAND_ID, CLOSE_SAVED_EDITORS_COMMAND_ID, GOTO_NEXT_CHANGE, GOTO_PREVIOUS_CHANGE, KEEP_EDITOR_COMMAND_ID,
PIN_EDITOR_COMMAND_ID, SHOW_EDITORS_IN_GROUP, SPLIT_EDITOR_DOWN, SPLIT_EDITOR_LEFT, SPLIT_EDITOR_RIGHT, SPLIT_EDITOR_UP, TOGGLE_DIFF_IGNORE_TRIM_WHITESPACE,
TOGGLE_DIFF_SIDE_BY_SIDE, TOGGLE_KEEP_EDITORS_COMMAND_ID, UNPIN_EDITOR_COMMAND_ID, setup as registerEditorCommands, REOPEN_WITH_COMMAND_ID
TOGGLE_DIFF_SIDE_BY_SIDE, TOGGLE_KEEP_EDITORS_COMMAND_ID, UNPIN_EDITOR_COMMAND_ID, setup as registerEditorCommands, REOPEN_WITH_COMMAND_ID, TOGGLE_LOCK_GROUP_COMMAND_ID, UNLOCK_GROUP_COMMAND_ID
} from 'vs/workbench/browser/parts/editor/editorCommands';
import { inQuickPickContext, getQuickNavigateHandler } from 'vs/workbench/browser/quickaccess';
import { KeybindingsRegistry, KeybindingWeight } from 'vs/platform/keybinding/common/keybindingsRegistry';
Expand Down Expand Up @@ -292,12 +292,17 @@ if (isMacintosh) {
});
}

// Empty Editor Group Toolbar
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroup, { command: { id: UNLOCK_GROUP_COMMAND_ID, title: localize('unlockGroupAction', "Unlock Group"), icon: Codicon.unlock }, group: 'navigation', order: 10, when: ActiveEditorGroupLockedContext });
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroup, { command: { id: CLOSE_EDITOR_GROUP_COMMAND_ID, title: localize('closeGroupAction', "Close Group"), icon: Codicon.close }, group: 'navigation', order: 10, when: ActiveEditorGroupLockedContext.toNegated() });

// Empty Editor Group Context Menu
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroupContext, { command: { id: SPLIT_EDITOR_UP, title: localize('splitUp', "Split Up") }, group: '2_split', order: 10 });
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroupContext, { command: { id: SPLIT_EDITOR_DOWN, title: localize('splitDown', "Split Down") }, group: '2_split', order: 20 });
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroupContext, { command: { id: SPLIT_EDITOR_LEFT, title: localize('splitLeft', "Split Left") }, group: '2_split', order: 30 });
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroupContext, { command: { id: SPLIT_EDITOR_RIGHT, title: localize('splitRight', "Split Right") }, group: '2_split', order: 40 });
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroupContext, { command: { id: CLOSE_EDITOR_GROUP_COMMAND_ID, title: localize('close', "Close") }, group: '3_close', order: 10, when: ContextKeyExpr.has('multipleEditorGroups') });
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroupContext, { command: { id: TOGGLE_LOCK_GROUP_COMMAND_ID, title: localize('toggleLockGroup', "Lock Group"), toggled: ActiveEditorGroupLockedContext }, group: '3_lock', order: 10, when: ContextKeyExpr.has('multipleEditorGroups') });
MenuRegistry.appendMenuItem(MenuId.EmptyEditorGroupContext, { command: { id: CLOSE_EDITOR_GROUP_COMMAND_ID, title: localize('close', "Close") }, group: '4_close', order: 10, when: ContextKeyExpr.has('multipleEditorGroups') });

// Editor Title Context Menu
MenuRegistry.appendMenuItem(MenuId.EditorTitleContext, { command: { id: CLOSE_EDITOR_COMMAND_ID, title: localize('close', "Close") }, group: '1_close', order: 10 });
Expand All @@ -320,6 +325,7 @@ MenuRegistry.appendMenuItem(MenuId.EditorTitle, { command: { id: SHOW_EDITORS_IN
MenuRegistry.appendMenuItem(MenuId.EditorTitle, { command: { id: CLOSE_EDITORS_IN_GROUP_COMMAND_ID, title: localize('closeAll', "Close All") }, group: '5_close', order: 10 });
MenuRegistry.appendMenuItem(MenuId.EditorTitle, { command: { id: CLOSE_SAVED_EDITORS_COMMAND_ID, title: localize('closeAllSaved', "Close Saved") }, group: '5_close', order: 20 });
MenuRegistry.appendMenuItem(MenuId.EditorTitle, { command: { id: TOGGLE_KEEP_EDITORS_COMMAND_ID, title: localize('toggleKeepEditors', "Keep Editors Open"), toggled: ContextKeyExpr.not('config.workbench.editor.enablePreview') }, group: '7_settings', order: 10 });
MenuRegistry.appendMenuItem(MenuId.EditorTitle, { command: { id: TOGGLE_LOCK_GROUP_COMMAND_ID, title: localize('lockGroup', "Lock Group"), toggled: ActiveEditorGroupLockedContext }, group: '8_lock', order: 10, when: ContextKeyExpr.has('multipleEditorGroups') });

interface IEditorToolItem { id: string; title: string; icon?: { dark?: URI; light?: URI; } | ThemeIcon; }

Expand Down Expand Up @@ -442,6 +448,17 @@ appendEditorToolItem(
}
);

// Unlock Group: only when group is locked
appendEditorToolItem(
{
id: UNLOCK_GROUP_COMMAND_ID,
title: localize('unlockEditorGroup', "Unlock Group"),
icon: Codicon.unlock
},
ActiveEditorGroupLockedContext,
1000000 - 1, // left to close action
);

const previousChangeIcon = registerIcon('diff-editor-previous-change', Codicon.arrowUp, localize('previousChangeIcon', 'Icon for the previous change action in the diff editor.'));
const nextChangeIcon = registerIcon('diff-editor-next-change', Codicon.arrowDown, localize('nextChangeIcon', 'Icon for the next change action in the diff editor.'));
const toggleWhitespace = registerIcon('diff-editor-toggle-whitespace', Codicon.whitespace, localize('toggleWhitespace', 'Icon for the toggle whitespace action in the diff editor.'));
Expand Down
9 changes: 9 additions & 0 deletions src/vs/workbench/browser/parts/editor/editor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,16 @@ export function getEditorPartOptions(configurationService: IConfigurationService

const config = configurationService.getValue<IWorkbenchEditorConfiguration>();
if (config?.workbench?.editor) {

// Assign all primitive configuration over
Object.assign(options, config.workbench.editor);

// Special handle array types and convert to Set
if (Array.isArray(config.workbench.editor.experimentalAutoLockGroups)) {
options.experimentalAutoLockGroups = new Set(config.workbench.editor.experimentalAutoLockGroups);
} else {
options.experimentalAutoLockGroups = undefined;
}
}

return options;
Expand Down
60 changes: 59 additions & 1 deletion src/vs/workbench/browser/parts/editor/editorCommands.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,8 @@ import { IEditorGroupsService, IEditorGroup, GroupDirection, GroupLocation, Grou
import { ContextKeyExpr } from 'vs/platform/contextkey/common/contextkey';
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
import { CommandsRegistry, ICommandHandler, ICommandService } from 'vs/platform/commands/common/commands';
import { MenuRegistry, MenuId } from 'vs/platform/actions/common/actions';
import { MenuRegistry, MenuId, registerAction2, Action2 } from 'vs/platform/actions/common/actions';
import { CATEGORIES } from 'vs/workbench/common/actions';
import { ActiveGroupEditorsByMostRecentlyUsedQuickAccess } from 'vs/workbench/browser/parts/editor/editorQuickAccess';
import { IOpenerService } from 'vs/platform/opener/common/opener';
import { EditorResolution, ITextEditorOptions } from 'vs/platform/editor/common/editor';
Expand All @@ -41,6 +42,9 @@ export const MOVE_ACTIVE_EDITOR_COMMAND_ID = 'moveActiveEditor';
export const LAYOUT_EDITOR_GROUPS_COMMAND_ID = 'layoutEditorGroups';
export const KEEP_EDITOR_COMMAND_ID = 'workbench.action.keepEditor';
export const TOGGLE_KEEP_EDITORS_COMMAND_ID = 'workbench.action.toggleKeepEditors';
export const TOGGLE_LOCK_GROUP_COMMAND_ID = 'workbench.action.experimentalToggleEditorGroupLock';
export const LOCK_GROUP_COMMAND_ID = 'workbench.action.experimentalLockEditorGroup';
export const UNLOCK_GROUP_COMMAND_ID = 'workbench.action.experimentalUnlockEditorGroup';
export const SHOW_EDITORS_IN_GROUP = 'workbench.action.showEditorsInGroup';
export const REOPEN_WITH_COMMAND_ID = 'workbench.action.reopenWithEditor';

Expand Down Expand Up @@ -958,6 +962,60 @@ function registerOtherEditorCommands(): void {
}
});

function setEditorGroupLock(accessor: ServicesAccessor, resourceOrContext?: URI | IEditorCommandsContext, context?: IEditorCommandsContext, locked?: boolean): void {
const editorGroupService = accessor.get(IEditorGroupsService);

const { group } = resolveCommandsContext(editorGroupService, getCommandsContext(resourceOrContext, context));
if (group) {
group.lock(locked ?? !group.isLocked);
}
}

registerAction2(class extends Action2 {
constructor() {
super({
id: TOGGLE_LOCK_GROUP_COMMAND_ID,
title: localize('toggleEditorGroupLock', "Toggle Editor Group Lock"),
category: CATEGORIES.View,
precondition: ContextKeyExpr.has('multipleEditorGroups'),
f1: true
});
}
async run(accessor: ServicesAccessor, resourceOrContext?: URI | IEditorCommandsContext, context?: IEditorCommandsContext): Promise<void> {
setEditorGroupLock(accessor, resourceOrContext, context);
}
});

registerAction2(class extends Action2 {
constructor() {
super({
id: LOCK_GROUP_COMMAND_ID,
title: localize('lockEditorGroup', "Lock Editor Group"),
category: CATEGORIES.View,
precondition: ContextKeyExpr.has('multipleEditorGroups'),
f1: true
});
}
async run(accessor: ServicesAccessor, resourceOrContext?: URI | IEditorCommandsContext, context?: IEditorCommandsContext): Promise<void> {
setEditorGroupLock(accessor, resourceOrContext, context, true);
}
});

registerAction2(class extends Action2 {
constructor() {
super({
id: UNLOCK_GROUP_COMMAND_ID,
title: localize('unlockEditorGroup', "Unlock Editor Group"),
precondition: ContextKeyExpr.has('multipleEditorGroups'),
category: CATEGORIES.View,
f1: true
});
}
async run(accessor: ServicesAccessor, resourceOrContext?: URI | IEditorCommandsContext, context?: IEditorCommandsContext): Promise<void> {
setEditorGroupLock(accessor, resourceOrContext, context, false);
}
});

KeybindingsRegistry.registerCommandAndKeybindingRule({
id: PIN_EDITOR_COMMAND_ID,
weight: KeybindingWeight.WorkbenchContrib,
Expand Down
Loading