gui.rs
1 use crate::{ 2 cam::Camera, 3 errors::{ 4 BinaryError::{self, *}, 5 DependentError::OpenCV, 6 }, 7 LandmarkDetection, Landmarks, 8 }; 9 use opencv::{core, highgui, imgproc}; 10 11 pub struct Gui { 12 window_name: String, 13 model: LandmarkDetection, 14 camera: Camera, 15 } 16 impl Gui { 17 pub fn new(window_name: &str) -> Result<Self, BinaryError> { 18 highgui::named_window(window_name, highgui::WINDOW_AUTOSIZE) 19 .map_err(|err| GUI(OpenCV(err)))?; 20 Ok(Self { 21 model: LandmarkDetection::new()?, 22 camera: Camera::default()?, 23 window_name: window_name.to_string(), 24 }) 25 } 26 pub fn run(&mut self) -> Result<(), BinaryError> { 27 loop { 28 let mut frame = self.camera.read_frame()?; 29 match self.model.detect(&mut frame)? { 30 Some(landmarks) => draw_landmarks(&mut frame, landmarks)?, 31 None => (), 32 }; 33 highgui::imshow(&self.window_name, &frame).map_err(|err| GUI(OpenCV(err)))?; 34 if highgui::wait_key(10).map_err(|err| GUI(OpenCV(err)))? == 27 { 35 break; 36 } 37 } 38 Ok(()) 39 } 40 } 41 /// Modifies a frame to draw circles at landmarks' coordinates. 42 /// 43 /// # Fields 44 /// - `frame`: The image frame to be drawn to. 45 /// - `landmarks`: A list of the landmarks' coordinates. 46 fn draw_landmarks(frame: &mut core::Mat, landmarks: Landmarks) -> Result<(), BinaryError> { 47 for point in landmarks.iter() { 48 let point = core::Point::new(point.0.try_into()?, point.1.try_into()?); 49 imgproc::circle( 50 frame, 51 point, 52 1, 53 core::Scalar::new(0.0, 255.0, 0.0, 0.0), 54 -1, 55 imgproc::LINE_8, 56 0, 57 ) 58 .map_err(|err| GUI(OpenCV(err)))?; 59 } 60 Ok(()) 61 }