Raxol. UI. Theming. Palette
(Raxol v2.6.1)
View Source
Single canonical home for Raxol's palette PRIMITIVES: the color VALUES that
theming, terminal rendering, and UI components pull from -- as opposed to
the color-manipulation ALGORITHMS (HSL conversion, harmony, gradients,
accessibility suggestion, contrast calculation), which stay where they are
(Raxol.Style.Colors.*, Raxol.UI.Theming.Salience).
Why this module exists
A full-codebase audit (docs/proposals/palette-inventory.md)
found the same conceptual color defined independently, with DIFFERENT
values, in many places -- most strikingly at least four conflicting "the
standard ANSI 16 colors" conventions (6+ literal copies) and at least five
unrelated "the default semantic theme" token sets. This module does not
silently pick a winner (that would change runtime behaviour for whichever
call sites are later pointed at it) -- it PRESERVES every existing value
under a clearly attributed name, so future migration work can make an
informed choice call site by call site. See the inventory doc for the full
duplicate/conflict catalogue, file:line citations, and a ranked list of the
call sites most worth migrating.
This module is additive only: nothing in the tree calls into it yet. Existing modules keep their own copies until migrated one at a time.
Sections
- Named colors -- CSS-ish web color names, merged from the two sources that agreed with each other byte-for-byte.
- WCAG-safe fallbacks -- black/white, duplicated ~15x verbatim elsewhere.
- The near-black surface convention --
#1E1E1E, duplicated 3x elsewhere. - ANSI 16 basic palette -- 4 documented, mutually conflicting variants.
- ANSI 256 cube / grayscale -- generation constants; 2 conflicting cube formulas, 1 uncontested grayscale ramp.
- Platform terminal palettes -- linux/mac/windows, uncontested.
- Semantic default-theme families -- 7 conflicting token sets, each preserved exactly under the name of the module it came from.
- Salience / H-K tier anchors -- delegates to the live source
(
Raxol.UI.Theming.SalienceTheme) rather than copying literals, so it can never drift. The darcula-family reference bake is a byte-exact test fixture intest/raxol/ui/theming/salience_test.exsand is deliberately NOT reproduced here -- it is generated bySalience.solve/3's floating-point math, not stored as a literal. - Effect accent palettes -- BorderBeam's 7 variants (ANSI + CSS flavors).
Non-goals
This module does not implement color conversion, blending, contrast
calculation, or theme resolution -- see Raxol.Style.Colors.Color,
Raxol.Style.Colors.Formats, Raxol.Style.Colors.Utilities,
Raxol.UI.Theming.Theme, and Raxol.Core.Theming.ThemeRegistry for those.
It also does not attempt to catalog the 10 named community themes already
well-organized in Raxol.Core.Theming.ThemeRegistry (dracula, nord,
monokai, gruvbox, solarized, tokyo_night, one_dark, catppuccin,
synthwave84) -- that module already serves that role; duplicating it here
would just add a fifth copy to a category that already has too many.
Summary
Functions
Returns one of the 4 conflicting ANSI 16-color conventions found in the
codebase, as a 16-element list of {r, g, b} tuples in ansi_16_names/0
order. Defaults to :xterm, the convention with the most independent
copies. See inventory §5.1 for the full comparison table.
Like ansi_16/1, but keyed by color name instead of positional index.
The 16 ANSI color names in SGR 30-37/90-97 order, shared by every ansi_16/1 variant.
The known ANSI 16-color convention variant names, for iteration/tests.
Generates the 216-entry ANSI 256-color cube (indices 16-231) under the
given step formula. Returns [{index, {r, g, b}}].
Generates the 24-entry ANSI 256-color grayscale ramp (indices 232-255).
Returns [{index, {level, level, level}}]. Unlike the cube, every source
in the codebase agrees on this formula -- there is only one variant.
The WCAG-safe black fallback, as reused independently 15+ times across the codebase.
The BorderBeam effect's muted inner-glow accent color for a variant.
The BorderBeam effect's ANSI-atom accent palette for a variant (terminal rendering path).
The BorderBeam effect's CSS hex accent palette for a variant (LiveView/web rendering path).
Looks up one named color. Returns nil for an unknown name.
All named colors as a name => hex map.
The near-black surface value shared (independently) by three unrelated call sites.
Same value as near_black_surface/0, as the RGB tuple form used by theme_integration.ex.
Returns the platform-flavored 16-color terminal palette as
[{index, {r, g, b}}], matching each OS's real terminal default colors
(as opposed to any of the ansi_16/1 conventions, which are all
synthetic/idealized).
RGB-tuple-flavored sibling of semantic_defaults/1 for the one family stored that way.
The semantic (name, hue, chroma, tier) seed table the salience/H-K color
system solves against a ground lightness. Delegates to
Raxol.UI.Theming.SalienceTheme.seeds/0 (not copied) so this can never
drift from the live source.
The reference near-black ground OKLCH lightness the salience tier deltas
were derived against. Delegates to
Raxol.UI.Theming.Salience.reference_ground/0 (not copied).
The known semantic-default family names, for iteration/tests.
Returns one of the 7 independently-defined "default semantic theme" token sets found in the codebase, exactly as defined at its source. Token keys and even the set of tokens differ between families by design -- these are not meant to be interchangeable, only auditable side by side.
The WCAG-safe white fallback, as reused independently 15+ times across the codebase.
Types
@type ansi_16_variant() :: :xterm | :vga | :gnome_terminal | :pure_pastel
@type ansi_256_cube_formula() :: :xterm_accurate | :naive_linear
@type border_beam_variant() ::
:colorful | :mono | :ocean | :sunset | :electric | :neon | :matrix
@type hex() :: String.t()
@type platform() :: :linux | :mac | :windows
@type rgb() :: {0..255, 0..255, 0..255}
@type semantic_family() ::
:dracula_ide
| :dracula_ide_dark
| :brand_light
| :material_dark
| :material_high_contrast
| :web_tailwind
| :web_bootstrap
| :renderer_defaults
Functions
@spec ansi_16(ansi_16_variant()) :: [rgb()]
Returns one of the 4 conflicting ANSI 16-color conventions found in the
codebase, as a 16-element list of {r, g, b} tuples in ansi_16_names/0
order. Defaults to :xterm, the convention with the most independent
copies. See inventory §5.1 for the full comparison table.
@spec ansi_16_named(ansi_16_variant()) :: %{required(atom()) => rgb()}
Like ansi_16/1, but keyed by color name instead of positional index.
@spec ansi_16_names() :: [atom()]
The 16 ANSI color names in SGR 30-37/90-97 order, shared by every ansi_16/1 variant.
@spec ansi_16_variants() :: [ansi_16_variant()]
The known ANSI 16-color convention variant names, for iteration/tests.
@spec ansi_256_cube(ansi_256_cube_formula()) :: [{16..231, rgb()}]
Generates the 216-entry ANSI 256-color cube (indices 16-231) under the
given step formula. Returns [{index, {r, g, b}}].
@spec ansi_256_grayscale() :: [{232..255, rgb()}]
Generates the 24-entry ANSI 256-color grayscale ramp (indices 232-255).
Returns [{index, {level, level, level}}]. Unlike the cube, every source
in the codebase agrees on this formula -- there is only one variant.
@spec black() :: hex()
The WCAG-safe black fallback, as reused independently 15+ times across the codebase.
@spec effect_accent(:border_beam, :glow | :bloom, border_beam_variant()) :: atom()
The BorderBeam effect's muted inner-glow accent color for a variant.
@spec effect_palette(:border_beam, border_beam_variant()) :: [atom()]
The BorderBeam effect's ANSI-atom accent palette for a variant (terminal rendering path).
@spec effect_palette_css(:border_beam, border_beam_variant()) :: [hex()]
The BorderBeam effect's CSS hex accent palette for a variant (LiveView/web rendering path).
Looks up one named color. Returns nil for an unknown name.
All named colors as a name => hex map.
@spec near_black_surface() :: hex()
The near-black surface value shared (independently) by three unrelated call sites.
@spec near_black_surface_rgb() :: rgb()
Same value as near_black_surface/0, as the RGB tuple form used by theme_integration.ex.
Returns the platform-flavored 16-color terminal palette as
[{index, {r, g, b}}], matching each OS's real terminal default colors
(as opposed to any of the ansi_16/1 conventions, which are all
synthetic/idealized).
RGB-tuple-flavored sibling of semantic_defaults/1 for the one family stored that way.
@spec salience_darcula_seeds() :: [map()]
The semantic (name, hue, chroma, tier) seed table the salience/H-K color
system solves against a ground lightness. Delegates to
Raxol.UI.Theming.SalienceTheme.seeds/0 (not copied) so this can never
drift from the live source.
@spec salience_reference_ground() :: float()
The reference near-black ground OKLCH lightness the salience tier deltas
were derived against. Delegates to
Raxol.UI.Theming.Salience.reference_ground/0 (not copied).
@spec semantic_default_families() :: [semantic_family()]
The known semantic-default family names, for iteration/tests.
@spec semantic_defaults(semantic_family()) :: %{required(atom()) => hex()}
Returns one of the 7 independently-defined "default semantic theme" token sets found in the codebase, exactly as defined at its source. Token keys and even the set of tokens differ between families by design -- these are not meant to be interchangeable, only auditable side by side.
@spec white() :: hex()
The WCAG-safe white fallback, as reused independently 15+ times across the codebase.