using System.Numerics; using System.Text.Json.Serialization; namespace Terminal.Gui.Drawing; /// /// Represents the visual styling for a UI element, including foreground and background color and text style. /// /// /// /// is a lightweight, immutable struct used to define how visual elements are rendered /// in a terminal UI. It wraps color and style information in a platform-independent way and is used /// extensively in , , and theming infrastructure. /// /// /// /// /// /// [JsonConverter (typeof (AttributeJsonConverter))] public readonly record struct Attribute : IEqualityOperators { /// Default empty attribute. [JsonIgnore] public static Attribute Default => new (Color.White, Color.Black); /// /// Gets the foreground used to render text. /// [JsonConverter (typeof (ColorJsonConverter))] public Color Foreground { get; init; } /// /// Gets the background used behind text. /// [JsonConverter (typeof (ColorJsonConverter))] public Color Background { get; init; } // TODO: Add constructors which permit including a Style. /// /// Gets the (e.g., bold, underline, italic) applied to text. /// public TextStyle Style { get; init; } = TextStyle.None; /// /// Initializes a new instance of the struct with default values. /// public Attribute () { this = Default; } /// /// Initializes a new from an existing instance, preserving explicit state. /// public Attribute (in Attribute attr) { this = attr; } /// /// Initializes an instance using two named colors. /// public Attribute (in Color foreground, in Color background) { Foreground = foreground; Background = background; Style = TextStyle.None; } /// /// Initializes a new instance with foreground, background, and . /// public Attribute (in Color foreground, in Color background, in TextStyle style) { Foreground = foreground; Background = background; Style = style; } /// /// Initializes a new instance of the struct from string representations of colors and style. /// /// Foreground color as a string (name, hex, or rgb). /// Background color as a string (name, hex, or rgb). /// Optional style as a string (e.g., "Bold,Underline"). /// Thrown if color parsing fails. public Attribute (in string foreground, in string background, in string? style = null) { Foreground = Color.Parse (foreground); Background = Color.Parse (background); Style = style is { } && Enum.TryParse (style, true, out TextStyle parsedStyle) ? parsedStyle : TextStyle.None; } /// /// Initializes a new instance of the struct from string representations of colors and style. /// /// Foreground color as a string (name, hex, or rgb). /// Background color as a string (name, hex, or rgb). /// Optional style as a string (e.g., "Bold,Underline"). /// Thrown if color parsing fails. public Attribute (in string foreground, in string background, in TextStyle style) { Foreground = Color.Parse (foreground); Background = Color.Parse (background); Style = style; } /// /// INTERNAL: Initializes a new instance with a value. Both and /// will be set to the specified color. /// /// Value. internal Attribute (in ColorName16 color16Name) : this (in color16Name, in color16Name) { } /// /// Initializes a new instance with foreground and background colors. /// public Attribute (in ColorName16 foreground16Name, in ColorName16 background16Name) : this (new Color (in foreground16Name), new Color (in background16Name)) { } /// /// Initializes a new instance with foreground and background colors. /// public Attribute (in ColorName16 foreground16Name, in Color background) : this (new Color (in foreground16Name), in background) { } /// /// Initializes a new instance with foreground and background colors. /// public Attribute (in Color foreground, in ColorName16 background16Name) : this (in foreground, new Color (in background16Name)) { } /// /// INTERNAL: Initializes a new instance with a value. Both and /// will be set to the specified color. /// /// Value. internal Attribute (in StandardColor standardColor) : this (in standardColor, in standardColor) { } /// /// Initializes a new instance with foreground and background colors. /// public Attribute (in StandardColor foreground, in StandardColor background) : this (new Color (in foreground), new Color (in background)) { } /// /// Initializes a new instance with foreground and background colors. /// public Attribute (in StandardColor foreground, in Color background) : this (new Color (in foreground), in background) { } /// /// Initializes a new instance with foreground and background colors. /// public Attribute (in Color foreground, in StandardColor background) : this (in foreground, new Color (in background)) { } /// /// Initializes an instance using a single color for both foreground and background. /// public Attribute (in Color color) : this (color, color) { } /// /// Initializes a new instance with foreground and background colors and a . /// public Attribute (in StandardColor foreground, in StandardColor background, in TextStyle style) : this ( new (in foreground), new Color (in background), style) { } /// public bool Equals (Attribute other) { return Foreground.Equals (other.Foreground) && Background.Equals (other.Background) && Style == other.Style; } /// public override int GetHashCode () { return HashCode.Combine (Foreground, Background, Style); } /// public override string ToString () { // Note: Unit tests are dependent on this format return $"[{Foreground},{Background},{Style}]"; } }