Retro.Crt 0.2.1

There is a newer version of this package available.
See the version list below for details.
dotnet add package Retro.Crt --version 0.2.1
                    
NuGet\Install-Package Retro.Crt -Version 0.2.1
                    
This command is intended to be used within the Package Manager Console in Visual Studio, as it uses the NuGet module's version of Install-Package.
<PackageReference Include="Retro.Crt" Version="0.2.1" />
                    
For projects that support PackageReference, copy this XML node into the project file to reference the package.
<PackageVersion Include="Retro.Crt" Version="0.2.1" />
                    
Directory.Packages.props
<PackageReference Include="Retro.Crt" />
                    
Project file
For projects that support Central Package Management (CPM), copy this XML node into the solution Directory.Packages.props file to version the package.
paket add Retro.Crt --version 0.2.1
                    
#r "nuget: Retro.Crt, 0.2.1"
                    
#r directive can be used in F# Interactive and Polyglot Notebooks. Copy this into the interactive tool or source code of the script to reference the package.
#:package Retro.Crt@0.2.1
                    
#:package directive can be used in C# file-based apps starting in .NET 10 preview 4. Copy this into a .cs file before any lines of code to reference the package.
#addin nuget:?package=Retro.Crt&version=0.2.1
                    
Install as a Cake Addin
#tool nuget:?package=Retro.Crt&version=0.2.1
                    
Install as a Cake Tool

Retro.Crt

ci docs nuget license

A Pascal CRT-Unit-style console library for modern .NET. Tiny, dependency- free, trim- and AOT-clean. ANSI styling, classic TextColor / GotoXY / ClrScr verbs, truecolor with graceful 16-color and NO_COLOR fallback, plus a small set of Pascal-flavoured output building blocks: framed banners, in-place progress bars, semantic logging, and a typewriter that fades characters in.

using Retro.Crt;

Crt.TextColor(Color.LightCyan);
Crt.WriteLine("system online.");

using (Crt.WithStyle(Color.Yellow, bold: true))
    Crt.WriteLine("> ready.");

Install

dotnet add package Retro.Crt

API reference: https://chloe-dream.github.io/retro-crt

Targets net10.0. No third-party dependencies.

Why

Spectre.Console is great, but it does not trim or AOT cleanly, and a launcher that ships as a 12 MB single binary cannot afford the runtime weight. Retro.Crt is the small, opinionated alternative for tools that want curated colored output, a banner, a progress bar, and nothing else.

Comparison

Retro.Crt Spectre.Console Pastel Crayon
Trim / AOT clean
Runtime dependencies 0 many 0 0
Truecolor
Pascal-flavoured verbs
Framed banner
Progress bar ✅ (single) ✅ (multi/live)
Tables / trees / forms
Live regions / layout
Markup language
Built-in logger ✅ (tiny)

If you need tables, trees, forms, layouts, or a markup language — use Spectre.Console. If you need a 12 MB AOT launcher with a charming splash screen, four log levels, and a single progress bar — this library.

How to use

Colors and styling

The 16 classic DOS palette names (LightCyan, Brown, …) map onto the user's terminal theme via SGR codes — so themed terminals (Solarized, Dracula, …) keep their identity. Use Color.Rgb(r, g, b) for truecolor.

Crt.TextColor(Color.LightGreen);
Crt.Write("ok");
Crt.ResetColor();

using (Crt.WithStyle(fg: Color.Rgb(255, 140, 0), bold: true))
    Crt.WriteLine("warning, in orange");

Crt.ColorEnabled reflects whether escapes will actually reach the terminal (false when output is redirected, NO_COLOR is set, or VT enablement failed on Windows). FORCE_COLOR=1 overrides redirection detection.

Color.TryParse, Color.TryFromHex, and Color.TryFromName accept hex strings (#RRGGBB, #RGB, with or without the leading hash) and the canonical DOS palette names (LightCyan, Brown, …, case insensitive). Useful for reading colors from config files.

if (Color.TryParse(userInput, out var c))
    Crt.TextColor(c);

Diagnostics

var report = Diagnostics.Capture();
Console.WriteLine(report);
// ansi=on unicode=on redirected=no TERM=xterm-256color
//   enc=utf-8(65001) os=linux

Use this in a startup hook when a user reports "I don't see colors" — the one-line summary usually contains the answer (NO_COLOR=set, redirected=stdout, enc=us-ascii, …).

Pascal CRT verbs

Crt.ClrScr();
Crt.GotoXY(10, 5);     // 1-based, like the original CRT unit
Crt.Write("hi");
Crt.ClrEol();
Banner.Box("Retro.Crt 0.2", fg: Color.LightCyan);

Banner.Box(
    ["Retro.Crt 0.2", "Banner / Bar / Log / Typewriter"],
    fg: Color.LightCyan);

Banner.Gradient(
    asciiArtLines,
    from: Color.Rgb(80, 220, 255),
    to:   Color.Rgb(255, 120, 175));

Box uses unicode box-drawing glyphs when the terminal can render them, and falls back to +--+ on legacy ASCII code pages. Gradient interpolates per line; both endpoints must be truecolor or it falls back to from.

ProgressBar

using var bar = ProgressBar.Start(
    total: 4_500_000,
    width: 30,
    label: " download",
    color: Color.LightCyan);

for (var i = 0; i <= 100; i++)
{
    bar.Set(i * 45_000);
    Thread.Sleep(40);
}

The bar redraws in place on every Set / Tick, hides the terminal cursor for its lifetime, and prints a single final frame on Dispose. When ANSI is unavailable (output redirected, NO_COLOR, dumb terminal) intermediate updates are suppressed and only the final frame is written — so log files do not end up with sixty progress lines in a row.

Log

Log.Debug("loading config from /etc/retro");
Log.Info("system online");
Log.Success("checksum verified");
Log.Warn("disk usage at 84%");
Log.Error("failed to bind port 8080");

Format: HH:MM:SS LEVEL message with a fixed five-char level tag so columns line up. Warn and Error go to stderr; everything else to stdout.

Typewriter

Reveals text one character at a time. Optional fake cursor between characters and optional alpha fade-in (the final glyph appears in its target color but ramps from dim to full brightness). The terminal's native cursor is hidden for the whole reveal.

Typewriter.TypeLine(
    "system online.",
    msPerChar: 25,
    fg: Color.LightCyan);

Typewriter.TypeLine(
    "with a fake cursor...",
    msPerChar: 30,
    fg: Color.LightGreen,
    cursor: TypewriterCursor.Block);

Typewriter.TypeLine(
    "alpha fade-in (truecolor)...",
    msPerChar: 50,
    fg: Color.Rgb(255, 120, 200),
    fade: TypewriterFade.Alpha);

Typewriter.TypeLine(
    "gradient + cursor + alpha fade",
    msPerChar: 40,
    cursor: TypewriterCursor.Block,
    fade: TypewriterFade.Alpha,
    gradient: (Color.Rgb(80, 220, 255), Color.Rgb(255, 120, 175)));

Alpha fade requires truecolor — on Standard16 it silently degrades to no fade (Standard16 has no brightness scaling). When ANSI is off both cursor and fade are skipped and the string is dumped at full speed — still typed, but without animation residue in logs.

The cursor and fade animations assume one terminal cell per char, so emoji (surrogate pairs), combining marks, and wide CJK glyphs aren't correctly tracked. Stick to BMP single-cell characters when animating.

TypeAsync / TypeLineAsync are the awaitable variants — same shape, plus a CancellationToken. Cancellation aborts the reveal mid-string; the finally block still erases the trailing cursor, restores color, and re-shows the terminal cursor before the OperationCanceledException propagates.

using var cts = new CancellationTokenSource(TimeSpan.FromSeconds(2));
try
{
    await Typewriter.TypeLineAsync(
        "running...", msPerChar: 40, fg: Color.LightCyan,
        cancellationToken: cts.Token);
}
catch (OperationCanceledException) { /* terminal is in a clean state */ }

Building from source

git clone https://github.com/chloe-dream/retro-crt
cd retro-crt
dotnet build
dotnet test
dotnet run --project samples/Retro.Crt.Demo

NuGet package

The library project is already packable. Build a .nupkg locally with:

dotnet pack src/Retro.Crt/Retro.Crt.csproj -c Release

Output lands in src/Retro.Crt/bin/Release/Retro.Crt.<version>.nupkg (plus a .snupkg symbol package — IncludeSymbols is on).

To publish to nuget.org, set up an API key and:

dotnet nuget push src/Retro.Crt/bin/Release/Retro.Crt.0.2.0.nupkg \
    --api-key $NUGET_API_KEY \
    --source https://api.nuget.org/v3/index.json

The package is not published yet — version 0.2.0 is the first one worth shipping (Stage 1 was barely a library).

Roadmap

See ROADMAP.md. Stage 3 sketches a cell-grid screen buffer with diff renderer for Turbo-Vision-style shadows, save/restore-rect, and flicker-free repaint.

Status

Pre-1.0. Public API may move between minor versions until 1.0.

License

MIT

Product Compatible and additional computed target framework versions.
.NET net10.0 is compatible.  net10.0-android was computed.  net10.0-browser was computed.  net10.0-ios was computed.  net10.0-maccatalyst was computed.  net10.0-macos was computed.  net10.0-tvos was computed.  net10.0-windows was computed. 
Compatible target framework(s)
Included target framework(s) (in package)
Learn more about Target Frameworks and .NET Standard.
  • net10.0

    • No dependencies.

NuGet packages (1)

Showing the top 1 NuGet packages that depend on Retro.Crt:

Package Downloads
Retro.Crt.Tui

Text User Interface widgets on top of Retro.Crt's cell-buffer / diff-renderer core. Layout, focus, mouse + keyboard, scrollable log viewer, dialogs — DOS-style UI in a modern terminal. Tiny, dependency-free, trim- and AOT-clean.

GitHub repositories

This package is not used by any popular GitHub repositories.

Version Downloads Last Updated
0.8.0 160 5/19/2026
0.7.1 192 5/8/2026
0.7.0 131 5/6/2026
0.6.0 134 5/5/2026
0.5.0 100 5/5/2026
0.4.0 111 5/4/2026
0.3.0 119 5/4/2026
0.2.1 172 5/3/2026