Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 21 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,29 @@ All notable changes to this project will be documented in this file.

The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).

## [0.2.0]

### Added

- Built-in themes embedded directly in `tca-types` (no files required): `catppuccin-mocha`, `cyberpunk`, `dracula`, `everforest-dark`, `gruvbox-dark`, `mono`, `nord`, `one-dark`, `rose-pine`, `solarized-light`, `tokyo-night`.
- `TcaTheme::new()` in `tca-ratatui` is the primary entry point for loading a theme. Resolves a theme name or file path through a 4-step fallback chain: user theme files -> built-in themes -> user preference config -> terminal dark/light auto-detection.
- `load_all_builtin()` in `tca-ratatui` returns all built-in themes as `Vec<TcaTheme>`.
- `BuiltinTheme` enum in `tca-types` with `EnumIter` support for iterating all built-ins.
- `TcaConfig` in `tca-loader` reads and writes user theme preferences from `~/.config/tca/tca.toml`. `mode_aware_theme()` returns the best theme name for the current terminal's dark or light mode.

### Changed

- `TryFrom<tca_types::Theme> for TcaTheme` is now `#[doc(hidden)]`.
- Updated all crate READMEs.

### Removed

- `load_all_from_dir()` and `load_all_from_theme_dir()` removed from `tca-ratatui`'s public API. Use `tca_loader::list_themes()` combined with `TcaTheme::new()` instead.

## [0.1.0]

### Initial Release

[Unreleased]: https://github.com/carmiac/tca-rust/commits/main
[0.2.0]: https://github.com/carmiac/tca-rust/compare/v0.1.0...v0.2.0
[0.1.0]: https://github.com/carmiac/tca-rust/releases/tag/v0.1.0
6 changes: 3 additions & 3 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ members = [
]

[workspace.package]
version = "0.1.0"
version = "0.2.0"
edition = "2021"
license = "MIT"
authors = ["carmiac"]
Expand All @@ -17,8 +17,8 @@ homepage = "https://github.com/carmiac/tca-rust"

[workspace.dependencies]
# Internal dependencies
tca-types = { path = "./tca-types", version = "0.1.0" }
tca-loader = { path = "./tca-loader", version = "0.1.0" }
tca-types = { path = "./tca-types", version = "0.2.0" }
tca-loader = { path = "./tca-loader", version = "0.2.0" }

# External dependencies
thiserror = "2.0"
Expand Down
91 changes: 57 additions & 34 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,68 +1,91 @@
# TCA Rust

Terminal Colors Architecture (TCA) implementation for Rust.
Terminal Colors Architecture (TCA) for Rust: consistent, user-configurable theming for terminal applications.

This repository contains the complete Rust ecosystem for TCA themes, including the core CLI tool, type definitions, theme loader, and Ratatui UI library.
## For Developers

## Packages
Add one line to your app and get beautiful theming with zero configuration:

```rust
let theme = TcaTheme::new(None);
```

This workspace contains 4 crates:
Your app immediately works with 11 built-in themes and any theme the user installs. You don't have to ship themes or write config parsers - TCA handles it.

- **[tca-types](tca-types/)** - Core types and data structures
- **[tca-loader](tca-loader/)** - XDG-compliant theme loading
- **[tca](tca/)** - CLI tool for validation and export
- **[tca-ratatui](tca-ratatui/)** - Ratatui UI library with widgets
```rust
// Use resolved colors directly in ratatui
let style = Style::default()
.fg(theme.ui.fg_primary)
.bg(theme.ui.bg_primary);

## Quick Start
let error_style = Style::default().fg(theme.semantic.error);
let border_style = Style::default().fg(theme.ui.border_primary);
```

## For Users

### Install the CLI Tool
Drop any `.toml` theme file into `~/.local/share/tca-themes/` and it becomes available to every TCA-powered app on the system with no per-app configuration needed.

```bash
cargo install --path tca
# Install a theme from the tca-themes collection
cp tokyo-night.toml ~/.local/share/tca-themes/

# Your app picks it up automatically
myapp --theme tokyo-night
```

### Use in Your Project
Browse available themes at [tca-themes](https://github.com/carmiac/tca-themes).

## How Theme Resolution Works

`TcaTheme::new(Some("name"))` tries each step in order, falling back gracefully:

1. **User theme files** - searches `~/.local/share/tca-themes/<name>.toml`, or accepts an exact file path
2. **Built-in themes** - catppuccin-mocha, cyberpunk, dracula, everforest-dark, gruvbox-dark, mono, nord, one-dark, rose-pine, solarized-light, tokyo-night
3. **User preference** - reads `~/.config/tca/tca.toml` for a configured default
4. **Auto-detect** - picks a dark or light built-in based on the terminal's background color

Passing `None` skips steps 1-2 and goes straight to the user's preference or auto-detection.

## Packages

| Crate | Purpose |
| ------------------------------- | ----------------------------------------- |
| **[tca-ratatui](tca-ratatui/)** | Ratatui integration - `TcaTheme`, widgets |
| **[tca-loader](tca-loader/)** | XDG theme file discovery and loading |
| **[tca-types](tca-types/)** | Core TOML types and color resolution |
| **[tca](tca/)** | CLI — `validate`, `export`, `list` |

## Getting Started

```toml
# For basic types
[dependencies]
tca-types = "0.1"
tca-ratatui = "0.2"
```

# For theme loading
[dependencies]
tca-loader = "0.1"
```rust
use tca_ratatui::TcaTheme;
use ratatui::style::Style;

# For Ratatui apps
[dependencies]
tca-ratatui = "0.1"
let theme = TcaTheme::new(None);
```

That's it. See [tca-ratatui](tca-ratatui/) for the full guide.

## Development

```bash
# Build all crates
cargo build --workspace

# Test all crates
cargo test --workspace

# Run clippy
cargo clippy --workspace

# Build CLI tool
cargo build --release -p tca
```

## Related Projects
## Related

- [tca-themes](https://github.com/carmiac/tca-themes) - Theme collection
- [tca-themes](https://github.com/carmiac/tca-themes) - community theme collection
- [tca-go](https://github.com/carmiac/tca-go) - Go implementation
- [tca-python](https://github.com/carmiac/tca-python) - Python implementation

## Changelog

See [CHANGELOG.md](CHANGELOG.md) for a history of notable changes.

## License

MIT
70 changes: 30 additions & 40 deletions tca-loader/README.md
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
# tca-loader

XDG-compliant theme loader for Terminal Colors Architecture.
XDG-compliant theme file discovery and loading for TCA.

## Overview

Provides filesystem operations for discovering and loading TCA themes from XDG data directories. Follows the XDG Base Directory specification.
Provides filesystem operations for discovering and loading TCA theme files, and reading user preferences. Used internally by `tca-ratatui` — most projects won't need to depend on this directly.

## Installation

Expand All @@ -13,64 +13,54 @@ Provides filesystem operations for discovering and loading TCA themes from XDG d
tca-loader = "0.1"
```

## Usage
## Theme directory

### Theme Discovery
Themes are `.toml` files stored in `~/.local/share/tca-themes/` (or `$XDG_DATA_HOME/tca-themes/`). Any file placed there is automatically discoverable by all TCA-powered apps.

```rust
use tca_loader::{get_themes_dir, list_themes, list_theme_names};
## API

// Get XDG theme directory path
let themes_dir = get_themes_dir()?;
// Returns: ~/.local/share/tca/themes (or equivalent)
### Discovery

// List all theme files
let theme_paths = list_themes()?;
```rust
use tca_loader::{get_themes_dir, list_themes, list_theme_names};

// List theme names (without extensions)
let names = list_theme_names()?;
let dir = get_themes_dir()?; // PathBuf to the themes directory
let paths = list_themes()?; // Vec<PathBuf> — all .toml files
let names = list_theme_names()?; // Vec<String> — names without extension
```

### Loading Themes
### Loading

```rust
use tca_loader::{find_theme, load_theme};
use tca_types::Theme;

// Find theme by name (searches XDG directory)
let path = find_theme("gruvbox")?;
use tca_loader::load_theme_file;

// Load with specific type
let theme: Theme = load_theme("gruvbox")?;
// Accepts a name ("nord"), a name with extension ("nord.toml"),
// or any file path ("/path/to/theme.toml")
let toml_str: String = load_theme_file("nord")?;

// Or load from explicit path
use tca_loader::load_theme_file;
let theme: Theme = load_theme_file(&path)?;
// Parse with tca-types
let theme: tca_types::Theme = toml::from_str(&toml_str)?;
```

### Generic Type Support

Works with any deserializable type:
### User preferences

```rust
use serde::Deserialize;
use tca_loader::TcaConfig;

// Reads ~/.config/tca/tca.toml
let config = TcaConfig::load();

#[derive(Deserialize)]
struct CustomTheme {
name: String,
colors: Vec<String>,
// Returns the best theme name for the current terminal mode
// (dark_theme, light_theme, or default_theme depending on what's configured)
if let Some(name) = config.mode_aware_theme() {
println!("preferred theme: {name}");
}

let custom: CustomTheme = load_theme("mytheme")?;
// Persist preferences
let config = TcaConfig { default_dark_theme: Some("nord".into()), ..Default::default() };
config.store();
```

## XDG Compliance

Theme directory resolution follows XDG Base Directory spec:

1. `$XDG_DATA_HOME/tca/themes/` (default: `~/.local/share/tca/themes/`)
2. Falls back to first writable location if directory doesn't exist

## License

MIT
Loading
Loading