#pragma once /// Represents a 4-channel color value, with Red, Green, Blue, and Alpha components. #include #include #include #include #include #include #include #include "ColorFormats.hpp" using u8 = uint8_t; class Color4; std::string toEscapeCode(Color4 c, bool bg=false); namespace mcolor { void printBuiltinColorList(); } /// A type representing a color with alpha. /// Our default format is RGBA with 8 bits-per-channel. /// Conversions to other color formats are provided. class Color4 { public: u8 r; u8 g; u8 b; u8 a; public: /// The default constructor does not initialize any members. Color4() = default; /// Constructs a new Color4 from a Color3 and an optional alpha value. explicit Color4(const Color3& color3, u8 alpha = 255); /// Constructs a new Color4 from red, green, blue channel values, and an optional alpha value. Color4(u8 red, u8 green, u8 blue, u8 alpha = 255); /// Constructs a new Color4 from an RGB structure and an optional alpha value. explicit Color4(const RGB& rgb, u8 alpha = 255); /// Constructs a new Color4 from an RGBA structure. explicit Color4(const RGBA& rgba); /// Constructs a new Color4 from a floating-point RGB structure and an optional alpha value. /// @note: Normalizes the color values from ranges [0, 1] to [0, 255]. explicit Color4(const RGBf& rgb, float alpha = 1.0f); /// Constructs a new Color4 from a floating-point RGBA structure. /// /// @note: Normalizes the color values from ranges [0, 1] to [0, 255]. explicit Color4(const RGBAf& rgba); /// Constructs a new Color4 from an HSV structure. explicit Color4(const HSV& hsv, float alpha = 1.f); /// Constructs a new Color4 from an HSVA structure. explicit Color4(const HSVA& hsva); /// TODO: HSL to RGB constructor explicit Color4(const HSL& hsl, float alpha = 1.f); // TODO: LCH to RGB constructor explicit Color4(const LCH& lch, float alpha = 1.f); // TODO: LCHA to RGB constructor explicit Color4(const LCHA& lcha); static Color4 FromColor3(const Color3& color3, u8 alpha = 255); static Color4 FromHex(const std::string& hexCode, u8 alpha = 255); static Color4 FromHexA(const std::string& hexACode); static Color4 FromHSV(const HSV& hsv, float alpha = 1.f); /// @param hue The hue value represented in degrees [0-360] static Color4 FromHSV(float hue, float saturation, float value, float alpha = 1.f); static Color4 FromHSL(float hue, float saturation, float lightness, float alpha = 1.f); static Color4 FromNormalized(float red, float green, float blue, float alpha = 1.f); static Color4 FromLCH(float l, float c, float h, float alpha = 1.f); public: /// Performs the interpolation in normalized color space (0-1) and converts it back. [[nodiscard]] Color4 Lerp(const Color4& rhs, float t) const; static Color4 Lerp(const Color4& lhs, const Color4& rhs, float t); /// Alternative to Lerp which does not normalize color channels before and after interpolation. [[nodiscard]] Color4 Lerp2(const Color4& rhs, float t) const; /// Alternative to Lerp which does not normalize color channels before and after interpolation. static Color4 Lerp2(const Color4& lhs, const Color4& rhs, float t); [[nodiscard]] Color4 LerpByHSVA(const Color4& rhs, float t) const; [[nodiscard]] std::string ToHex() const; [[nodiscard]] std::string ToHexAlpha() const; [[nodiscard]] u8 RedChannel() const; [[nodiscard]] u8 GreenChannel() const; [[nodiscard]] u8 BlueChannel() const; [[nodiscard]] u8 AlphaChannel() const; [[nodiscard]] u8 R() const; [[nodiscard]] u8 G() const; [[nodiscard]] u8 B() const; [[nodiscard]] u8 A() const; [[nodiscard]] float RedChannelNormalized() const; [[nodiscard]] float GreenChannelNormalized() const; [[nodiscard]] float BlueChannelNormalized() const; [[nodiscard]] float AlphaChannelNormalized() const; [[nodiscard]] float RN() const; [[nodiscard]] float GN() const; [[nodiscard]] float BN() const; [[nodiscard]] float AN() const; u8* ptr(); [[nodiscard]] const u8* ptr() const; [[nodiscard]] HSV ToHSV() const; [[nodiscard]] HSVA ToHSVA() const; HSL ToHSL() const; HSLA ToHSLA() const; // TODO: Color4 ToLCH LCH ToLCH() const; // TODO: Disparate with mcolor::toEscapeCode, resolve. [[nodiscard]] std::string EscapeCode(bool bg = false, bool bold = false) const; [[nodiscard]] std::string FGEscapeCode(bool bold = false) const; [[nodiscard]] std::string BGEscapeCode(bool bold = false) const; bool operator==(const Color4& rhs) const; bool operator!=(const Color4& rhs) const; std::string ToEscapeCode(bool bg = false) const; }; inline std::ostream& operator << (std::ostream& os, const Color4& c) { os << "Color4(" << c.r << "," << c.g << "," << c.b << "," << c.a << ") AKA " << c.ToHex(); return os; }