feat: Embedded Copilot CLI tool window#7
Merged
sailro merged 7 commits intosailro:mainfrom Apr 12, 2026
Merged
Conversation
Add a dockable tool window (Tools > Copilot CLI Window) that hosts the Copilot CLI inside Visual Studio using WebView2 + xterm.js + ConPTY. New files: - ConPty.cs: P/Invoke wrapper for Windows pseudo-console APIs - TerminalProcess.cs: manages CLI process via ConPTY with async I/O - TerminalSessionService.cs: package-level session lifecycle manager - TerminalToolWindow.cs: VS ToolWindowPane shell - TerminalToolWindowControl.cs: WPF control with WebView2 + xterm.js - Resources/Terminal/: HTML, JS, and bundled xterm.js assets Modified files: - CopilotCliIdePackage.cs: wire up tool window, session service, command - CopilotCliIdePackage.vsct: add Copilot CLI Window menu command - VsServices.cs: expose TerminalSessionService singleton - CopilotCliIde.csproj: add WebView2 NuGet, WPF refs, terminal resources - Directory.Packages.props: add WebView2 version The existing 'Launch Copilot CLI' external terminal remains available. The /ide bridge connection is completely unaffected. Refs: sailro#6 Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Defer ConPTY process start until xterm.js reports actual dimensions via the first resize message (fixes text overlap/misalignment) - Pass cols/rows from xterm.js through to ConPty.Create instead of hardcoded 120x40 - Use TryGetWebMessageAsString instead of WebMessageAsJson to correctly handle JS postMessage(JSON.stringify(...)) string messages - Add detailed diagnostic logging to WebView2 initialization Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Accumulate pipe reads in a StringBuilder and flush every 16ms (~60fps) instead of firing a separate SwitchToMainThreadAsync + PostWebMessageAsJson for each read. This eliminates keystroke lag caused by echo latency. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Override PreProcessMessage in TerminalToolWindow to prevent VS from intercepting arrow keys, Tab, Escape, Enter, Backspace, Delete, Home, End, PgUp, and PgDn — letting them reach WebView2 and xterm.js so interactive prompts (e.g., multi-choice selection) work correctly. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Remove GotFocus handler that caused infinite focus loop (_webView.Focus() triggered bubbling GotFocus, which called _webView.Focus() again — locking the UI thread) - Keep IsVisibleChanged handler for auto-focus when window appears - Make WebView2 init lazy (placeholder TextBlock in constructor, WebView2 created in DeferredInitialize at ApplicationIdle priority) - Add Transient=true to ProvideToolWindow to avoid forced auto-restore - Add dispose/initializing guards to prevent races during startup - Replace JoinableTaskFactory.RunAsync with Dispatcher.BeginInvoke for terminal output dispatch (lighter UI thread marshaling) - Move JSON serialization off UI thread for output messages - Remove temporary diagnostic file logging (DiagLog) Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
- Replace GotFocus with PreviewMouseDown for focus handling. GotFocus + WebView2 causes infinite loops because: (a) IsKeyboardFocusWithin is always False for hosted Chromium HWNDs (b) term.focus() triggers focus-in escape sequences back to C# - PreviewMouseDown fires only on real user clicks — no loop possible. Calls both _webView.Focus() (WPF) and term.focus() (Chromium) to resync focus state after VS layout transitions. - Re-attach to session service in OnLoaded when WebView2 is already initialized (handles Unloaded/Loaded cycle during debug layout switch). Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
sailro
reviewed
Apr 12, 2026
sailro
reviewed
Apr 12, 2026
Owner
|
Hey thank you @bommerts for this nice contribution !. I added two comments after quick testing. But yes this is definitively useful. Thanks ! |
…orkspaceFolder - Make GetWorkspaceFolder() internal static on CopilotCliIdePackage as single source of truth (removes duplicate from TerminalToolWindowControl) - RestartSession() accepts optional workingDirectory parameter - OnSolutionOpened passes fresh workspace folder to RestartSession - StopSession clears _workingDirectory to prevent stale path reuse Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Contributor
Author
Appreciate it! I absolutely love using GitHub Copilot CLI + the VS ide + what you have done with this extension. I hope this helps. |
sailro
added a commit
that referenced
this pull request
Apr 12, 2026
Add embedded terminal subsystem to README usage section, populate CHANGELOG [Unreleased] with full feature breakdown, and add comprehensive terminal architecture section to copilot-instructions.md covering ConPTY, WebView2, xterm.js lifecycle, and threading patterns. Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
9 tasks
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds a dockable tool window (Tools → Copilot CLI Window) that hosts the Copilot CLI inside Visual Studio using WebView2 + xterm.js + Windows ConPTY.
Closes #6
What's new
New files
Modified files
Testing
Screenshot
Will add screenshot after review feedback
This is a draft — happy to adjust the approach based on your feedback!