use anyhow::bail; use image::{GenericImageView, ImageReader}; const TOAST_TIME_SECONDS: u64 = 15; const CENTER_X: f64 = 100.0; const CENTER_Y: f64 = 100.0; const BREAD_HEIGHT: f64 = 12.0; const IDLE_HEIGHT: f64 = BREAD_HEIGHT + 5.0; const PIXEL_SIZE_MM: f64 = 3.0; fn main() -> anyhow::Result<()> { let img = ImageReader::open("/home/stephen/Downloads/scd31-qr.png")?.decode()?; preamble(); for x in 0..img.width() { for y in 0..img.height() { let p = img.get_pixel(x, y); match p.0 { [0, 0, 0, 255] => { toast( x as f64 - (img.width() as f64 / 2.0), y as f64 - (img.height() as f64 / 2.0), ); } [255, 255, 255, 255] => { // white } _ => bail!("Pixel was not entirely black nor entirely white: {:?}", p), } } } Ok(()) } fn preamble() { println!( r#" G28 ; home G90 ; absolute positioning G0 Z{IDLE_HEIGHT} G0 X{CENTER_X} Y{CENTER_Y} M109 S230 ; heat hotend to 230C and wait "# ); } fn toast(x: f64, y: f64) { println!( r#" G0 X{:.2} Y{:.2}; G0 Z{BREAD_HEIGHT}; G4 S{TOAST_TIME_SECONDS} ; wait G0 Z{IDLE_HEIGHT}; "#, x * PIXEL_SIZE_MM + CENTER_X, y * PIXEL_SIZE_MM + CENTER_Y ); }