1use std::{
5 collections::HashMap,
6 fmt::{Display, Formatter},
7};
8use serde::{Serialize, Deserialize};
9use lazy_static::lazy_static;
10
11#[derive(Copy, Clone, PartialEq, Eq, PartialOrd, Ord, Hash, Debug, Default,
14 Serialize, Deserialize)]
15pub enum Color
16{
17 None = 0,
18 Black = 1,
19 #[default]
20 Blue = 2,
21 Cyan = 3,
22 Green = 4,
23 Gray = 5,
24 Magenta = 6,
25 Red = 7,
26 White = 8,
27 Yellow = 9,
28
29 BrightBlack = 10,
30 BrightBlue = 11,
31 BrightCyan = 12,
32 BrightGreen = 13,
33 BrightMagenta = 14,
34 BrightRed = 15,
35 BrightWhite = 16,
36 BrightYellow = 17,
37}
38
39static BLACK: &str = "\x1b[30m";
40static BLUE: &str = "\x1b[34m";
41static CYAN: &str = "\x1b[36m";
42static GREEN: &str = "\x1b[32m";
43static GRAY: &str = "\x1b[90m";
44static MAGENTA: &str = "\x1b[35m";
45static RED: &str = "\x1b[31m";
46static WHITE: &str = "\x1b[37m";
47static YELLOW: &str = "\x1b[33m";
48
49static BRIGHT_BLACK: &str = "\x1b[90m";
50static BRIGHT_BLUE: &str = "\x1b[94m";
51static BRIGHT_CYAN: &str = "\x1b[96m";
52static BRIGHT_GREEN: &str = "\x1b[92m";
53static BRIGHT_MAGENTA: &str = "\x1b[95m";
54static BRIGHT_RED: &str = "\x1b[91m";
55static BRIGHT_WHITE: &str = "\x1b[97m";
56static BRIGHT_YELLOW: &str = "\x1b[93m";
57
58pub(crate) static RESET: &str = "\x1b[0m";
59
60lazy_static! {
61 static ref COLOR_MAP: HashMap<i32, &'static str> = {
62 let mut m = HashMap::new();
63 m.insert(Color::None as i32, "");
64 m.insert(Color::Black as i32, BLACK);
65 m.insert(Color::Blue as i32, BLUE);
66 m.insert(Color::Cyan as i32, CYAN);
67 m.insert(Color::Green as i32, GREEN);
68 m.insert(Color::Gray as i32, GRAY);
69 m.insert(Color::Magenta as i32, MAGENTA);
70 m.insert(Color::Red as i32, RED);
71 m.insert(Color::White as i32, WHITE);
72 m.insert(Color::Yellow as i32, YELLOW);
73
74 m.insert(Color::BrightBlack as i32, BRIGHT_BLACK);
75 m.insert(Color::BrightBlue as i32, BRIGHT_BLUE);
76 m.insert(Color::BrightCyan as i32, BRIGHT_CYAN);
77 m.insert(Color::BrightGreen as i32, BRIGHT_GREEN);
78 m.insert(Color::BrightMagenta as i32, BRIGHT_MAGENTA);
79 m.insert(Color::BrightRed as i32, BRIGHT_RED);
80 m.insert(Color::BrightWhite as i32, BRIGHT_WHITE);
81 m.insert(Color::BrightYellow as i32, BRIGHT_YELLOW);
82 return m;
83 };
84}
85
86pub fn color_text(text: &str, color: Color) -> String {
95 if color != Color::None {
96 return COLOR_MAP[&(color as i32)].to_string() + text + RESET;
97 }
98 return String::from(text)
99}
100
101impl Display for Color {
102 fn fmt(&self, f: &mut Formatter) -> std::fmt::Result {
103 let level_str = match *self {
104 Color::None => "None",
105 Color:: Black => "Black",
106 Color::Blue => "Blue",
107 Color::Cyan => "Cyan",
108 Color::Green => "Green",
109 Color::Gray => "Gray",
110 Color::Magenta => "Magenta",
111 Color::Red => "Red",
112 Color::White => "White",
113 Color::Yellow => "Yellow",
114
115 Color::BrightBlack => "BrightBlack",
116 Color::BrightBlue => "BrightBlue",
117 Color::BrightCyan => "BrightCyan",
118 Color::BrightGreen => "BrightGreen",
119 Color::BrightMagenta => "BrightMagenta",
120 Color::BrightRed => "BrightRed",
121 Color::BrightWhite => "BrightWhite",
122 Color::BrightYellow => "BrightYellow",
123 };
124 return write!(f, "{}", level_str)
125 }
126}
127
128impl TryFrom<i32> for Color {
129 type Error = &'static str;
130 fn try_from(value: i32) -> Result<Self, Self::Error> {
131 match value {
132 0 => Ok(Color::None),
133 1 => Ok(Color::Black),
134 2 => Ok(Color::Blue),
135 3 => Ok(Color::Cyan),
136 4 => Ok(Color::Green),
137 5 => Ok(Color::Gray),
138 6 => Ok(Color::Magenta),
139 7 => Ok(Color::Red),
140 8 => Ok(Color::White),
141 9 => Ok(Color::Yellow),
142
143 10 => Ok(Color::BrightBlack),
144 11 => Ok(Color::BrightBlue),
145 12 => Ok(Color::BrightCyan),
146 13 => Ok(Color::BrightGreen),
147 14 => Ok(Color::BrightMagenta),
148 15 => Ok(Color::BrightRed),
149 16 => Ok(Color::BrightWhite),
150 17 => Ok(Color::BrightYellow),
151 _ => Err("Invalid value! Please provide a value in range 0-9."),
152 }
153 }
154}
155
156impl AsRef<str> for Color {
157 fn as_ref(&self) -> &str {
158 match self {
159 Color::None => "None",
160 Color:: Black => "Black",
161 Color::Blue => "Blue",
162 Color::Cyan => "Cyan",
163 Color::Green => "Green",
164 Color::Gray => "Gray",
165 Color::Magenta => "Magenta",
166 Color::Red => "Red",
167 Color::White => "White",
168 Color::Yellow => "Yellow",
169
170 Color::BrightBlack => "BrightBlack",
171 Color::BrightBlue => "BrightBlue",
172 Color::BrightCyan => "BrightCyan",
173 Color::BrightGreen => "BrightGreen",
174 Color::BrightMagenta => "BrightMagenta",
175 Color::BrightRed => "BrightRed",
176 Color::BrightWhite => "BrightWhite",
177 Color::BrightYellow => "BrightYellow",
178 }
179 }
180}