Theme System
SharpConsoleUI includes a powerful theme system that allows runtime theme switching and custom theme creation.
Table of Contents
Built-in Themes
SharpConsoleUI includes three built-in themes:
Classic Theme
Traditional navy blue windows with classic styling.
windowSystem.ThemeRegistry.SetTheme("Classic");
Color Scheme:
- Window Background: Navy (DarkBlue)
- Window Foreground: White
- Active Border: Yellow
- Inactive Border: Gray
- Active Title: Yellow
- Inactive Title: Gray
- Desktop Background: Blue
- Desktop Foreground: White
ModernGray Theme (Default)
Modern dark theme with gray color scheme.
windowSystem.ThemeRegistry.SetTheme("ModernGray");
Color Scheme:
- Window Background: Grey11 (very dark gray)
- Window Foreground: Grey93 (light gray)
- Active Border: DeepSkyBlue1
- Inactive Border: Grey35
- Active Title: White
- Inactive Title: Grey50
- Desktop Background: Grey7
- Desktop Foreground: Grey70
DevDark Theme
Dark developer theme with green terminal-inspired accents. Requires the DeveloperTools plugin.
// Load plugin first
windowSystem.LoadPlugin<DeveloperToolsPlugin>();
// Then switch to DevDark theme
windowSystem.ThemeRegistry.SetTheme("DevDark");
Color Scheme:
- Window Background: Black
- Window Foreground: Green
- Active Border: Lime
- Inactive Border: DarkGreen
- Active Title: Yellow
- Inactive Title: DarkOliveGreen1
- Desktop Background: Grey3
- Desktop Foreground: Green
Using Themes
Setting Theme at Startup
using SharpConsoleUI;
using SharpConsoleUI.Drivers;
using SharpConsoleUI.Themes;
// Option 1: Use default theme (ModernGray)
var windowSystem = new ConsoleWindowSystem(new NetConsoleDriver(RenderMode.Buffer));
// Option 2: Specify theme by name
var windowSystem = new ConsoleWindowSystem(
new NetConsoleDriver(RenderMode.Buffer),
themeName: "Classic"
);
// Option 3: Provide theme instance
var windowSystem = new ConsoleWindowSystem(
new NetConsoleDriver(RenderMode.Buffer),
theme: new ModernGrayTheme()
);
Changing Theme at Runtime
// Using ThemeRegistry
windowSystem.ThemeRegistry.SetTheme("Classic");
// Direct assignment
windowSystem.Theme = new ModernGrayTheme();
// Using built-in theme selector dialog
windowSystem.ShowThemeSelectorDialog();
Creating Custom Themes
Implement the ITheme interface to create custom themes:
using SharpConsoleUI.Themes;
using Spectre.Console;
public class MyCustomTheme : ITheme
{
public Color WindowBackgroundColor => Color.DarkSlateGray;
public Color WindowForegroundColor => Color.White;
public Color ActiveBorderForegroundColor => Color.Cyan;
public Color InactiveBorderForegroundColor => Color.DarkGray;
public Color ActiveTitleForegroundColor => Color.Yellow;
public Color InactiveTitleForegroundColor => Color.Gray;
public Color DesktopBackgroundColor => Color.Black;
public Color DesktopForegroundColor => Color.DarkGray;
public char DesktopBackroundChar => '░';
}
Theme Properties
| Property | Description |
|---|---|
WindowBackgroundColor |
Background color for window content area |
WindowForegroundColor |
Default text color for window content |
ActiveBorderForegroundColor |
Border color for focused window |
InactiveBorderForegroundColor |
Border color for non-focused windows |
ActiveTitleForegroundColor |
Title bar color for focused window |
InactiveTitleForegroundColor |
Title bar color for non-focused windows |
DesktopBackgroundColor |
Background color for empty desktop space |
DesktopForegroundColor |
Foreground color for desktop character |
DesktopBackroundChar |
Character used to fill desktop background |
Registering Custom Themes
// Register a custom theme
windowSystem.ThemeRegistry.RegisterTheme("MyCustomTheme", new MyCustomTheme());
// Now you can switch to it
windowSystem.ThemeRegistry.SetTheme("MyCustomTheme");
Complete Custom Theme Example
using SharpConsoleUI;
using SharpConsoleUI.Themes;
using SharpConsoleUI.Drivers;
using Spectre.Console;
public class SolarizedDarkTheme : ITheme
{
// Base colors from Solarized Dark palette
public Color WindowBackgroundColor => new Color(0, 43, 54); // base03
public Color WindowForegroundColor => new Color(131, 148, 150); // base0
public Color ActiveBorderForegroundColor => new Color(38, 139, 210); // blue
public Color InactiveBorderForegroundColor => new Color(88, 110, 117); // base01
public Color ActiveTitleForegroundColor => new Color(181, 137, 0); // yellow
public Color InactiveTitleForegroundColor => new Color(88, 110, 117); // base01
public Color DesktopBackgroundColor => new Color(7, 54, 66); // base02
public Color DesktopForegroundColor => new Color(88, 110, 117); // base01
public char DesktopBackroundChar => '·';
}
// Usage
var windowSystem = new ConsoleWindowSystem(new NetConsoleDriver(RenderMode.Buffer));
windowSystem.ThemeRegistry.RegisterTheme("SolarizedDark", new SolarizedDarkTheme());
windowSystem.ThemeRegistry.SetTheme("SolarizedDark");
Theme Registry
The ThemeRegistry manages theme registration and switching.
Available Methods
// Register a new theme
windowSystem.ThemeRegistry.RegisterTheme("MyTheme", new MyCustomTheme());
// Set active theme by name
windowSystem.ThemeRegistry.SetTheme("MyTheme");
// Get a theme by name
ITheme? theme = windowSystem.ThemeRegistry.GetTheme("Classic");
// Get all registered theme names
IEnumerable<string> themes = windowSystem.ThemeRegistry.GetRegisteredThemes();
// Check if theme exists
bool exists = windowSystem.ThemeRegistry.HasTheme("MyTheme");
// Get default theme
ITheme defaultTheme = ThemeRegistry.GetDefaultTheme();
// Get theme or fallback to default
ITheme theme = ThemeRegistry.GetThemeOrDefault("NonExistent", new ClassicTheme());
List All Available Themes
var themes = windowSystem.ThemeRegistry.GetRegisteredThemes();
foreach (var themeName in themes)
{
Console.WriteLine($"- {themeName}");
}
Runtime Theme Switching
Themes can be changed at any time and apply immediately to all windows.
Using Theme Selector Dialog
The easiest way for users to change themes:
windowSystem.ShowThemeSelectorDialog();
Programmatic Theme Switching
// Add a button to switch themes
mainWindow.AddControl(
Controls.Button("Switch to Classic")
.OnClick((sender, e, window) =>
{
windowSystem.ThemeRegistry.SetTheme("Classic");
})
.Build()
);
// Cycle through themes
var themes = windowSystem.ThemeRegistry.GetRegisteredThemes().ToList();
int currentIndex = 0;
mainWindow.AddControl(
Controls.Button("Next Theme")
.OnClick((sender, e, window) =>
{
currentIndex = (currentIndex + 1) % themes.Count;
windowSystem.ThemeRegistry.SetTheme(themes[currentIndex]);
windowSystem.NotificationStateService.ShowNotification(
"Theme Changed",
$"Switched to {themes[currentIndex]}",
NotificationSeverity.Info
);
})
.Build()
);
Theme Switching with Keyboard Shortcut
mainWindow.KeyPressed += (sender, e) =>
{
if (e.KeyInfo.Key == ConsoleKey.F9)
{
windowSystem.ShowThemeSelectorDialog();
e.Handled = true;
}
};
Best Practices
- Use high contrast: Ensure good readability between background and foreground colors
- Test both states: Verify both active and inactive window states look good
- Consider desktop: Desktop colors should not distract from windows
- Name descriptively: Use clear theme names (e.g., "DarkBlue" not "Theme1")
- Register early: Register custom themes before showing any windows
- Provide selector: Give users a way to change themes (F9 is recommended)
Color Guidelines
Recommended Color Combinations
Dark Themes:
- Background: Black, very dark gray (Grey7-Grey15)
- Foreground: White, light gray (Grey85-Grey93)
- Active Border: Bright colors (Cyan, Blue, Yellow)
- Inactive Border: Medium gray (Grey30-Grey50)
Light Themes:
- Background: White, very light gray (Grey93-Grey100)
- Foreground: Black, dark gray (Grey7-Grey15)
- Active Border: Medium-dark colors
- Inactive Border: Light gray (Grey70-Grey85)
Spectre.Console Color Support
SharpConsoleUI uses Spectre.Console colors. Available color types:
// Named colors
Color.Red, Color.Blue, Color.Green, Color.Yellow, etc.
// RGB colors
new Color(255, 128, 0) // Orange
// Hex colors
Color.FromInt32(0xFF8000)
// Gray scale (Grey0 to Grey100)
Color.Grey0 // Black
Color.Grey50 // Medium gray
Color.Grey100 // White
Complete Theme Manager Example
using SharpConsoleUI;
using SharpConsoleUI.Builders;
using SharpConsoleUI.Controls;
using SharpConsoleUI.Themes;
using SharpConsoleUI.Drivers;
var windowSystem = new ConsoleWindowSystem(new NetConsoleDriver(RenderMode.Buffer));
// Register custom themes
windowSystem.ThemeRegistry.RegisterTheme("SolarizedDark", new SolarizedDarkTheme());
windowSystem.ThemeRegistry.RegisterTheme("Dracula", new DraculaTheme());
var mainWindow = new WindowBuilder(windowSystem)
.WithTitle("Theme Manager")
.WithSize(60, 20)
.Centered()
.Build();
// Add theme selector button
mainWindow.AddControl(new MarkupControl(new List<string>
{
"[bold yellow]Available Themes:[/]",
""
}));
// Create buttons for each theme
foreach (var themeName in windowSystem.ThemeRegistry.GetRegisteredThemes())
{
mainWindow.AddControl(
Controls.Button($"Switch to {themeName}")
.OnClick((sender, e, window) =>
{
windowSystem.ThemeRegistry.SetTheme(themeName);
windowSystem.NotificationStateService.ShowNotification(
"Theme Changed",
$"Active theme: {themeName}",
NotificationSeverity.Success
);
})
.Build()
);
}
// Add keyboard shortcut
mainWindow.KeyPressed += (sender, e) =>
{
if (e.KeyInfo.Key == ConsoleKey.F9)
{
windowSystem.ShowThemeSelectorDialog();
e.Handled = true;
}
};
windowSystem.AddWindow(mainWindow);
windowSystem.Run();