From 86b4b227bf1cd43de0580b55c81da27eb467218e Mon Sep 17 00:00:00 2001 From: Hexa Dust Date: Fri, 18 Jul 2025 20:31:23 +0100 Subject: [PATCH] deeper stack support and state refactoring --- src/display.rs | 31 ------- src/main.rs | 238 +++++++++++++++++++++++++------------------------ 2 files changed, 121 insertions(+), 148 deletions(-) diff --git a/src/display.rs b/src/display.rs index 4c5d744..9ba3dc6 100644 --- a/src/display.rs +++ b/src/display.rs @@ -87,8 +87,6 @@ pub enum SegmentState { Minus, Prompt(bool), Dot, - O, - P, Off, } @@ -181,21 +179,6 @@ impl SegmentState { seg.set_dp() } } - SegmentState::O => { - seg.set_a(); - seg.set_b(); - seg.set_c(); - seg.set_d(); - seg.set_e(); - seg.set_f(); - } - SegmentState::P => { - seg.set_a(); - seg.set_b(); - seg.set_g(); - seg.set_e(); - seg.set_f(); - } SegmentState::Off => (), } } @@ -271,20 +254,6 @@ impl DispalyState { SegmentState::Off, ]) } - - pub fn operation(&mut self) { - self.set([ - SegmentState::Off, - SegmentState::Off, - SegmentState::Off, - SegmentState::Off, - SegmentState::O, - SegmentState::P, - SegmentState::Off, - SegmentState::Off, - SegmentState::Off, - ]) - } } // Show data on segment display diff --git a/src/main.rs b/src/main.rs index 093201d..e070df4 100644 --- a/src/main.rs +++ b/src/main.rs @@ -34,6 +34,8 @@ pub const DISPLAY_SEGMENT_SIG_MINUS: usize = 0; pub const DISPLAY_SEGMENTS_EXP: usize = 2; pub const DISPLAY_SEGMENT_EXP_MINUS: usize = 6; +type Calc = StackCalc; + struct IOSelect<'p> { display_no: usize, pin: &'p mut Pin, @@ -206,10 +208,118 @@ enum State { EnterSignificant, EnterExponent, EnterOperation, - Result, Err { timeout: usize }, } +impl State { + fn on_key( + &self, + key: KeyPress, + number_input: &mut NumberInput, + calc: &mut Calc, + ) -> Result { + match self { + State::EnterSignificant => match key { + KeyPress::C => { + number_input.reset(); + calc.reset(); + Ok(State::EnterSignificant) + } + KeyPress::Num(val) => { + number_input.input(val)?; + Ok(State::EnterSignificant) + } + KeyPress::Minus => { + number_input.toggle_minus(); + Ok(State::EnterSignificant) + } + KeyPress::E => { + number_input.enter_exponent(); + Ok(State::EnterExponent) + } + _ => Ok(State::EnterSignificant), + }, + State::EnterExponent => match key { + KeyPress::C => { + number_input.reset(); + calc.reset(); + Ok(State::EnterSignificant) + } + KeyPress::Num(val) => { + number_input.input(val)?; + Ok(State::EnterExponent) + } + KeyPress::Minus => { + number_input.toggle_minus(); + Ok(State::EnterExponent) + } + KeyPress::E => { + number_input.done(); + match calc.push(number_input.to_decimal()) { + Ok(()) => Ok(State::EnterOperation), + Err(_) => Err(()), + } + } + _ => Ok(State::EnterExponent), + }, + State::EnterOperation => match key { + KeyPress::Up => todo!(), + KeyPress::C => { + number_input.reset(); + calc.reset(); + Ok(State::EnterSignificant) + } + KeyPress::Num(_) => todo!(), + KeyPress::Mul => match calc.mul() { + Ok(dec) => { + number_input.set_result(dec)?; + Ok(State::EnterOperation) + } + Err(_) => Err(()), + }, + KeyPress::Div => match calc.div() { + Ok(dec) => { + number_input.set_result(dec)?; + Ok(State::EnterOperation) + } + Err(_) => Err(()), + }, + KeyPress::Plus => match calc.add() { + Ok(dec) => { + number_input.set_result(dec)?; + Ok(State::EnterOperation) + } + Err(_) => Err(()), + }, + KeyPress::Minus => match calc.sub() { + Ok(dec) => { + number_input.set_result(dec)?; + Ok(State::EnterOperation) + } + Err(_) => Err(()), + }, + KeyPress::Down => todo!(), + KeyPress::E => { + if calc.is_full() { + Err(()) + } else { + number_input.reset(); + Ok(State::EnterSignificant) + } + } + }, + State::Err { timeout } => match key { + KeyPress::C => { + number_input.reset(); + calc.reset(); + Ok(State::EnterSignificant) + } + _ => Ok(State::Err { timeout: *timeout }), + }, + } + } +} + #[arduino_hal::entry] fn main() -> ! { let dp = arduino_hal::Peripherals::take().unwrap(); @@ -250,7 +360,7 @@ fn main() -> ! { let mut display = DispalyState::default(); number_input.show(&mut display); - let mut calc = StackCalc::::default(); + let mut calc = Calc::default(); let mut state = State::EnterSignificant; loop { @@ -284,132 +394,26 @@ fn main() -> ! { if let Some(key) = debounce.input(last_key_readout) { ufmt::uwriteln!(&mut serial, "key: {:?} state: {:?}", key, state).unwrap_infallible(); - let res = match &mut state { - State::Result => match key { - KeyPress::C => { - number_input.reset(); - calc.reset(); - state = State::EnterSignificant; - Ok(()) + match state.on_key(key, &mut number_input, &mut calc) { + Ok(new_state) => state = new_state, + Err(()) => { + state = State::Err { + timeout: ERROR_TIMEOUT, } - KeyPress::E => { - number_input.reset(); - state = State::EnterSignificant; - Ok(()) - } - _ => Ok(()), - }, - State::EnterSignificant => match key { - KeyPress::C => { - number_input.reset(); - calc.reset(); - Ok(()) - } - KeyPress::Num(val) => number_input.input(val), - KeyPress::Minus => Ok(number_input.toggle_minus()), - KeyPress::E => { - number_input.enter_exponent(); - state = State::EnterExponent; - Ok(()) - } - _ => Ok(()), - }, - State::EnterExponent => match key { - KeyPress::C => { - number_input.reset(); - calc.reset(); - state = State::EnterSignificant; - Ok(()) - } - KeyPress::Num(val) => number_input.input(val), - KeyPress::Minus => Ok(number_input.toggle_minus()), - KeyPress::E => { - number_input.done(); - match calc.push(number_input.to_decimal()) { - Ok(()) => { - number_input.reset(); - state = if calc.is_full() { - State::EnterOperation - } else { - State::EnterSignificant - }; - Ok(()) - } - Err(_) => Err(()), - } - } - _ => Ok(()), - }, - State::EnterOperation => match key { - KeyPress::Up => todo!(), - KeyPress::C => { - number_input.reset(); - calc.reset(); - state = State::EnterSignificant; - Ok(()) - } - KeyPress::Num(_) => todo!(), - KeyPress::Mul => match calc.mul() { - Ok(dec) => { - state = State::Result; - number_input.set_result(dec) - } - Err(_) => Err(()), - }, - KeyPress::Div => match calc.div() { - Ok(dec) => { - state = State::Result; - number_input.set_result(dec) - } - Err(_) => Err(()), - }, - KeyPress::Plus => match calc.add() { - Ok(dec) => { - state = State::Result; - number_input.set_result(dec) - } - Err(_) => Err(()), - }, - KeyPress::Minus => match calc.sub() { - Ok(dec) => { - state = State::Result; - number_input.set_result(dec) - } - Err(_) => Err(()), - }, - KeyPress::Down => todo!(), - KeyPress::E => todo!(), - }, - State::Err { .. } => match key { - KeyPress::C => { - number_input.reset(); - calc.reset(); - state = State::EnterSignificant; - Ok(()) - } - _ => Ok(()), - }, - }; - if res.is_err() { - state = State::Err { - timeout: ERROR_TIMEOUT, - }; + } } - ufmt::uwriteln!(&mut serial, "state: {:?} stack: {}", state, calc.len()) .unwrap_infallible(); - match state { - State::Result | State::EnterSignificant | State::EnterExponent => { + match &state { + State::EnterSignificant | State::EnterExponent | State::EnterOperation => { number_input.show(&mut display) } - State::EnterOperation => { - display.operation(); - } State::Err { .. } => { display.error(); } } } + arduino_hal::delay_ms(1); }