VigilantLamp/extra/
color.rs

1/// Representation of a color
2pub struct Color (u32);
3
4// CONSTANTS
5impl Color {
6    pub const WHITE : Color = Color(u32::MAX);
7    pub const BLACK : Color = Color(255);
8    pub const TRANSPARENT : Color = Color(0);
9
10    pub const RED : Color = Color(0xFF0000FF);
11    pub const GREEN : Color = Color(0x00FF00FF);
12    pub const BLUE : Color = Color(0x0000FFFF);
13
14    pub const PINK : Color = Color(0xFFAFAFFF);
15    pub const ORANGE : Color = Color(0xFFC800FF);
16    pub const YELLOW : Color = Color(0xFFFF00FF);
17    pub const CYAN : Color = Color(0x00FFFFFF);
18}
19
20// INITIALIZERS
21impl Color {
22    pub fn from_rgba (r: u8, g: u8, b: u8, a: u8) -> Color {
23        let alpha = a as u32;
24        let blue = (b as u32) << 8;
25        let green = (g as u32) << 16;
26        let red = (r as u32) << 24;
27
28        Color(red | green | blue | alpha)
29    }
30
31    pub fn from_rgb (r: u8, g: u8, b: u8) -> Color {
32        let blue = (b as u32) << 8;
33        let green = (g as u32) << 16;
34        let red = (r as u32) << 24;
35
36        Color(red | green | blue | 255)
37    }
38
39    pub fn from_hex (value: &str) -> Option<Color> {
40        let hex : &str;
41
42        if value.chars().next().unwrap() == '#' {
43            hex = &value[1..]
44        } else {
45            hex = value;
46        }
47
48        if hex.len() == 6 {
49            let parse = u32::from_str_radix(hex, 16);
50            match parse {
51                Ok(x) => return Some(Color(x << 8)),
52                Err(_) => return None
53            }
54            
55        } else if hex.len() == 8 {
56            let parse = u32::from_str_radix(hex, 16);
57            match parse {
58                Ok(x) => return Some(Color(x)),
59                Err(_) => return None
60            }
61        }
62
63        None
64    }
65}
66
67// METHODS
68impl Color {
69    pub fn alpha (&self) -> u8 {
70        (self.0 & 255) as u8
71    }
72
73    pub fn alpha_f32 (&self) -> f32 {
74        (self.alpha() as f32) / 255.
75    }
76
77    // RGB
78    pub fn red (&self) -> u8 {
79        ((self.0 >> 24) & 255) as u8
80    }
81
82    pub fn green (&self) -> u8 {
83        ((self.0 >> 16) & 255) as u8
84    }
85    
86    pub fn blue (&self) -> u8 {
87        ((self.0 >> 8) & 255) as u8
88    }
89
90    pub fn red_f32 (&self) -> f32 {
91        (self.red() as f32) / 255.
92    }
93
94    pub fn green_f32 (&self) -> f32 {
95        (self.green() as f32) / 255.
96    }
97
98    pub fn blue_f32 (&self) -> f32 {
99        (self.blue() as f32) / 255.
100    }
101
102    // HSV
103    pub fn hue (&self) -> f32 {
104        let r = self.red_f32();
105        let g = self.green_f32();
106        let b = self.blue_f32();
107
108        let min = r.min(g.min(b));
109        let max = r.max(g.max(b));
110        let delta = max - min;
111
112        if delta == 0. {
113            0.
114        } else if max == r {
115            (((g - b) / delta) % 6.) / 6.
116        } else if max == g {
117            (((b - r) / delta) + 2.) / 6.
118        } else {
119            (((r - g) / delta) + 4.) / 6.
120        }
121    }
122
123    pub fn saturation (&self) -> f32 {
124        let r = self.red_f32();
125        let g = self.green_f32();
126        let b = self.blue_f32();
127
128        let max = r.max(g.max(b));
129        if max == 0. {
130            return 0.;
131        }
132
133        let min = r.min(g.min(b));
134        let delta = max - min;
135
136        delta / max
137    }
138
139    pub fn brightness (&self) -> f32 {
140        let r = self.red_f32();
141        let g = self.green_f32();
142        let b = self.blue_f32();
143
144        r.max(g.max(b))
145    } 
146
147    // COMPONENTS
148    pub fn rgba_components (&self) -> [u8;4] {
149        [self.red(), self.green(), self.blue(), self.alpha()]
150    }
151
152    pub fn argb_components (&self) -> [u8;4] {
153        [self.alpha(), self.red(), self.green(), self.blue()]
154    }
155
156    pub fn rgb_components (&self) -> [u8;3] {
157        [self.red(), self.green(), self.blue()]
158    }
159
160    pub fn rgba_components_f32 (&self) -> [f32;4] {
161        [self.red_f32(), self.green_f32(), self.blue_f32(), self.alpha_f32()]
162    }
163
164    pub fn argb_components_f32 (&self) -> [f32;4] {
165        [self.alpha_f32(), self.red_f32(), self.green_f32(), self.blue_f32()]
166    }
167
168    pub fn rgb_components_f32 (&self) -> [f32;3] {
169        [self.red_f32(), self.green_f32(), self.blue_f32()]
170    }
171
172    pub fn hsv_components (&self) -> [f32;3] {
173        let r = self.red_f32();
174        let g = self.green_f32();
175        let b = self.blue_f32();
176
177        let min = r.min(g.min(b));
178        let max = r.max(g.max(b));
179        let delta = max - min;
180
181        let hue = 
182            if delta == 0. {
183                0.
184            } else if max == r {
185                (((g - b) / delta) % 6.) / 6.
186            } else if max == g {
187                (((b - r) / delta) + 2.) / 6.
188            } else {
189                (((r - g) / delta) + 4.) / 6.
190            };
191
192        let saturation = if max == 0. { 0. } else { delta / max };
193        [hue, saturation, max]
194    }
195}