diff --git a/ui-app/src/lib.rs b/ui-app/src/lib.rs index e4fee8e..108dee2 100644 --- a/ui-app/src/lib.rs +++ b/ui-app/src/lib.rs @@ -61,12 +61,23 @@ pub enum Button { B, } +#[derive(Copy, Clone, Debug, PartialEq, Format)] +pub enum FromNet { + Pong, +} + +#[derive(Copy, Clone, Debug, PartialEq, Format)] +pub enum ToNet { + Ping, +} + #[derive(Copy, Clone, Debug, PartialEq, Format)] pub enum Event { ButtonDown(Button), ButtonUp(Button), KeyDown(Key, KeyValue), KeyUp(Key), + FromNet(FromNet), } #[allow(dead_code)] @@ -131,9 +142,14 @@ pub trait Screen { fn draw(&mut self, left: usize, right: usize, top: usize, bottom: usize, data: &[u16]); } +pub trait NetTx { + fn write(&mut self, to_net: &ToNet); +} + pub trait Outputs { fn status_led(&mut self) -> &mut impl Led; fn screen(&mut self) -> &mut impl Screen; + fn net_tx(&mut self) -> &mut impl NetTx; fn log(&mut self, message: &str); } @@ -204,18 +220,23 @@ impl App { match event { Event::ButtonDown(button) => match button { Button::A => { + out.log("button a down"); self.a_down = true; + out.net_tx().write(&ToNet::Ping); } Button::B => { + out.log("button b down"); self.b_down = true; } }, Event::ButtonUp(button) => match button { Button::A => { + out.log("button a up"); self.a_down = false; } Button::B => { + out.log("button b up"); self.b_down = false; } }, @@ -227,6 +248,12 @@ impl App { Event::KeyUp(_key) => { out.log("key up"); } + + Event::FromNet(from_net) => match from_net { + FromNet::Pong => { + out.log("pong"); + } + }, } out.status_led().set(false, self.a_down, self.b_down); diff --git a/ui-app/tests/integration.rs b/ui-app/tests/integration.rs index 2652442..f627372 100644 --- a/ui-app/tests/integration.rs +++ b/ui-app/tests/integration.rs @@ -33,10 +33,22 @@ impl Screen for MockScreen { } } +#[derive(Default)] +struct MockNetTx { + last_to_net: Option, +} + +impl NetTx for MockNetTx { + fn write(&mut self, to_net: &ToNet) { + self.last_to_net = Some(*to_net); + } +} + #[derive(Default)] struct MockOutputs { status_led: MockLed, screen: MockScreen, + net_tx: MockNetTx, last_message: String, } @@ -49,6 +61,10 @@ impl Outputs for MockOutputs { &mut self.screen } + fn net_tx(&mut self) -> &mut impl NetTx { + &mut self.net_tx + } + fn log(&mut self, message: &str) { self.last_message = message.into(); } @@ -130,3 +146,13 @@ fn key_logging() { app.handle(Event::KeyUp(Key::A), &mut outputs); assert_eq!(outputs.last_message, "key up"); } + +#[test] +fn button_a_sends_ping() { + let mut outputs = MockOutputs::default(); + let mut app = App::new(); + app.start(&mut outputs); + + app.handle(Event::ButtonDown(Button::A), &mut outputs); + assert_eq!(outputs.net_tx.last_to_net, Some(ToNet::Ping)); +} diff --git a/ui-stm32/Cargo.toml b/ui-stm32/Cargo.toml index 23bb70c..6336fe8 100644 --- a/ui-stm32/Cargo.toml +++ b/ui-stm32/Cargo.toml @@ -22,11 +22,17 @@ embassy-executor = { version = "0.8.0", features = ["arch-cortex-m", "executor-t embassy-futures = { version = "0.1.1", features = ["defmt"] } embassy-stm32 = { version = "0.3.0", features = ["defmt", "stm32f405rg", "memory-x", "time-driver-tim1", "exti", "chrono"] } embassy-time = { version = "0.4.0", features = ["defmt", "defmt-timestamp-uptime", "tick-hz-32_768"] } - -heapless = { version = "0.8", default-features = false } panic-probe = { version = "1.0.0", features = ["print-defmt"] } embassy-sync = { version = "0.7.1", features = ["defmt"] } num_enum = { version = "0.7.4", default-features = false } +hex = { version = "0.4.3", default-features = false } +heapless = { version = "0.9.1", features = ["defmt"] } +embedded-io-async = "0.6.1" +embedded-io = { version = "0.6.1", default-features = false } [profile.release] debug = 2 + +[profile.dev] +debug = 2 +opt-level = "s" diff --git a/ui-stm32/src/board/ev12.rs b/ui-stm32/src/board/ev12.rs index af90eff..30ddaf8 100644 --- a/ui-stm32/src/board/ev12.rs +++ b/ui-stm32/src/board/ev12.rs @@ -1,19 +1,29 @@ -use super::{Button, Keyboard, Screen, StatusLed}; +use super::{Button, Keyboard, NetTx, Screen, StatusLed}; use embassy_stm32::{ + bind_interrupts, exti::ExtiInput, gpio::{Input, Level, Output, Pull, Speed}, + mode::Async, + peripherals, spi::Spi, + usart::{self, UartRx, UartTx}, }; use ui_app::{Led, Outputs}; pub struct Board { status_led: StatusLed, screen: Screen, - pub ptt_button: Option