virt_ic/chip/
outputs.rs

1pub mod helpers;
2
3pub use helpers::*;
4
5use crate::{generate_chip, State};
6
7use super::{ChipBuilder, ChipRunner, ChipSet, Pin, PinType};
8
9/// Simple 7-Segment display
10///
11/// # Diagram
12/// ```txt
13///     ------------
14///  a -|1        9|- VCC
15///  b -|2   ──    |
16///  c -|3  |  |   |
17///  d -|4   ──    |
18///  e -|5  |  |   |
19///  f -|6   ──    |
20///  g -|7        8|- GND
21///     ------------
22/// ```
23///
24/// pins-to-segment map:
25/// ```txt
26///    a
27///   ───
28/// f|   |b
29///   ─g─
30/// e|   |c
31///   ───
32///    d
33/// ```
34///
35#[derive(Debug, Clone)]
36#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
37pub struct SegmentDisplay {
38    pub vcc: Pin,
39    pub gnd: Pin,
40    pub a: Pin,
41    pub b: Pin,
42    pub c: Pin,
43    pub d: Pin,
44    pub e: Pin,
45    pub f: Pin,
46    pub g: Pin,
47}
48
49impl SegmentDisplay {
50    pub const VCC: usize = 9;
51    pub const GND: usize = 8;
52    pub const A: usize = 1;
53    pub const B: usize = 2;
54    pub const C: usize = 3;
55    pub const D: usize = 4;
56    pub const E: usize = 5;
57    pub const F: usize = 6;
58    pub const G: usize = 7;
59}
60
61generate_chip!(
62    SegmentDisplay,
63    vcc: SegmentDisplay::VCC,
64    gnd: SegmentDisplay::GND,
65    a: SegmentDisplay::A,
66    b: SegmentDisplay::B,
67    c: SegmentDisplay::C,
68    d: SegmentDisplay::D,
69    e: SegmentDisplay::E,
70    f: SegmentDisplay::F,
71    g: SegmentDisplay::G
72);
73
74impl ChipBuilder<ChipSet> for SegmentDisplay {
75    fn build() -> ChipSet {
76        ChipSet::SegmentDisplay(SegmentDisplay {
77            vcc: Pin::from(PinType::Input),
78            gnd: Pin::from(PinType::Output),
79            a: Pin::from(PinType::Input),
80            b: Pin::from(PinType::Input),
81            c: Pin::from(PinType::Input),
82            d: Pin::from(PinType::Input),
83            e: Pin::from(PinType::Input),
84            f: Pin::from(PinType::Input),
85            g: Pin::from(PinType::Input),
86        })
87    }
88}
89
90impl ChipRunner for SegmentDisplay {
91    fn run(&mut self, _: std::time::Duration) {
92        if self.vcc.state.into() {
93            self.gnd.state = State::Low;
94        }
95    }
96}
97
98impl ToString for SegmentDisplay {
99    fn to_string(&self) -> String {
100        if self.vcc.state.into() {
101            format!(
102                " {} \n{}  {}\n {} \n{}  {}\n {} ",
103                if self.a.state.into() { "──" } else { "  " },
104                if self.f.state.into() { "|" } else { " " },
105                if self.b.state.into() { "|" } else { " " },
106                if self.g.state.into() { "──" } else { "  " },
107                if self.e.state.into() { "|" } else { " " },
108                if self.c.state.into() { "|" } else { " " },
109                if self.d.state.into() { "──" } else { "  " }
110            )
111        } else {
112            String::from("    \n    \n    \n    \n    ")
113        }
114    }
115}
116
117impl SegmentDisplay {
118    pub fn as_char(&self) -> char {
119        if self.vcc.state.into() {
120            let segments = Pin::read(&[
121                &self.g, &self.f, &self.e, &self.d, &self.c, &self.b, &self.a,
122            ]);
123            match segments {
124                0b0000000 => ' ',
125                0b1111110 => '0',
126                0b0110000 => '1',
127                0b1101101 => '2',
128                0b1111001 => '3',
129                0b0110011 => '4',
130                0b1011011 => '5',
131                0b1011111 => '6',
132                0b1110000 | 0b1110010 => '7',
133                0b1111111 => '8',
134                0b1111011 => '9',
135                0b1110111 => 'A',
136                0b0011111 => 'b',
137                0b1001110 => 'C',
138                0b0001101 => 'c',
139                0b0111101 => 'd',
140                0b1001111 => 'E',
141                0b1000111 => 'F',
142                0b1011110 => 'G',
143                0b0110111 => 'H',
144                0b0010111 => 'h',
145                0b0111100 => 'J',
146                0b0001110 => 'L',
147                0b0001100 => 'l',
148                0b1110110 => 'M',
149                0b0010101 => 'n',
150                0b0011101 => 'o',
151                0b1100111 => 'p',
152                0b1110011 => 'q',
153                0b0001111 => 't',
154                0b0111110 => 'U',
155                0b0011100 => 'u',
156                0b0111011 => 'y',
157                0b0001000 => '_',
158                0b0000001 => '-',
159                0b0001001 | 0b1001000 => '=',
160                _ => '?',
161            }
162        } else {
163            ' '
164        }
165    }
166}