diff options
author | Matthias P. Braendli <matthias.braendli@mpb.li> | 2020-07-17 15:39:45 +0200 |
---|---|---|
committer | Matthias P. Braendli <matthias.braendli@mpb.li> | 2020-07-17 15:39:45 +0200 |
commit | 9be7009e6eed7e4d0c54c07a919b46642f4b3a6f (patch) | |
tree | 84f2f6744062ed99d3392016dfad80c3fb2af376 /sw/demo1/src/ui.rs | |
parent | cd3d884aabc50fa577d0914bbd2cc8299dd7ae11 (diff) | |
download | picardy-9be7009e6eed7e4d0c54c07a919b46642f4b3a6f.tar.gz picardy-9be7009e6eed7e4d0c54c07a919b46642f4b3a6f.tar.bz2 picardy-9be7009e6eed7e4d0c54c07a919b46642f4b3a6f.zip |
SW: handle buttons
Diffstat (limited to 'sw/demo1/src/ui.rs')
-rw-r--r-- | sw/demo1/src/ui.rs | 151 |
1 files changed, 151 insertions, 0 deletions
diff --git a/sw/demo1/src/ui.rs b/sw/demo1/src/ui.rs new file mode 100644 index 0000000..76f89b9 --- /dev/null +++ b/sw/demo1/src/ui.rs @@ -0,0 +1,151 @@ +/* + The MIT License (MIT) + + Copyright (c) 2020 Matthias P. Braendli + + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be included in all + copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + SOFTWARE. +*/ + +use stm32f1xx_hal::{ + prelude::*, + adc, + rcc::{APB2, Clocks}, + stm32::ADC1, + gpio::gpiob::*, + gpio::gpioc::*, + gpio::{Analog, Input, PullUp}, +}; + +use embedded_hal::digital::v2::InputPin; + +#[derive(PartialEq, Eq, Clone, Copy)] +pub enum ButtonPress { + A, + B, + C, + D, + E, + F, + G, + ENC, +} + +pub struct UI { + btn0_hist : [u16; 3], + btn1_hist : [u16; 3], + + btn0_ch : PB1<Analog>, + btn1_ch : PB0<Analog>, + + btn2 : PB12<Input<PullUp>>, + btn3 : PB13<Input<PullUp>>, + + btn_enc : PC15<Input<PullUp>>, + + adc : adc::Adc<ADC1>, +} + +impl UI { + pub fn new(pb0: PB0<Analog>, pb1: PB1<Analog>, adc1: ADC1, mut apb2: &mut APB2, clocks: &Clocks, pb12: PB12<Input<PullUp>>, pb13: PB13<Input<PullUp>>, pc15 : PC15<Input<PullUp>>) -> UI { + + let adc1 = adc::Adc::adc1(adc1, &mut apb2, *clocks); + + UI { + btn0_hist : [4095; 3], + btn1_hist : [4095; 3], + btn0_ch : pb1, + btn1_ch : pb0, + btn2 : pb12, + btn3 : pb13, + btn_enc : pc15, + adc : adc1, + } + } + + pub fn read_buttons(&mut self) -> Option<ButtonPress> { + // Debounce BTN0 + let btn0_value: u16 = self.adc.read(&mut self.btn0_ch).unwrap(); + + self.btn0_hist[2] = self.btn0_hist[1]; + self.btn0_hist[1] = self.btn0_hist[0]; + self.btn0_hist[0] = btn0_value; + + let mut btn0 = [None; 3]; + for (i, &v) in self.btn0_hist.iter().enumerate() { + btn0[i] = + if v > 3050 { + None + } + else if v > 1650 { + Some(ButtonPress::B) + } + else if v > 675 { + Some(ButtonPress::C) + } + else { + Some(ButtonPress::D) + }; + } + + if btn0.iter().all(|&v| v != None && v == btn0[0]) { + return btn0[0]; + } + + + // Debounce BTN1 + let btn1_value: u16 = self.adc.read(&mut self.btn1_ch).unwrap(); + + self.btn1_hist[2] = self.btn1_hist[1]; + self.btn1_hist[1] = self.btn1_hist[0]; + self.btn1_hist[0] = btn1_value; + + + let mut btn1 = [None; 3]; + for (i, &v) in self.btn1_hist.iter().enumerate() { + btn1[i] = + if v > 3050 { + None + } + else if v > 675 { + Some(ButtonPress::F) + } + else { + Some(ButtonPress::A) + }; + } + + if btn1.iter().all(|&v| v != None && v == btn1[0]) { + return btn1[0]; + } + + if self.btn2.is_low().unwrap() { + return Some(ButtonPress::E) + } + + if self.btn3.is_low().unwrap() { + return Some(ButtonPress::G) + } + + if self.btn_enc.is_low().unwrap() { + return Some(ButtonPress::ENC) + } + + None + } +} |