diff --git a/src/main.rs b/src/main.rs index 40cc462..d619fe8 100644 --- a/src/main.rs +++ b/src/main.rs @@ -61,7 +61,9 @@ fn main() -> Result<(), ProgramError> { // I do not care if the web ui crashes let _web_ui_handle = thread::spawn(move || -> Result<(), io::Error> { - webui::start(h) + let ret = webui::start(h); + println!("Webui dead"); + ret // TODO: Do not join -- this is just because we are running on a computer with no spi env }) .join()?; diff --git a/src/pattern.rs b/src/pattern.rs index ffc11e8..e8fe8ba 100644 --- a/src/pattern.rs +++ b/src/pattern.rs @@ -15,24 +15,32 @@ pub use orb::Orb; pub use solid::Solid; #[derive(Deserialize, Debug)] -enum PatternParameters { - Collide(Rgb, Rgb, Rgb), -} - pub enum PatternParameters { Collide(Rgb, Rgb, Rgb), - Fade(Rgb), - MovingPixel(Rgb), + Fade((Rgb,)), + MovingPixel((Rgb,)), MovingRainbow(u8, bool), Orb(Rgb, u8, u8), - Solid(Rgb), + Solid((Rgb,)), } -pub trait Pattern: std::fmt::Debug { +impl PatternParameters { + pub fn to_pattern(&self) -> Box { + match self { + PatternParameters::Collide(l, r, c) => Box::new(Collide::new(*l, *r, *c)), + PatternParameters::Fade((c,)) => Box::new(Fade::new(*c)), + PatternParameters::MovingPixel((c,)) => Box::new(MovingPixel::new(*c)), + PatternParameters::MovingRainbow(w, f) => Box::new(MovingRainbow::new(*w, *f)), + PatternParameters::Orb(c, x, y) => Box::new(Orb::new(*c, *x, *y)), + PatternParameters::Solid((c,)) => Box::new(Solid::new(*c)), + } + } +} + +pub trait Pattern: std::fmt::Debug + Send + Sync { fn init(&mut self, num_lights: u16) -> Result<(), ()>; fn step(&mut self) -> Result; fn get_strip(&self) -> &[Rgb]; - // fn get_strip_mut(&mut self) -> &[Rgb]; } // #[cfg(test)] diff --git a/src/pattern/moving_pixel.rs b/src/pattern/moving_pixel.rs index a8694ee..94e4945 100644 --- a/src/pattern/moving_pixel.rs +++ b/src/pattern/moving_pixel.rs @@ -26,7 +26,7 @@ impl Pattern for MovingPixel { let len = self.num_lights; self.lights_buf.swap( self.step.rem_euclid(len).into(), - self.step.saturating_add(1).saturating_mul(3).into(), + self.step.saturating_add(1).rem_euclid(len).into(), ); self.step = self.step.wrapping_add(1); Ok(true) diff --git a/src/webui.rs b/src/webui.rs index b580384..d0f2548 100644 --- a/src/webui.rs +++ b/src/webui.rs @@ -1,21 +1,25 @@ use crate::color::Rgb; use crate::pattern; use crate::strip; -use actix_web::web::Form; +use actix_web::web::{Form, JsonConfig}; use actix_web::{get, post, web, App, HttpRequest, HttpServer, Responder, Result}; // use actix_web::error::InternalError; +use actix_web_static_files; +use pattern::{Pattern, PatternParameters}; use rust_embed::RustEmbed; use serde::Deserialize; use std::io; use std::str::FromStr; use std::sync::{Arc, Mutex}; +include!(concat!(env!("OUT_DIR"), "/generated.rs")); + use std::sync::mpsc::Sender; // TODO: Pre-compute binary somehow? So do not have to unwrap -#[derive(RustEmbed)] -#[folder = "html/"] -struct Asset; +// #[derive(RustEmbed)] +// #[folder = "html/"] +// struct Asset; struct AppState { strip_tx: Arc>>, @@ -32,20 +36,14 @@ async fn set_color( data: web::Data, params: web::Json, ) -> Result { - println!("{:?}", params); - let pattern = match params.0 { - PatternParameters::Collide(l, r, c) => pattern::Collide::new(l, r, c), - }; + println!("Got params: {:?}", params); data.strip_tx .lock() .or(Err(io::Error::new( io::ErrorKind::Other, "Failed to get a lock", )))? - .send(strip::Message::ChangePattern(Box::new( - // pattern::Solid::new(Rgb::from_str(¶ms.color).or(Err(io::Error::new(io::ErrorKind::Other, "Failed to parse")))?), - pattern, - ))) + .send(strip::Message::ChangePattern(params.0.to_pattern())) .or(Err(io::Error::new( io::ErrorKind::Other, "Failed to send to channel", @@ -53,27 +51,23 @@ async fn set_color( Ok(format!("{:?}", params)) } -#[get("/")] -async fn index(_data: web::Data, _req: HttpRequest) -> impl Responder { - // TODO: This is probably the ugliest possible way to do it. Make this better - String::from_utf8((&Asset::get("index.html").unwrap().data).to_vec()).unwrap() -} - #[actix_web::main] pub async fn start(tx: Sender) -> std::io::Result<()> { println!("Starting webui"); HttpServer::new(move || { + let generated = generate(); App::new() .data(AppState { strip_tx: Arc::new(Mutex::new(tx.clone())), }) - .service(index) - .service(set_color) - // App::new() - // .route("/", web::get().to(greet)) - // .route("/{name}", web::get().to(greet)) + .service( + web::scope("/api") + // .app_data(JsonConfig::default()) + .service(set_color), + ) + .service(actix_web_static_files::ResourceFiles::new("/", generated)) }) - .bind(("127.0.0.1", 8080))? + .bind(("0.0.0.0", 8080))? .run() .await }