Skip to content

Commit

Permalink
Merge pull request #182699 from microsoft/roblou/future-toad
Browse files Browse the repository at this point in the history
Chat fixes
  • Loading branch information
roblourens authored May 17, 2023
2 parents bfc0808 + dbb3dd4 commit 011ae39
Show file tree
Hide file tree
Showing 3 changed files with 58 additions and 49 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
import { Codicon } from 'vs/base/common/codicons';
import { KeyCode, KeyMod } from 'vs/base/common/keyCodes';
import { ICodeEditor, isCodeEditor, isDiffEditor } from 'vs/editor/browser/editorBrowser';
import { EditorAction2, ServicesAccessor } from 'vs/editor/browser/editorExtensions';
import { ServicesAccessor } from 'vs/editor/browser/editorExtensions';
import { IBulkEditService, ResourceTextEdit } from 'vs/editor/browser/services/bulkEditService';
import { ICodeEditorService } from 'vs/editor/browser/services/codeEditorService';
import { Range } from 'vs/editor/common/core/range';
Expand Down Expand Up @@ -42,6 +42,28 @@ export function isCodeBlockActionContext(thing: unknown): thing is IChatCodeBloc
return typeof thing === 'object' && thing !== null && 'code' in thing && 'element' in thing;
}

abstract class ChatCodeBlockAction extends Action2 {
run(accessor: ServicesAccessor, ...args: any[]) {
let context = args[0];
if (!isCodeBlockActionContext(context)) {
const codeEditorService = accessor.get(ICodeEditorService);
const editor = codeEditorService.getFocusedCodeEditor() || codeEditorService.getActiveCodeEditor();
if (!editor) {
return;
}

context = getContextFromEditor(editor, accessor);
if (!isCodeBlockActionContext(context)) {
return;
}
}

return this.runWithContext(accessor, context);
}

abstract runWithContext(accessor: ServicesAccessor, context: IChatCodeBlockActionContext): any;
}

export function registerChatCodeBlockActions() {
registerAction2(class CopyCodeBlockAction extends Action2 {
constructor() {
Expand Down Expand Up @@ -135,7 +157,7 @@ export function registerChatCodeBlockActions() {
return false;
});

registerAction2(class InsertCodeBlockAction extends EditorAction2 {
registerAction2(class InsertCodeBlockAction extends ChatCodeBlockAction {
constructor() {
super({
id: 'workbench.action.chat.insertCodeBlock',
Expand All @@ -153,15 +175,7 @@ export function registerChatCodeBlockActions() {
});
}

override async runEditorCommand(accessor: ServicesAccessor, editor: ICodeEditor, ...args: any[]) {
let context = args[0];
if (!isCodeBlockActionContext(context)) {
context = getContextFromEditor(editor, accessor);
if (!isCodeBlockActionContext(context)) {
return;
}
}

override async runWithContext(accessor: ServicesAccessor, context: IChatCodeBlockActionContext) {
const editorService = accessor.get(IEditorService);
const textFileService = accessor.get(ITextFileService);

Expand Down Expand Up @@ -220,12 +234,15 @@ export function registerChatCodeBlockActions() {
private async handleTextEditor(accessor: ServicesAccessor, codeEditor: ICodeEditor, activeModel: ITextModel, context: IChatCodeBlockActionContext) {
this.notifyUserAction(accessor, context);
const bulkEditService = accessor.get(IBulkEditService);
const codeEditorService = accessor.get(ICodeEditorService);

const activeSelection = codeEditor.getSelection() ?? new Range(activeModel.getLineCount(), 1, activeModel.getLineCount(), 1);
await bulkEditService.apply([new ResourceTextEdit(activeModel.uri, {
range: activeSelection,
text: context.code,
})]);

codeEditorService.listCodeEditors().find(editor => editor.getModel()?.uri.toString() === activeModel.uri.toString())?.focus();
}

private notifyUserAction(accessor: ServicesAccessor, context: IChatCodeBlockActionContext) {
Expand All @@ -243,7 +260,7 @@ export function registerChatCodeBlockActions() {

});

registerAction2(class InsertIntoNewFileAction extends EditorAction2 {
registerAction2(class InsertIntoNewFileAction extends ChatCodeBlockAction {
constructor() {
super({
id: 'workbench.action.chat.insertIntoNewFile',
Expand All @@ -262,15 +279,7 @@ export function registerChatCodeBlockActions() {
});
}

override async runEditorCommand(accessor: ServicesAccessor, editor: ICodeEditor, ...args: any[]) {
let context = args[0];
if (!isCodeBlockActionContext(context)) {
context = getContextFromEditor(editor, accessor);
if (!isCodeBlockActionContext(context)) {
return;
}
}

override async runWithContext(accessor: ServicesAccessor, context: IChatCodeBlockActionContext) {
const editorService = accessor.get(IEditorService);
const chatService = accessor.get(IChatService);
editorService.openEditor(<IUntitledTextResourceEditorInput>{ contents: context.code, languageId: context.languageId, resource: undefined });
Expand All @@ -288,7 +297,7 @@ export function registerChatCodeBlockActions() {
}
});

registerAction2(class RunInTerminalAction extends EditorAction2 {
registerAction2(class RunInTerminalAction extends ChatCodeBlockAction {
constructor() {
super({
id: 'workbench.action.chat.runInTerminal',
Expand All @@ -314,15 +323,7 @@ export function registerChatCodeBlockActions() {
});
}

override async runEditorCommand(accessor: ServicesAccessor, editor: ICodeEditor, ...args: any[]) {
let context = args[0];
if (!isCodeBlockActionContext(context)) {
context = getContextFromEditor(editor, accessor);
if (!isCodeBlockActionContext(context)) {
return;
}
}

override async runWithContext(accessor: ServicesAccessor, context: IChatCodeBlockActionContext) {
const chatService = accessor.get(IChatService);
const terminalService = accessor.get(ITerminalService);
const editorService = accessor.get(IEditorService);
Expand Down
43 changes: 25 additions & 18 deletions src/vs/workbench/contrib/chat/browser/chatViewPane.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import { IContextMenuService } from 'vs/platform/contextview/browser/contextView
import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation';
import { ServiceCollection } from 'vs/platform/instantiation/common/serviceCollection';
import { IKeybindingService } from 'vs/platform/keybinding/common/keybinding';
import { ILogService } from 'vs/platform/log/common/log';
import { IOpenerService } from 'vs/platform/opener/common/opener';
import { IStorageService, StorageScope, StorageTarget } from 'vs/platform/storage/common/storage';
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
Expand Down Expand Up @@ -58,6 +59,7 @@ export class ChatViewPane extends ViewPane implements IChatViewPane {
@ITelemetryService telemetryService: ITelemetryService,
@IStorageService private readonly storageService: IStorageService,
@IChatService private readonly chatService: IChatService,
@ILogService private readonly logService: ILogService,
) {
super(options, keybindingService, contextMenuService, configurationService, contextKeyService, viewDescriptorService, instantiationService, openerService, themeService, telemetryService);

Expand All @@ -79,26 +81,31 @@ export class ChatViewPane extends ViewPane implements IChatViewPane {
}

protected override renderBody(parent: HTMLElement): void {
super.renderBody(parent);

const scopedInstantiationService = this.instantiationService.createChild(new ServiceCollection([IContextKeyService, this.scopedContextKeyService]));

this._widget = this._register(scopedInstantiationService.createInstance(
ChatWidget,
{ viewId: this.id },
{
listForeground: SIDE_BAR_FOREGROUND,
listBackground: this.getBackgroundColor(),
inputEditorBackground: this.getBackgroundColor(),
resultEditorBackground: editorBackground
try {
super.renderBody(parent);

const scopedInstantiationService = this.instantiationService.createChild(new ServiceCollection([IContextKeyService, this.scopedContextKeyService]));

this._widget = this._register(scopedInstantiationService.createInstance(
ChatWidget,
{ viewId: this.id },
{
listForeground: SIDE_BAR_FOREGROUND,
listBackground: this.getBackgroundColor(),
inputEditorBackground: this.getBackgroundColor(),
resultEditorBackground: editorBackground
}));
this._register(this.onDidChangeBodyVisibility(visible => {
this._widget.setVisible(visible);
}));
this._register(this.onDidChangeBodyVisibility(visible => {
this._widget.setVisible(visible);
}));
this._widget.render(parent);
this._widget.render(parent);

const initialModel = this.viewState.sessionId ? this.chatService.getOrRestoreSession(this.viewState.sessionId) : undefined;
this.updateModel(initialModel);
const initialModel = this.viewState.sessionId ? this.chatService.getOrRestoreSession(this.viewState.sessionId) : undefined;
this.updateModel(initialModel);
} catch (e) {
this.logService.error(e);
throw e;
}
}

acceptInput(query?: string): void {
Expand Down
1 change: 1 addition & 0 deletions src/vs/workbench/contrib/chat/browser/chatWidget.ts
Original file line number Diff line number Diff line change
Expand Up @@ -260,6 +260,7 @@ export class ChatWidget extends Disposable implements IChatWidget {
[this.renderer],
{
identityProvider: { getId: (e: InteractiveTreeItem) => e.id },
horizontalScrolling: false,
supportDynamicHeights: true,
hideTwistiesOfChildlessElements: true,
accessibilityProvider: new ChatAccessibilityProvider(),
Expand Down

0 comments on commit 011ae39

Please sign in to comment.