diff --git a/Cargo.toml b/Cargo.toml index e8f59758..90284ebe 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -50,9 +50,8 @@ windows = { version = "0.51", features = [ ] } [target.'cfg(target_os = "macos")'.dependencies] -core-foundation = "0.9" core-graphics = { version = "0.23", features = ["highsierra"] } -objc = "0.2" +icrate = { version = "0.0.4", features = ["AppKit_all"] } [target.'cfg(target_os = "linux")'.dependencies] libc = "0.2" diff --git a/examples/timer.rs b/examples/timer.rs index e7e66c33..aac37a1c 100644 --- a/examples/timer.rs +++ b/examples/timer.rs @@ -21,7 +21,12 @@ fn main() { println!("{time:?}"); // select all - enigo.key(Key::Control, Press).unwrap(); + let control_or_command = if cfg!(target_os = "macos") { + Key::Meta + } else { + Key::Control + }; + enigo.key(control_or_command, Press).unwrap(); enigo.key(Key::Unicode('a'), Click).unwrap(); - enigo.key(Key::Control, Release).unwrap(); + enigo.key(control_or_command, Release).unwrap(); } diff --git a/src/macos/macos_impl.rs b/src/macos/macos_impl.rs index a88d4cc0..fa31faf9 100644 --- a/src/macos/macos_impl.rs +++ b/src/macos/macos_impl.rs @@ -10,18 +10,14 @@ use core_graphics::event::{ ScrollEventUnit, }; use core_graphics::event_source::{CGEventSource, CGEventSourceStateID}; +use icrate::AppKit; use log::{debug, error, info}; -use objc::{class, msg_send, runtime::Class, sel, sel_impl}; use crate::{ Axis, Button, Coordinate, Direction, InputError, InputResult, Key, Keyboard, Mouse, NewConError, Settings, }; -// required for NSEvent -#[link(name = "AppKit", kind = "framework")] -extern "C" {} - type CFDataRef = *const c_void; #[repr(C)] @@ -218,7 +214,7 @@ impl Mouse for Enigo { fn move_mouse(&mut self, x: i32, y: i32, coordinate: Coordinate) -> InputResult<()> { debug!("\x1b[93mmove_mouse(x: {x:?}, y: {y:?}, coordinate:{coordinate:?})\x1b[0m"); - let pressed = Self::pressed_buttons()?; + let pressed = unsafe { AppKit::NSEvent::pressedMouseButtons() }; let (current_x, current_y) = self.location()?; let (absolute, relative) = match coordinate { @@ -227,14 +223,15 @@ impl Mouse for Enigo { Coordinate::Rel => ((current_x + x, current_y + y), (x, y)), }; - let (event_type, button) = - if pressed & 1 > 0 { - (CGEventType::LeftMouseDragged, CGMouseButton::Left) - } else if pressed & 2 > 0 { - (CGEventType::RightMouseDragged, CGMouseButton::Right) - } else { - (CGEventType::MouseMoved, CGMouseButton::Left) // The mouse button here is ignored so it can be anything - }; + let (event_type, button) = if pressed & 1 > 0 { + (CGEventType::LeftMouseDragged, CGMouseButton::Left) + } else if pressed & 2 > 0 { + (CGEventType::RightMouseDragged, CGMouseButton::Right) + } else { + (CGEventType::MouseMoved, CGMouseButton::Left) // The mouse button + // here is ignored so + // it can be anything + }; let dest = CGPoint::new(absolute.0 as f64, absolute.1 as f64); let Ok(event) = @@ -292,10 +289,7 @@ impl Mouse for Enigo { fn location(&self) -> InputResult<(i32, i32)> { debug!("\x1b[93mlocation()\x1b[0m"); - let ns_event = Class::get("NSEvent").ok_or(InputError::Simulate( - "failed creating event to get the mouse location", - ))?; - let pt: CGPoint = unsafe { msg_send![ns_event, mouseLocation] }; + let pt = unsafe { AppKit::NSEvent::mouseLocation() }; let (x, y_inv) = (pt.x as i32, pt.y as i32); Ok((x, self.display.pixels_high() as i32 - y_inv)) } @@ -434,8 +428,8 @@ impl Enigo { let held = (Vec::new(), Vec::new()); let double_click_delay = Duration::from_secs(1); - let double_click_delay_setting: f64 = - unsafe { msg_send![class!(NSEvent), doubleClickInterval] }; // Returns the double click interval (https://developer.apple.com/documentation/appkit/nsevent/1528384-doubleclickinterval). This is a TimeInterval which is a f64 of the number of seconds + let double_click_delay_setting = unsafe { AppKit::NSEvent::doubleClickInterval() }; + // Returns the double click interval (https://developer.apple.com/documentation/appkit/nsevent/1528384-doubleclickinterval). This is a TimeInterval which is a f64 of the number of seconds let double_click_delay = double_click_delay.mul_f64(double_click_delay_setting); let Ok(event_source) = CGEventSource::new(CGEventSourceStateID::CombinedSessionState) @@ -473,15 +467,6 @@ impl Enigo { self.held.clone() } - fn pressed_buttons() -> InputResult { - let ns_event = Class::get("NSEvent").ok_or(InputError::Simulate( - "failed creating event to get the pressed mouse buttons", - ))?; - let pressed_buttons = unsafe { msg_send![ns_event, pressedMouseButtons] }; - debug!("pressed_buttons: {pressed_buttons}"); - Ok(pressed_buttons) - } - // On macOS, we have to determine ourselves if it was a double click of a mouse // button. The Enigo struct stores the information needed to do so. This // function checks if the button was pressed down again fast enough to issue a