mirror of
https://github.com/microsoft/vscode.git
synced 2026-08-20 16:23:02 +01:00
sessions: move Create Pull Request bar to the editor tabs title (#325122)
* sessions: move Create Pull Request bar to the editor tabs title Host the Changes 'Create Pull Request' button bar (ChangesActionsBar) in the single-pane editor tabs title (the editor-actions area of the docked tab bar, Menus.SessionsEditorTitle) instead of the session title bar. - Contribute the CHANGES_HEADER_ACTIONS_ID anchor action to Menus.SessionsEditorTitle, gated on the Changes editor being active in single-pane (singlePaneChangesEditorTitle) + SessionHasChangesContext. - Provide the custom action view item (ChangesActionsBarActionViewItem) from SessionChangesEditor.getActionViewItem so the group's editor-actions toolbar renders it. - Collapse the button labels to icon-only when the tabs title is narrow: a ResizeObserver on the tab-bar ancestor drives a compact observable that the button-bar widgets read to strip labels, freeing room for tabs. - Adjust the ChangesActionsBar CSS comments/scoping for the editor tabs title host. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> * Make the button responsive --------- Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com> Co-authored-by: Ladislau Szomoru <3372902+lszomoru@users.noreply.github.com>
This commit is contained in:
co-authored by
Copilot
Ladislau Szomoru
parent
02955b5aae
commit
45d9cf02a2
File diff suppressed because one or more lines are too long
@@ -31,6 +31,17 @@
|
||||
padding-right: 0;
|
||||
}
|
||||
|
||||
.agent-sessions-workbench .part.editor > .content .editor-group-container > .title > .tabs-and-actions-container.tabs-border-bottom > .editor-actions {
|
||||
flex: 0 999 auto;
|
||||
min-width: 70px;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.agent-sessions-workbench .part.editor > .content .editor-group-container > .title > .tabs-and-actions-container.tabs-border-bottom > .monaco-scrollable-element {
|
||||
flex: 1 1 auto;
|
||||
min-width: 0;
|
||||
}
|
||||
|
||||
.agent-sessions-workbench .part.editor > .content .editor-group-container > .title .editor-actions-separator {
|
||||
display: block;
|
||||
align-self: center;
|
||||
|
||||
@@ -446,18 +446,21 @@ export class ChangesActionsBar extends Disposable {
|
||||
updateVisibility();
|
||||
}));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// --- Editor header menus (single-pane): the Changes editor declares
|
||||
// Menus.SessionsEditorHeaderPrimary (Branch Changes picker + diff stats, left) and
|
||||
// Menus.SessionsEditorHeaderSecondary (diff/code-review/view-mode actions, right), and
|
||||
// the editor group renders them. The Create Pull Request bar (ChangesActionsBar) is
|
||||
// hosted in the sessions title bar (Menus.TitleBarSessionMenu). The custom action view
|
||||
// items below are registered globally by menu id so the toolbars render them.
|
||||
// hosted in the editor tabs title (Menus.SessionsEditorTitle); its custom action view
|
||||
// item is provided by the Changes editor pane (SessionChangesEditor.getActionViewItem).
|
||||
// The custom action view items below are registered globally by menu id so the
|
||||
// header toolbars render them.
|
||||
|
||||
export const CHANGES_HEADER_ACTIONS_ID = 'workbench.changesView.headerActions';
|
||||
|
||||
/** Renders the {@link ChangesActionsBar} widget as the Create Pull Request title-bar action item. */
|
||||
/** Renders the {@link ChangesActionsBar} widget as the Create Pull Request editor tabs title action item. */
|
||||
export class ChangesActionsBarActionViewItem extends BaseActionViewItem {
|
||||
constructor(
|
||||
action: IAction,
|
||||
@@ -509,11 +512,6 @@ class ChangesEditorHeaderContribution extends Disposable implements IWorkbenchCo
|
||||
return instantiationService.createInstance(ChangesDiffStatsActionItem, action, options);
|
||||
}, onDidRegister.event));
|
||||
|
||||
// Create Pull Request button bar, hosted in the title bar (right, session actions area).
|
||||
this._register(actionViewItemService.register(Menus.TitleBarSessionMenu, CHANGES_HEADER_ACTIONS_ID, (action, options, instantiationService) => {
|
||||
return instantiationService.createInstance(ChangesActionsBarActionViewItem, action, options);
|
||||
}, onDidRegister.event));
|
||||
|
||||
onDidRegister.fire();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -142,9 +142,11 @@ const singlePaneChangesEditorTitleVisible = ContextKeyExpr.and(
|
||||
|
||||
/**
|
||||
* Anchor action hosting the Create Pull Request button bar ({@link ChangesActionsBar})
|
||||
* in the single-pane title bar (right side — the session actions area). The custom action
|
||||
* view item is registered for {@link Menus.TitleBarSessionMenu} via IActionViewItemService
|
||||
* in changesView.ts. The bar hides itself when its underlying menu has no actions.
|
||||
* in the single-pane editor tabs title (the editor-actions area of the docked tab bar).
|
||||
* The custom action view item is provided by the Changes editor pane
|
||||
* ({@link SessionChangesEditor.getActionViewItem}) when the Changes editor is active,
|
||||
* so the anchor is gated on the same. The bar hides itself when its underlying menu has
|
||||
* no actions.
|
||||
*/
|
||||
class ChangesHeaderActionsAction extends Action2 {
|
||||
constructor() {
|
||||
@@ -153,13 +155,11 @@ class ChangesHeaderActionsAction extends Action2 {
|
||||
title: localize2('changesView.headerActions', "Changes Actions"),
|
||||
f1: false,
|
||||
menu: {
|
||||
id: Menus.TitleBarSessionMenu,
|
||||
id: Menus.SessionsEditorTitle,
|
||||
group: 'navigation',
|
||||
order: 5,
|
||||
when: ContextKeyExpr.and(
|
||||
IsSessionsWindowContext,
|
||||
IsAuxiliaryWindowContext.toNegated(),
|
||||
SinglePaneLayoutEnabledContext,
|
||||
singlePaneChangesEditorTitle,
|
||||
SessionHasChangesContext
|
||||
)
|
||||
},
|
||||
|
||||
@@ -250,7 +250,7 @@
|
||||
|
||||
/* Compact the ChangesActionsBar buttons to 24px (2px shorter than the classic
|
||||
* 26px header buttons) so the changes-editor header stays compact without extra
|
||||
* header padding. Keyed off the bar's marker class. In the sessions title bar the
|
||||
* header padding. Keyed off the bar's marker class. In the editor tabs title the
|
||||
* 20px override below (scoped to the toolbar action-item context) wins on
|
||||
* specificity, so this 24px baseline effectively applies to the classic internal
|
||||
* changes-editor header. */
|
||||
@@ -261,8 +261,8 @@
|
||||
}
|
||||
|
||||
/* The Create Pull Request bar is rendered as a toolbar action item
|
||||
* (`.action-item.changes-actions-bar` inside a `.monaco-action-bar`) in the sessions
|
||||
* title bar (session actions area), where the classic
|
||||
* (`.action-item.changes-actions-bar` inside a `.monaco-action-bar`) in the editor
|
||||
* tabs title (the editor-actions area of the docked tab bar), where the classic
|
||||
* `.session-changes-editor-header-right` normalization does not reach. Scope these to
|
||||
* the action-item context so the classic internal changes-editor header and the aux-bar
|
||||
* Changes view are left untouched. */
|
||||
@@ -270,23 +270,49 @@
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: var(--vscode-spacing-size40);
|
||||
min-width: 0;
|
||||
/* Small breathing room so the button isn't flush against neighbouring toolbar icons. */
|
||||
margin-left: var(--vscode-spacing-size20);
|
||||
margin-right: var(--vscode-spacing-size20);
|
||||
}
|
||||
|
||||
/* Render the button bar thinner so it sits comfortably in the title bar. Overrides the
|
||||
* default 24px ChangesActionsBar button height without affecting the classic internal
|
||||
/* Normalize the button bar height so it sits comfortably in the editor tabs title. Overrides the
|
||||
* default ChangesActionsBar button height without affecting the classic internal
|
||||
* changes-editor header (which renders the bar on a plain div, not inside a
|
||||
* `.monaco-action-bar .action-item`). */
|
||||
.monaco-action-bar .action-item.changes-actions-bar .monaco-button,
|
||||
.monaco-action-bar .action-item.changes-actions-bar .monaco-button-dropdown {
|
||||
height: 20px;
|
||||
min-height: 20px;
|
||||
height: 26px;
|
||||
min-height: 26px;
|
||||
padding-top: 0;
|
||||
padding-bottom: 0;
|
||||
}
|
||||
|
||||
.monaco-action-bar .action-item.changes-actions-bar .monaco-button-dropdown {
|
||||
display: flex;
|
||||
min-width: 0;
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.monaco-action-bar .action-item.changes-actions-bar .monaco-button-dropdown > .monaco-button:not(.monaco-dropdown-button) {
|
||||
flex: 1 1 auto;
|
||||
flex-wrap: wrap;
|
||||
min-width: 0;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
.monaco-action-bar .action-item.changes-actions-bar .monaco-button-dropdown > .monaco-button-dropdown-separator,
|
||||
.monaco-action-bar .action-item.changes-actions-bar .monaco-button-dropdown > .monaco-button.monaco-dropdown-button {
|
||||
flex: 0 0 auto;
|
||||
}
|
||||
|
||||
.monaco-action-bar .action-item.changes-actions-bar .monaco-button > span:not(.codicon) {
|
||||
min-width: 0;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
/* The generic actionbar rule `.monaco-action-bar .action-item .codicon { width:
|
||||
* 16px; height: 16px }` clamps every codicon — including the button elements
|
||||
* themselves (which carry the `codicon` class), squashing the secondary icon
|
||||
@@ -294,7 +320,8 @@
|
||||
* specificity than the base rule) so the buttons size to their own content. */
|
||||
.monaco-action-bar .action-item.changes-actions-bar .codicon {
|
||||
width: auto;
|
||||
height: auto;
|
||||
height: 24px;
|
||||
flex-shrink: 0;
|
||||
color: var(--vscode-button-foreground) !important;
|
||||
}
|
||||
|
||||
|
||||
@@ -37,8 +37,11 @@ import { Menus } from '../../../browser/menus.js';
|
||||
import { IAgentWorkbenchLayoutService } from '../../../browser/workbench.js';
|
||||
import { ActiveSessionContextKeys } from '../common/changes.js';
|
||||
import { IChangesViewService } from '../common/changesViewService.js';
|
||||
import { ChangesActionsBar } from './changesView.js';
|
||||
import { ChangesActionsBar, ChangesActionsBarActionViewItem, CHANGES_HEADER_ACTIONS_ID } from './changesView.js';
|
||||
import { SessionChangesEditorInput } from './sessionChangesEditorInput.js';
|
||||
import { IAction } from '../../../../base/common/actions.js';
|
||||
import { IBaseActionViewItemOptions } from '../../../../base/browser/ui/actionbar/actionViewItems.js';
|
||||
import { IActionViewItem } from '../../../../base/browser/ui/actionbar/actionbar.js';
|
||||
|
||||
const HEADER_HEIGHT = 35;
|
||||
|
||||
@@ -210,6 +213,17 @@ export class SessionChangesEditor extends AbstractEditorWithViewState<IMultiDiff
|
||||
return { instantiationService: this._scopedInstantiationService };
|
||||
}
|
||||
|
||||
/**
|
||||
* In single-pane, render the Create Pull Request button bar ({@link ChangesActionsBar})
|
||||
* as the editor tabs title anchor action ({@link CHANGES_HEADER_ACTIONS_ID}).
|
||||
*/
|
||||
override getActionViewItem(action: IAction, options: IBaseActionViewItemOptions): IActionViewItem | undefined {
|
||||
if (this._singlePane && action.id === CHANGES_HEADER_ACTIONS_ID) {
|
||||
return this.instantiationService.createInstance(ChangesActionsBarActionViewItem, action, options);
|
||||
}
|
||||
return super.getActionViewItem(action, options);
|
||||
}
|
||||
|
||||
override async setInput(input: SessionChangesEditorInput, options: IMultiDiffEditorOptions | undefined, context: IEditorOpenContext, token: CancellationToken): Promise<void> {
|
||||
await super.setInput(input, options, context, token);
|
||||
const viewModel = await input.getViewModel();
|
||||
|
||||
@@ -10,7 +10,7 @@ import { ensureNoDisposablesAreLeakedInTestSuite } from '../../../../../base/tes
|
||||
import { isIMenuItem, MenuId, MenuRegistry } from '../../../../../platform/actions/common/actions.js';
|
||||
import { isICommandActionToggleInfo } from '../../../../../platform/action/common/action.js';
|
||||
import { EditorContextKeys } from '../../../../../editor/common/editorContextKeys.js';
|
||||
import { ActiveEditorContext, AuxiliaryBarVisibleContext, IsSessionsWindowContext, MainEditorAreaVisibleContext } from '../../../../../workbench/common/contextkeys.js';
|
||||
import { ActiveEditorContext, AuxiliaryBarVisibleContext, IsAuxiliaryWindowContext, IsSessionsWindowContext, IsTopRightEditorGroupContext, MainEditorAreaVisibleContext } from '../../../../../workbench/common/contextkeys.js';
|
||||
import { Menus } from '../../../../browser/menus.js';
|
||||
import { ChangesContextKeys } from '../../common/changes.js';
|
||||
import { SessionHasChangesContext, SinglePaneLayoutEnabledContext } from '../../../../common/contextkeys.js';
|
||||
@@ -184,24 +184,30 @@ suite('Changes View Actions', () => {
|
||||
}]);
|
||||
});
|
||||
|
||||
test('Create Pull Request anchor is contributed to the title bar session menu', () => {
|
||||
const item = MenuRegistry.getMenuItems(Menus.TitleBarSessionMenu)
|
||||
test('Create Pull Request anchor is contributed to the editor tabs title menu', () => {
|
||||
const item = MenuRegistry.getMenuItems(Menus.SessionsEditorTitle)
|
||||
.filter(isIMenuItem)
|
||||
.find(item => item.command.id === CHANGES_HEADER_ACTIONS_ID);
|
||||
|
||||
assert.ok(item, 'expected the changes header actions anchor on the title bar session menu');
|
||||
assert.ok(item, 'expected the changes header actions anchor on the editor tabs title menu');
|
||||
const when = item.when?.serialize() ?? '';
|
||||
assert.deepStrictEqual({
|
||||
group: item.group,
|
||||
order: item.order,
|
||||
hasSessionsWindowGate: when.includes(IsSessionsWindowContext.key),
|
||||
hasActiveEditorGate: when.includes(ActiveEditorContext.key) && when.includes(SessionChangesEditor.ID),
|
||||
hasSinglePaneConfigGate: when.includes(SinglePaneLayoutEnabledContext.key),
|
||||
hasAuxiliaryWindowGate: when.includes(IsAuxiliaryWindowContext.key),
|
||||
hasTopRightEditorGroupGate: when.includes(IsTopRightEditorGroupContext.key),
|
||||
hasChangesGate: when.includes(SessionHasChangesContext.key),
|
||||
}, {
|
||||
group: 'navigation',
|
||||
order: 5,
|
||||
hasSessionsWindowGate: true,
|
||||
hasActiveEditorGate: true,
|
||||
hasSinglePaneConfigGate: true,
|
||||
hasAuxiliaryWindowGate: true,
|
||||
hasTopRightEditorGroupGate: true,
|
||||
hasChangesGate: true,
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user