1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
/// Represents a color mode that can be applied to the [`blink(1)`] LED light.
///
/// [`blink(1)`]: https://blink1.thingm.com
#[derive(Debug, Copy, Clone, PartialEq)]
pub enum Color {
    Three(u8, u8, u8),
    Red,
    Green,
    Blue,
}

impl Color {
    /// Returns a three element tuple of bytes representing a value of the red, green and blue
    /// components of a color in the0-255 range.
    pub fn rgb(self) -> (u8, u8, u8) {
        match self {
            Color::Three(red, green, blue) => (red, green, blue),
            Color::Red => (0xff, 0x00, 0x00),
            Color::Green => (0x00, 0xff, 0x00),
            Color::Blue => (0x00, 0x00, 0xff),
        }
    }
}

impl From<&str> for Color {
    fn from(input: &str) -> Self {
        match input {
            "red" => Color::Red,
            "green" => Color::Green,
            "blue" => Color::Blue,
            _ => Color::Three(0x00, 0x00, 0x00),
        }
    }
}

#[cfg(test)]
mod tests {
    use super::Color::{Blue, Green, Red, Three};

    #[test]
    fn test_red() {
        let r = Red;
        assert_eq!(r, Red);
        assert_eq!(r.rgb(), r.rgb());
        assert_eq!(r.rgb(), (0xff, 0x00, 0x00));
    }

    #[test]
    fn test_green() {
        let g = Green;
        assert_eq!(g, Green);
        assert_eq!(g.rgb(), g.rgb());
        assert_eq!(g.rgb(), (0x00, 0xff, 0x00));
    }

    #[test]
    fn test_blue() {
        let b = Blue;
        assert_eq!(b, Blue);
        assert_eq!(b.rgb(), b.rgb());
        assert_eq!(b.rgb(), (0x00, 0x00, 0xff));
    }

    #[test]
    fn test_three() {
        let c = Three(0x11, 0xaa, 0xee);
        assert_eq!(c, Three(0x11, 0xaa, 0xee));
        assert_eq!(c.rgb(), c.rgb());
        assert_eq!(c.rgb(), (0x11, 0xaa, 0xee));
    }
}