### Clipboard binary data with PNG format Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Shows how to set and get binary clipboard data using the PNG format. The example assumes a helper GetClipboardReadyPngBytes() and a consumer UsePngBytes(). ```csharp byte[] pngBytes = GetClipboardReadyPngBytes(); Terminal.Clipboard.TrySetData(TerminalClipboardFormats.Png, pngBytes); if (Terminal.Clipboard.TryGetFormats(out var formats) && formats.Contains(TerminalClipboardFormats.Png) && Terminal.Clipboard.TryGetData(TerminalClipboardFormats.Png, out var pastedPng)) { UsePngBytes(pastedPng); } ``` -------------------------------- ### Grapheme-cluster aware width example Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Shows that emoji/ZWJ/combining sequences are treated as a single unit; the example returns 2 for the file cabinet emoji. ```csharp var emojiCells = TerminalTextUtility.GetWidth("\U0001F5C3\uFE0F".AsSpan()); // 🗃️ => 2 ``` -------------------------------- ### TerminalTextUtility.GetWordStart Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Returns the index of the start of the word containing the given index. ```APIDOC ## TerminalTextUtility.GetWordStart ### Description Returns the index of the start of the word containing the given index. ### Method GetWordStart ### Signature `public static int GetWordStart(ReadOnlySpan text, int index)` ### Parameters - **text** (ReadOnlySpan) - Required - The input string. - **index** (int) - Required - The character index within the text. ### Returns - **int** - The index of the start of the word. ### Example ```csharp var wordStart = TerminalTextUtility.GetWordStart("hello_world".AsSpan(), index: 8); ``` ``` -------------------------------- ### Set and get clipboard text Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Sets the clipboard text to "Hello from XenoAtom.Terminal" and then reads it back. ```csharp Terminal.Clipboard.Text = "Hello from XenoAtom.Terminal"; var text = Terminal.Clipboard.Text; ``` -------------------------------- ### Quick start: WriteLine and WriteMarkup Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/readme.md Shows the basic usage of XenoAtom.Terminal: writing a plain line with Terminal.WriteLine and rendering markup with Terminal.WriteMarkup. The markup uses [bold green] and [gray] tags to style text. ```csharp using XenoAtom.Terminal; Terminal.WriteLine("Hello"); Terminal.WriteMarkup("[bold green]Hello[/] [gray]world[/]!"); ``` -------------------------------- ### Testing with InMemoryTerminalBackend Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Initializes the terminal with an in-memory backend, starts input without mouse events, reads a line with echo disabled, injects text and Enter key events, and retrieves captured output. ```csharp using XenoAtom.Terminal.Backends; var backend = new InMemoryTerminalBackend(); Terminal.Initialize(backend); Terminal.StartInput(new TerminalInputOptions { EnableMouseEvents = false }); var task = Terminal.ReadLineAsync(new TerminalReadLineOptions { Echo = false }).AsTask(); backend.PushEvent(new TerminalTextEvent { Text = "abc" }); backend.PushEvent(new TerminalKeyEvent { Key = TerminalKey.Enter }); var line = await task; var outText = backend.GetOutText(); ``` -------------------------------- ### Terminal.StartInput Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Starts the input processing loop for the terminal. Required when TerminalOptions.ImplicitStartInput is disabled. ```APIDOC ## Terminal.StartInput ### Description Starts the input processing loop for the terminal. Required when TerminalOptions.ImplicitStartInput is disabled. ### Method StartInput ### Signature `public void StartInput()` ### Remarks Call this before calling ReadLineAsync if implicit start is disabled. ``` -------------------------------- ### Terminal.WindowWidth / WindowHeight / BufferWidth / BufferHeight / LargestWindowWidth / LargestWindowHeight Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Gets or sets window and buffer sizes, mirroring System.Console. ```APIDOC ## Terminal.WindowWidth / WindowHeight / BufferWidth / BufferHeight / LargestWindowWidth / LargestWindowHeight ### Description Properties to get or set the terminal window and buffer dimensions. ### Properties - `Terminal.WindowWidth` (int) - Gets or sets the window width. - `Terminal.WindowHeight` (int) - Gets or sets the window height. - `Terminal.BufferWidth` (int) - Gets or sets the buffer width. - `Terminal.BufferHeight` (int) - Gets or sets the buffer height. - `Terminal.LargestWindowWidth` (int) - Gets the largest possible window width. - `Terminal.LargestWindowHeight` (int) - Gets the largest possible window height. ``` -------------------------------- ### ReadKey / KeyAvailable (Console-like) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Starts input and checks for available keys, then reads a key with interception and converts it to ConsoleKeyInfo. This is a Console-like alternative to the event stream. ```csharp Terminal.StartInput(); if (Terminal.KeyAvailable) { var key = Terminal.ReadKey(intercept: true); var consoleKeyInfo = key.ToConsoleKeyInfo(); } ``` -------------------------------- ### Async clipboard helpers with timeout Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Shows async clipboard operations with a 500 ms timeout: getting text, setting text, and getting binary data. ```csharp var text = await Terminal.Clipboard.GetTextAsync(timeoutMs: 500); await Terminal.Clipboard.TrySetTextAsync("Hello".AsMemory(), timeoutMs: 500); var image = await Terminal.Clipboard.GetDataAsync(TerminalClipboardFormats.Png, timeoutMs: 500); ``` -------------------------------- ### Terminal.Title Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Sets or gets the terminal window title. ```APIDOC ## Terminal.Title ### Description Sets or gets the terminal window title. ### Property `Terminal.Title` (string) ### Example ```csharp Terminal.Title = "My App"; ``` ``` -------------------------------- ### Terminal.Clipboard.Text Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Gets or sets clipboard text. ```APIDOC ## Terminal.Clipboard.Text ### Description Gets or sets the clipboard text. ### Property `Terminal.Clipboard.Text` (string) - Gets or sets the clipboard text. ### Example ```csharp Terminal.Clipboard.Text = "Hello from XenoAtom.Terminal"; var text = Terminal.Clipboard.Text; ``` ``` -------------------------------- ### Parsing gestures with TerminalKeyGesture Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md TerminalKeyGesture can format and parse gestures. This example parses "CTRL+R" and prints it. ```csharp var gesture = TerminalKeyGesture.Parse("CTRL+R"); Console.WriteLine(gesture); // CTRL+R ``` -------------------------------- ### Basic usage of Terminal.ReadLineAsync Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Starts input and reads a line with echo enabled. Requires interactive output and cursor positioning for the in-terminal editor; otherwise falls back to a simple non-editing mode. ```csharp Terminal.StartInput(); var line = await Terminal.ReadLineAsync(new TerminalReadLineOptions { Echo = true }); ``` -------------------------------- ### Custom key bindings (KeyBindings) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Customize key bindings via TerminalReadLineKeyBindings. This example disables the Left arrow key. ```csharp var bindings = TerminalReadLineKeyBindings.CreateDefault(); bindings.Bind(TerminalKey.Left, TerminalModifiers.None, TerminalReadLineCommand.Ignore); // disable Left var options = new TerminalReadLineOptions { Echo = true, KeyBindings = bindings, }; ``` -------------------------------- ### Initialize with an in-memory backend for tests Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md For deterministic tests or headless scenarios, pass an InMemoryTerminalBackend to Terminal.Initialize. Requires the XenoAtom.Terminal.Backends namespace. ```csharp using XenoAtom.Terminal.Backends; var backend = new InMemoryTerminalBackend(); Terminal.Initialize(backend); ``` -------------------------------- ### Build and test commands Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/AGENTS.md Commands to build and test the project from the repository root. Run `cd src` first, then `dotnet build -c Release` and `dotnet test -c Release`. All tests must pass before submitting. ```sh cd src dotnet build -c Release dotnet test -c Release ``` -------------------------------- ### Prompt with markup (PromptMarkup) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Uses PromptMarkup to render a styled prompt with a counter and cyan '>' symbol. The prompt is a function that returns markup text. ```csharp var counter = 1; var options = new TerminalReadLineOptions { Echo = true, PromptMarkup = () => $"[gray]{counter++}[/] [cyan]>[/] ", }; var line = await Terminal.ReadLineAsync(options); ``` -------------------------------- ### Open a terminal session for deterministic cleanup Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Use Terminal.Open to create a session that restores input modes and stops the input loop when disposed. The using statement ensures cleanup. ```csharp using var session = Terminal.Open(options: new TerminalOptions { PreferUtf8Output = true }); ``` -------------------------------- ### Terminal.UseCursorPosition() / SetCursorPosition() Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Scoped cursor position restore and direct position setting. ```APIDOC ## Terminal.UseCursorPosition() / SetCursorPosition() ### Description `UseCursorPosition()` returns a disposable that restores the cursor position when disposed. `SetCursorPosition` sets the cursor position directly. ### Methods - `IDisposable UseCursorPosition()` - Returns a scope that restores the cursor position on dispose. - `void SetCursorPosition(int left, int top)` - Sets the cursor position. ### Example ```csharp using var _pos = Terminal.UseCursorPosition(); Terminal.SetCursorPosition(10, 5); Terminal.WriteLine("Temporarily moved"); ``` ``` -------------------------------- ### Terminal.WriteMarkup(string) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Renders markup text to ANSI using the XenoAtom.Ansi.AnsiMarkup library. ```APIDOC ## Terminal.WriteMarkup(string) ### Description Renders markup text to ANSI using the XenoAtom.Ansi.AnsiMarkup library. ### Method WriteMarkup ### Parameters - **markup** (string) - Required - The markup string to render. ### Usage ```csharp Terminal.WriteMarkup("[bold yellow]Warning:[/] something happened"); ``` ``` -------------------------------- ### Explicit terminal initialization with TerminalOptions Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Initialize the terminal explicitly with options controlling UTF-8 output, 7-bit C1 control codes, ANSI forcing, and strict mode. The first use initializes lazily if not called. ```csharp Terminal.Initialize(options: new TerminalOptions { PreferUtf8Output = true, Prefer7BitC1 = true, ForceAnsi = false, StrictMode = false, }); ``` -------------------------------- ### TerminalTextUtility width and word boundary methods Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Use these methods for layout, clipping, and hit testing. Width and hit testing are grapheme-cluster aware. ```csharp var cells = TerminalTextUtility.GetWidth("A😃中".AsSpan()); TerminalTextUtility.TryGetIndexAtCell("hello world".AsSpan(), cellOffset: 6, out var index); var wordStart = TerminalTextUtility.GetWordStart("hello_world".AsSpan(), index: 8); var wordEnd = TerminalTextUtility.GetWordEnd("hello_world".AsSpan(), index: 8); ``` -------------------------------- ### Render markup with Terminal.WriteMarkup Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Use Terminal.WriteMarkup to render markup strings provided by XenoAtom.Ansi.AnsiMarkup into ANSI output. ```csharp Terminal.WriteMarkup("[bold yellow]Warning:[/] something happened"); ``` -------------------------------- ### Inspect detected terminal capabilities Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Write a line that reports ANSI support, color level, mouse support, and preferred graphics protocol. Capabilities vary by host; some APIs are best-effort. ```csharp Terminal.WriteLine($"Ansi={Terminal.Capabilities.AnsiEnabled}, Color={Terminal.Capabilities.ColorLevel}, Mouse={Terminal.Capabilities.SupportsMouse}, Graphics={Terminal.Graphics.Capabilities.PreferredProtocol}"); ``` -------------------------------- ### Tab completion with CompletionHandler Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Provides tab completion candidates. Press Tab repeatedly to cycle through them until another key is typed. The handler returns candidates and replacement range. ```csharp var options = new TerminalReadLineOptions { Echo = true, CompletionHandler = static (text, cursor, selectionStart, selectionLength) => { _ = selectionStart; _ = selectionLength; // Return candidates, then press Tab repeatedly to cycle through them until you type another key. return new TerminalReadLineCompletion { Handled = true, Candidates = ["help", "hello", "helium"], ReplaceStart = 0, ReplaceLength = cursor, }; }, }; ``` -------------------------------- ### Terminal.Clipboard.TrySetData / TryGetFormats / TryGetData Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Low-level clipboard access for named binary formats. ```APIDOC ## Terminal.Clipboard.TrySetData / TryGetFormats / TryGetData ### Description Provides low-level clipboard access for named binary formats (e.g., PNG). ### Methods - `bool TrySetData(string format, byte[] data)` - Attempts to set clipboard data for the given format. - `bool TryGetFormats(out string[] formats)` - Gets the list of available clipboard formats. - `bool TryGetData(string format, out byte[] data)` - Attempts to get clipboard data for the given format. ### Example ```csharp byte[] pngBytes = GetClipboardReadyPngBytes(); Terminal.Clipboard.TrySetData(TerminalClipboardFormats.Png, pngBytes); if (Terminal.Clipboard.TryGetFormats(out var formats) && formats.Contains(TerminalClipboardFormats.Png) && Terminal.Clipboard.TryGetData(TerminalClipboardFormats.Png, out var pastedPng)) { UsePngBytes(pastedPng); } ``` ``` -------------------------------- ### Terminal.ForegroundColor / BackgroundColor / Decorations Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Sets the foreground color, background color, and text decorations using XenoAtom.Ansi types. ```APIDOC ## Terminal.ForegroundColor / BackgroundColor / Decorations ### Description Sets the foreground color, background color, and text decorations. Colors support implicit conversion from `ConsoleColor`. ### Properties - `Terminal.ForegroundColor` (XenoAtom.Ansi.AnsiColor) - Sets the foreground color. - `Terminal.BackgroundColor` (XenoAtom.Ansi.AnsiColor) - Sets the background color. - `Terminal.Decorations` (XenoAtom.Ansi.AnsiDecorations) - Sets text decorations (e.g., Bold). ### Example ```csharp Terminal.ForegroundColor = (XenoAtom.Ansi.AnsiColor)ConsoleColor.Green; Terminal.BackgroundColor = XenoAtom.Ansi.AnsiColor.Default; Terminal.Decorations = XenoAtom.Ansi.AnsiDecorations.Bold; ``` ``` -------------------------------- ### Write Sixel stream with fixed RGB332 palette Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Uses the fixed RGB332 palette and disables dithering for high-throughput Sixel streams. Faster than adaptive quantization but with lower color fidelity. ```csharp await TerminalGraphics.WriteImageAsync( frameSource, new TerminalImageWriteOptions { Protocol = TerminalGraphicsProtocol.Sixel, SixelOptions = new TerminalSixelEncoderOptions { PaletteMode = TerminalSixelPaletteMode.FixedRgb332, EnableDithering = false, }, }); ``` -------------------------------- ### Terminal.Clipboard.GetTextAsync / TrySetTextAsync / GetDataAsync Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Asynchronous clipboard helpers with timeout and cancellation support. ```APIDOC ## Terminal.Clipboard.GetTextAsync / TrySetTextAsync / GetDataAsync ### Description Asynchronous clipboard operations with timeout and cancellation support. ### Methods - `Task GetTextAsync(int timeoutMs = ...)` - Gets clipboard text asynchronously. - `Task TrySetTextAsync(ReadOnlyMemory text, int timeoutMs = ...)` - Sets clipboard text asynchronously. - `Task GetDataAsync(string format, int timeoutMs = ...)` - Gets clipboard data for a format asynchronously. ### Example ```csharp var text = await Terminal.Clipboard.GetTextAsync(timeoutMs: 500); await Terminal.Clipboard.TrySetTextAsync("Hello".AsMemory(), timeoutMs: 500); var image = await Terminal.Clipboard.GetDataAsync(TerminalClipboardFormats.Png, timeoutMs: 500); ``` ``` -------------------------------- ### Terminal.EnableMouseInput Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Enables mouse input reporting for the terminal. ```APIDOC ## Terminal.EnableMouseInput ### Description Enables mouse input reporting for the terminal. ### Method EnableMouseInput ### Signature `public IDisposable EnableMouseInput(...)` ### Remarks Wrap usage in a using statement to ensure disposal. Input must be running (StartInput) for mouse events to be received. ``` -------------------------------- ### Register custom markup tokens and use them with WriteMarkup Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Register custom markup styles (e.g., 'primary' and 'danger') using Terminal.SetMarkupStyle, then use them in WriteMarkup. The underlying dictionary is available via Terminal.MarkupStyles; if mutated in-place, call Terminal.NotifyMarkupStylesChanged() to rebuild cached renderers. ```csharp Terminal.SetMarkupStyle("primary", AnsiStyle.Default with { Foreground = (AnsiColor)ConsoleColor.Cyan, Decorations = AnsiDecorations.Bold }); Terminal.SetMarkupStyle("danger", AnsiStyle.Default with { Foreground = (AnsiColor)ConsoleColor.Red, Decorations = AnsiDecorations.Bold }); Terminal.WriteMarkup("[primary]Hello[/] [danger]world[/]!"); ``` -------------------------------- ### Terminal.MarkupStyles / TerminalInstance.MarkupStyles Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Provides access to the underlying markup style dictionary for sharing with higher-level libraries. ```APIDOC ## Terminal.MarkupStyles / TerminalInstance.MarkupStyles ### Description Provides access to the underlying markup style dictionary for sharing with higher-level libraries. ### Method Property access ### Usage Access the dictionary to read or mutate styles. If mutated in-place, call Terminal.NotifyMarkupStylesChanged() to rebuild cached markup renderers. ``` -------------------------------- ### Terminal.Cursor.Visible / Position / Style Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Controls cursor visibility, position, and style. ```APIDOC ## Terminal.Cursor.Visible / Position / Style ### Description Controls the cursor's visibility, position, and style. ### Properties - `Terminal.Cursor.Visible` (bool) - Sets whether the cursor is visible. - `Terminal.Cursor.Position` (TerminalPosition) - Sets the cursor position (0-based). - `Terminal.Cursor.Style` (XenoAtom.Ansi.AnsiCursorStyle) - Sets the cursor style (e.g., Bar). ### Example ```csharp Terminal.Cursor.Visible = false; Terminal.Cursor.Position = new TerminalPosition(0, 0); Terminal.Cursor.Style = XenoAtom.Ansi.AnsiCursorStyle.Bar; Terminal.WriteLine("Top-left"); Terminal.Cursor.Visible = true; ``` ``` -------------------------------- ### Set terminal title Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Sets the terminal window title to "My App". ```csharp Terminal.Title = "My App"; ``` -------------------------------- ### Mouse editing (opt-in) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Enables mouse reporting and mouse editing. Requires EnableMouseInput with Drag mode; otherwise mouse events are not received. ```csharp using var _mouse = Terminal.EnableMouseInput(TerminalMouseMode.Drag); var line = await Terminal.ReadLineAsync(new TerminalReadLineOptions { EnableMouseEditing = true }); ``` -------------------------------- ### Write an image with XenoAtom.Terminal.Graphics Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Writes an image from a file using TerminalGraphics.WriteImageAsync with cell size, reserved area, and fallback text. Requires referencing the XenoAtom.Terminal.Graphics package. ```csharp using XenoAtom.Terminal.Graphics; await TerminalGraphics.WriteImageAsync( TerminalImageSource.FromFile("logo.png"), new TerminalImageWriteOptions { CellSize = new TerminalImageSize(24, 12), ReserveCellArea = true, FallbackText = "[logo]\n", }); ``` -------------------------------- ### Detect graphics capabilities with Terminal.Graphics.Capabilities Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Retrieves the preferred graphics protocol and support state, then prints diagnostics. Useful for validating terminal graphics support before writing images. ```csharp var capabilities = Terminal.Graphics.Capabilities; Terminal.WriteLine($"Graphics={capabilities.PreferredProtocol}, State={capabilities.SupportState}"); foreach (var diagnostic in capabilities.Diagnostics) { Terminal.WriteLine($"- {diagnostic}"); } ``` -------------------------------- ### Write ANSI-styled output with Terminal.WriteAtomic and AnsiWriter Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Use Terminal.WriteAtomic with an AnsiWriter to apply foreground color, write a timestamp, reset style, and write a message. This ensures atomic output for styling transitions. ```csharp Terminal.WriteAtomic(w => { w.Foreground(ConsoleColor.DarkGray); w.Write("["); w.Write(DateTimeOffset.UtcNow.ToString("HH:mm:ss.fff")); w.Write("] "); w.ResetStyle(); w.Write("message\n"); }); ``` -------------------------------- ### Terminal.SetMarkupStyle(string, AnsiStyle) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Registers a custom markup token style for use with WriteMarkup. ```APIDOC ## Terminal.SetMarkupStyle(string, AnsiStyle) ### Description Registers a custom markup token style for use with WriteMarkup. ### Method SetMarkupStyle ### Parameters - **name** (string) - Required - The token name (e.g., "primary"). - **style** (AnsiStyle) - Required - The style to associate with the token. ### Usage ```csharp Terminal.SetMarkupStyle("primary", AnsiStyle.Default with { Foreground = (AnsiColor)ConsoleColor.Cyan, Decorations = AnsiDecorations.Bold }); Terminal.SetMarkupStyle("danger", AnsiStyle.Default with { Foreground = (AnsiColor)ConsoleColor.Red, Decorations = AnsiDecorations.Bold }); Terminal.WriteMarkup("[primary]Hello[/] [danger]world[/]!"); ``` ``` -------------------------------- ### Read events with mouse and bracketed paste enabled Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Enables mouse input in drag mode and bracketed paste, then reads events asynchronously until Escape is pressed. Mouse and paste are opt-in because they change terminal behavior. ```csharp // Resize events are published automatically when supported. // Mouse and bracketed paste are opt-in because enabling them can change terminal behavior (selection/paste semantics). using var _mouse = Terminal.EnableMouseInput(TerminalMouseMode.Drag); using var _paste = Terminal.EnableBracketedPasteInput(); await foreach (var ev in Terminal.ReadEventsAsync()) { if (ev is TerminalKeyEvent { Key: TerminalKey.Escape }) break; } ``` -------------------------------- ### Emit hyperlinks with OSC 8 using Terminal.WriteAtomic Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md When supported, emit hyperlinks using BeginLink, Write, and EndLink within an atomic write block. ```csharp Terminal.WriteAtomic(w => { w.BeginLink("https://github.com/XenoAtom/XenoAtom.Terminal"); w.Write("XenoAtom.Terminal"); w.EndLink(); w.Write("\n"); }); ``` -------------------------------- ### Control cursor visibility, position, and style Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Hides the cursor, moves it to (0,0), sets style to Bar, writes "Top-left", then shows the cursor again. ```csharp Terminal.Cursor.Visible = false; Terminal.Cursor.Position = new TerminalPosition(0, 0); Terminal.Cursor.Style = XenoAtom.Ansi.AnsiCursorStyle.Bar; Terminal.WriteLine("Top-left"); Terminal.Cursor.Visible = true; ``` -------------------------------- ### Set graphics and cell size environment overrides Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md PowerShell commands to override graphics protocol and cell size for validation. Set XENOATOM_TERMINAL_GRAPHICS to auto, none, kitty, iterm2, or sixel; XENOATOM_TERMINAL_CELL_SIZE is optional WIDTHxHEIGHT. ```powershell $env:XENOATOM_TERMINAL_GRAPHICS = "sixel" # auto|none|kitty|iterm2|sixel $env:XENOATOM_TERMINAL_CELL_SIZE = "9x18" # optional WIDTHxHEIGHT cell metrics ``` -------------------------------- ### Set foreground/background colors and decorations Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Sets foreground color using an implicit conversion from ConsoleColor, background to default, and bold decorations. Note: these properties reflect style changes made via Terminal APIs; raw ANSI outside Terminal APIs can make tracked state inaccurate. ```csharp Terminal.ForegroundColor = (XenoAtom.Ansi.AnsiColor)ConsoleColor.Green; Terminal.BackgroundColor = XenoAtom.Ansi.AnsiColor.Default; Terminal.Decorations = XenoAtom.Ansi.AnsiDecorations.Bold; ``` -------------------------------- ### Fluent ANSI output with Terminal.T alias Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Terminal.T is a convenience alias for the Terminal instance, enabling fluent chaining of style and write methods. ```csharp Terminal.T.Foreground(ConsoleColor.Green).Write("ok").ResetStyle().WriteLine(); ``` -------------------------------- ### History scoped to options Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md History is stored on TerminalReadLineOptions, allowing explicit scoping or sharing. This loop reads lines until an empty line or null is entered. ```csharp Terminal.StartInput(); var options = new TerminalReadLineOptions { Echo = true, PromptMarkup = () => "[cyan]>[/] " }; while (true) { var line = await Terminal.ReadLineAsync(options); if (line is null || line.Length == 0) break; } ``` -------------------------------- ### Terminal.EnableBracketedPasteInput Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Enables bracketed paste mode for the terminal. ```APIDOC ## Terminal.EnableBracketedPasteInput ### Description Enables bracketed paste mode for the terminal. ### Method EnableBracketedPasteInput ### Signature `public IDisposable EnableBracketedPasteInput()` ### Remarks Wrap usage in a using statement to ensure disposal. ``` -------------------------------- ### Custom key handlers (KeyHandler) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md React to keys like Esc, F2, F3, F4 using KeyHandler. The handler receives a TerminalReadLineController to edit the line. ```csharp var options = new TerminalReadLineOptions { Echo = true, KeyHandler = static (ctl, key) => { if (key.Key == TerminalKey.Escape) ctl.Cancel(); if (key.Key == TerminalKey.F2) ctl.Insert(" --flag".AsSpan()); if (key.Key == TerminalKey.F3) ctl.SetCursorIndex(0); if (key.Key == TerminalKey.F4) ctl.Select(0, ctl.Length); }, }; ``` -------------------------------- ### Terminal.WriteAtomic with BeginLink/EndLink (OSC 8) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Emits hyperlinks using OSC 8 escape sequences when supported. ```APIDOC ## Terminal.WriteAtomic with BeginLink/EndLink (OSC 8) ### Description Emits hyperlinks using OSC 8 escape sequences when supported. ### Method WriteAtomic with BeginLink/EndLink ### Usage ```csharp Terminal.WriteAtomic(w => { w.BeginLink("https://github.com/XenoAtom/XenoAtom.Terminal"); w.Write("XenoAtom.Terminal"); w.EndLink(); w.Write("\n"); }); ``` ``` -------------------------------- ### Terminal.Cursor.GetPositionAsync() Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Asynchronously queries the current cursor position. ```APIDOC ## Terminal.Cursor.GetPositionAsync() ### Description Asynchronously queries the current cursor position. ### Method `Task GetPositionAsync()` ### Returns A `Task` representing the cursor position. ### Example ```csharp var pos = await Terminal.Cursor.GetPositionAsync(); ``` ``` -------------------------------- ### Treat Ctrl+C as input Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Sets TreatControlCAsInput to true to make Ctrl+C be treated as input instead of a signal event. This changes the default behavior where Ctrl+C is published as TerminalSignalEvent. ```csharp Terminal.TreatControlCAsInput = true; ``` -------------------------------- ### Ctrl+letter bindings with BindChar Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Use BindChar for Ctrl+letter bindings for readability. Binds Ctrl+A to CursorHome and Ctrl+E to CursorEnd. ```csharp bindings.BindChar(TerminalChar.CtrlA, TerminalModifiers.Ctrl, TerminalReadLineCommand.CursorHome); bindings.BindChar(TerminalChar.Ctrl('E'), TerminalModifiers.Ctrl, TerminalReadLineCommand.CursorEnd); ``` -------------------------------- ### Terminal.T (AnsiWriter fluent alias) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md A convenience alias for the AnsiWriter instance, enabling fluent chaining of styling and write methods. ```APIDOC ## Terminal.T (AnsiWriter fluent alias) ### Description A convenience alias for the AnsiWriter instance, enabling fluent chaining of styling and write methods. ### Method Fluent API ### Usage ```csharp Terminal.T.Foreground(ConsoleColor.Green).Write("ok").ResetStyle().WriteLine(); ``` ``` -------------------------------- ### Write plain text to stdout and stderr with Terminal.Out and Terminal.Error Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Use Terminal.Out and Terminal.Error to write plain text safely from multiple threads; writes are serialized. ```csharp Terminal.Out.WriteLine("stdout"); Terminal.Error.WriteLine("stderr"); ``` -------------------------------- ### Query cursor position asynchronously Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Asynchronously retrieves the current cursor position. ```csharp var pos = await Terminal.Cursor.GetPositionAsync(); ``` -------------------------------- ### Custom MarkupRenderer Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Controls how the visible slice of the line is rendered, e.g., for highlighting matches or selection. Uses XenoAtom.Ansi.AnsiMarkup.Escape. ```csharp var options = new TerminalReadLineOptions { Echo = true, MarkupRenderer = static (text, cursor, viewStart, viewLength, selectionStart, selectionLength) => XenoAtom.Ansi.AnsiMarkup.Escape(text.Slice(viewStart, viewLength)), }; ``` -------------------------------- ### Terminal.NotifyMarkupStylesChanged() Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Notifies the terminal that markup styles have changed, so cached markup renderers can be rebuilt. ```APIDOC ## Terminal.NotifyMarkupStylesChanged() ### Description Notifies the terminal that markup styles have changed, so cached markup renderers can be rebuilt. ### Method NotifyMarkupStylesChanged ### Usage Call after mutating MarkupStyles in-place. ``` -------------------------------- ### Terminal.ReadLineAsync Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Reads a line of input from the terminal asynchronously. ```APIDOC ## Terminal.ReadLineAsync ### Description Reads a line of input from the terminal asynchronously. ### Method ReadLineAsync ### Signature `public ValueTask ReadLineAsync()` ### Remarks Requires input to be started (either implicitly or via StartInput). ``` -------------------------------- ### Scoped cursor position restore Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Uses a using statement to restore the cursor position after temporarily moving it to (10,5) and writing text. ```csharp using var _pos = Terminal.UseCursorPosition(); Terminal.SetCursorPosition(10, 5); Terminal.WriteLine("Temporarily moved"); ``` -------------------------------- ### Terminal.WriteAtomic(Action) Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Executes a multi-step output sequence atomically, preventing interleaving with other concurrent output. Useful for styling transitions and cursor operations. ```APIDOC ## Terminal.WriteAtomic(Action) ### Description Executes a multi-step output sequence atomically, preventing interleaving with other concurrent output. Useful for styling transitions and cursor operations. ### Method WriteAtomic ### Parameters - **action** (Action) - Required - The action that performs the output operations. ### Usage ```csharp Terminal.WriteAtomic(w => { w.Foreground(ConsoleColor.DarkGray); w.Write("["); w.Write(DateTimeOffset.UtcNow.ToString("HH:mm:ss.fff")); w.Write("] "); w.ResetStyle(); w.Write("message\n"); }); ``` ``` -------------------------------- ### Terminal.ReadEventsAsync Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Reads terminal events asynchronously. ```APIDOC ## Terminal.ReadEventsAsync ### Description Reads terminal events asynchronously. ### Method ReadEventsAsync ### Signature `public IAsyncEnumerable ReadEventsAsync()` ### Remarks Use this instead of Console.Read* when input is running. ``` -------------------------------- ### Scoped terminal state operations Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Uses using declarations to restore terminal state when disposed. Sets title, alternate screen, hidden cursor, raw mode, and bracketed paste, then clears and writes to the alternate screen. ```csharp using var _title = Terminal.UseTitle("My App"); using var _alt = Terminal.UseAlternateScreen(); using var _cursor = Terminal.HideCursor(); using var _raw = Terminal.UseRawMode(); using var _paste = Terminal.EnableBracketedPaste(); Terminal.Clear(); Terminal.WriteLine("Hello from the alternate screen"); ``` -------------------------------- ### Terminal.Out.WriteLine / Terminal.Error.WriteLine Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Writes plain text to standard output or standard error. Writes are serialized and safe from multiple threads. ```APIDOC ## Terminal.Out.WriteLine / Terminal.Error.WriteLine ### Description Writes plain text to standard output or standard error. Writes are serialized and safe from multiple threads. ### Method WriteLine ### Usage ```csharp Terminal.Out.WriteLine("stdout"); Terminal.Error.WriteLine("stderr"); ``` ``` -------------------------------- ### TerminalTextUtility.TryGetIndexAtCell Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Attempts to find the character index at a given cell offset, accounting for grapheme clusters. ```APIDOC ## TerminalTextUtility.TryGetIndexAtCell ### Description Attempts to find the character index at a given cell offset, accounting for grapheme clusters. ### Method TryGetIndexAtCell ### Signature `public static bool TryGetIndexAtCell(ReadOnlySpan text, int cellOffset, out int index)` ### Parameters - **text** (ReadOnlySpan) - Required - The input string. - **cellOffset** (int) - Required - The cell offset to convert to a character index. - **index** (out int) - Required - The resulting character index. ### Returns - **bool** - True if the conversion succeeded; otherwise false. ### Example ```csharp TerminalTextUtility.TryGetIndexAtCell("hello world".AsSpan(), cellOffset: 6, out var index); ``` ``` -------------------------------- ### TerminalTextUtility.GetWidth Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Returns the display width of a string in terminal cells, accounting for grapheme clusters (emoji, ZWJ, combining sequences). ```APIDOC ## TerminalTextUtility.GetWidth ### Description Returns the display width of a string in terminal cells, accounting for grapheme clusters (emoji, ZWJ, combining sequences). ### Method GetWidth ### Signature `public static int GetWidth(ReadOnlySpan text)` ### Parameters - **text** (ReadOnlySpan) - Required - The input string to measure. ### Returns - **int** - The number of terminal cells the text occupies. ### Example ```csharp var cells = TerminalTextUtility.GetWidth("A😃中".AsSpan()); ``` ``` -------------------------------- ### TerminalTextUtility.GetWordEnd Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Returns the index of the end of the word containing the given index. ```APIDOC ## TerminalTextUtility.GetWordEnd ### Description Returns the index of the end of the word containing the given index. ### Method GetWordEnd ### Signature `public static int GetWordEnd(ReadOnlySpan text, int index)` ### Parameters - **text** (ReadOnlySpan) - Required - The input string. - **index** (int) - Required - The character index within the text. ### Returns - **int** - The index of the end of the word. ### Example ```csharp var wordEnd = TerminalTextUtility.GetWordEnd("hello_world".AsSpan(), index: 8); ``` ``` -------------------------------- ### Atomic output with Terminal.WriteAtomic for error message Source: https://github.com/xenoatom/xenoatom.terminal/blob/main/doc/readme.md Use Terminal.WriteAtomic to guarantee that a multi-step output sequence is not interleaved with other concurrent output, important for styling transitions and cursor operations. ```csharp Terminal.WriteAtomic(w => { w.Foreground(ConsoleColor.Red).Write("Error: ").ResetStyle(); w.Write("something went wrong\n"); }); ```