From 447023527502f4318e7c8b842620ad1f7823996c Mon Sep 17 00:00:00 2001 From: Michael Zhang Date: Sun, 30 Sep 2018 17:37:54 -0500 Subject: [PATCH] yay all fixed --- imlib2/src/image.rs | 2 +- imlib2/src/lib.rs | 33 +++++++++++++++++++++++++ src/capture.rs | 3 +++ src/gui.rs | 59 ++++++++++++++++++++++++--------------------- 4 files changed, 69 insertions(+), 28 deletions(-) diff --git a/imlib2/src/image.rs b/imlib2/src/image.rs index a99de23..a236101 100644 --- a/imlib2/src/image.rs +++ b/imlib2/src/image.rs @@ -8,7 +8,7 @@ use Error; /// A simple wrapper around Imlib_Image pub struct Image { - inner: im::Imlib_Image, + pub(crate) inner: im::Imlib_Image, } impl Image { diff --git a/imlib2/src/lib.rs b/imlib2/src/lib.rs index fe1a031..17501ea 100644 --- a/imlib2/src/lib.rs +++ b/imlib2/src/lib.rs @@ -35,3 +35,36 @@ pub fn context_set_image(image: &Image) { pub fn image_get_data() -> *mut u32 { unsafe { imlib2_sys::imlib_image_get_data_for_reading_only() } } + +/// Create cropped image +pub fn create_cropped_image(x: i32, y: i32, width: u32, height: u32) -> Result { + let inner = + unsafe { imlib2_sys::imlib_create_cropped_image(x, y, width as i32, height as i32) }; + if inner.is_null() { + return Err(Error::Error); + } + Ok(Image { inner }) +} + +/// Create scaled cropped image +pub fn create_scaled_cropped_image( + x: i32, + y: i32, + width: u32, + height: u32, +) -> Result { + let inner = unsafe { + imlib2_sys::imlib_create_cropped_scaled_image( + x, + y, + width as i32, + height as i32, + width as i32, + height as i32, + ) + }; + if inner.is_null() { + return Err(Error::Error); + } + Ok(Image { inner }) +} diff --git a/src/capture.rs b/src/capture.rs index cd98fa4..1a56446 100644 --- a/src/capture.rs +++ b/src/capture.rs @@ -1,6 +1,7 @@ use errors::ScreenshotError; use gui::GUI; +use imlib2; use options::{Options, Region}; /// The main capture routine. @@ -13,6 +14,8 @@ pub fn capture(opt: &Options) -> Result<(), ScreenshotError> { }; let capture = gui.capture_window(&opt, window_to_capture)?; + + imlib2::context_set_image(&capture); capture.save_image(&opt.outfile)?; Ok(()) diff --git a/src/gui.rs b/src/gui.rs index 7ff5f8a..be397fb 100644 --- a/src/gui.rs +++ b/src/gui.rs @@ -19,33 +19,26 @@ impl GUI { /// Captures the window and produces an Image. pub fn capture_window(&self, opt: &Options, window: Window) -> Result { let attr = window.get_attributes()?; - let mut width = attr.get_width(); - let mut height = attr.get_height(); + let width = attr.get_width(); + let height = attr.get_height(); let root = attr.get_root(); - let (mut x, mut y, _) = self.display.translate_coordinates(window, 0, 0, root)?; + let (x, y, _) = self.display.translate_coordinates(window, 0, 0, root)?; imlib2::context_set_display(&self.display); let visual = Visual::default(&self.display, 0); imlib2::context_set_visual(&visual); - match opt.region { - Region::Selection => { - let capture = Image2::create_from_drawable( - window, - 0, - x, - y, - width as i32, - height as i32, - true, - )?; - let region = self.interactive_select(capture)?; - x = region.x; - y = region.y; - width = region.width; - height = region.height; - } - _ => (), + if let Region::Selection = opt.region { + let capture = + Image2::create_from_drawable(window, 0, x, y, width as i32, height as i32, true)?; + let region = self.interactive_select(&capture)?; + imlib2::context_set_image(&capture); + return imlib2::create_scaled_cropped_image( + region.x, + region.y, + region.width, + region.height, + ).map_err(|err| err.into()); } Image2::create_from_drawable(window, 0, x, y, width as i32, height as i32, true) @@ -61,7 +54,7 @@ impl GUI { } /// Brings up an interactive selection GUI. - pub fn interactive_select(&self, capture: Image2) -> Result { + pub fn interactive_select(&self, capture: &Image2) -> Result { // let window = SelectWindow::new(&self.display); // let root = self.display.get_default_root_window()?; @@ -88,7 +81,7 @@ impl GUI { use gl; use glutin::{ self, - dpi::{PhysicalSize, PhysicalPosition}, + dpi::{PhysicalPosition, PhysicalSize}, os::unix::{WindowBuilderExt, WindowExt, XWindowType}, ElementState, Event, EventsLoop, GlContext, GlWindow, KeyboardInput, MouseButton, MouseCursor, VirtualKeyCode, WindowBuilder, WindowEvent, @@ -113,8 +106,9 @@ impl GUI { .with_decorations(false) .with_visibility(false) .with_always_on_top(true) - .with_dimensions(PhysicalSize::new(width.into(), height.into()).to_logical(mon.get_hidpi_factor())) - .with_fullscreen(Some(mon)); + .with_dimensions( + PhysicalSize::new(width.into(), height.into()).to_logical(mon.get_hidpi_factor()), + ).with_fullscreen(Some(mon)); let ctx = glutin::ContextBuilder::new() .with_vsync(false) .with_multisampling(4) @@ -253,7 +247,7 @@ impl GUI { evl.poll_events(|event| match event { Event::WindowEvent { event, .. } => match event { - WindowEvent::CloseRequested | WindowEvent::Destroyed => running = false, + WindowEvent::Destroyed => running = false, WindowEvent::KeyboardInput { input: KeyboardInput { @@ -269,6 +263,12 @@ impl GUI { rectw = 0.0; recth = 0.0; } else { + unsafe { + x11::xlib::XDestroyWindow( + self.display.as_raw(), + win.get_xlib_window().unwrap(), + ) + }; running = false; } } @@ -303,6 +303,12 @@ impl GUI { } ElementState::Released => { if down && rectw.abs() > 0.0 && recth.abs() > 0.0 { + unsafe { + x11::xlib::XDestroyWindow( + self.display.as_raw(), + win.get_xlib_window().unwrap(), + ) + }; running = false; } false @@ -315,7 +321,6 @@ impl GUI { }, _ => (), }); - win.swap_buffers().expect("couldn't swap buffers"); } if rectw.abs() > 0.0 && recth.abs() > 0.0 {