Vendor things
This commit is contained in:
parent
5deceec006
commit
977e3c17e5
19434 changed files with 10682014 additions and 0 deletions
814
third-party/vendor/core-graphics/src/event.rs
vendored
Normal file
814
third-party/vendor/core-graphics/src/event.rs
vendored
Normal file
|
|
@ -0,0 +1,814 @@
|
|||
#![allow(non_upper_case_globals)]
|
||||
use core_foundation::{
|
||||
base::{CFRelease, CFRetain, CFTypeID, TCFType},
|
||||
mach_port::{CFMachPort, CFMachPortRef},
|
||||
};
|
||||
use event_source::CGEventSource;
|
||||
use foreign_types::ForeignType;
|
||||
use geometry::CGPoint;
|
||||
use libc::c_void;
|
||||
use std::mem::ManuallyDrop;
|
||||
|
||||
pub type CGEventField = u32;
|
||||
pub type CGKeyCode = u16;
|
||||
pub type CGScrollEventUnit = u32;
|
||||
|
||||
bitflags! {
|
||||
/// Flags for events
|
||||
///
|
||||
/// [Ref](http://opensource.apple.com/source/IOHIDFamily/IOHIDFamily-700/IOHIDSystem/IOKit/hidsystem/IOLLEvent.h)
|
||||
#[repr(C)]
|
||||
pub struct CGEventFlags: u64 {
|
||||
const CGEventFlagNull = 0;
|
||||
|
||||
// Device-independent modifier key bits.
|
||||
const CGEventFlagAlphaShift = 0x00010000;
|
||||
const CGEventFlagShift = 0x00020000;
|
||||
const CGEventFlagControl = 0x00040000;
|
||||
const CGEventFlagAlternate = 0x00080000;
|
||||
const CGEventFlagCommand = 0x00100000;
|
||||
|
||||
// Special key identifiers.
|
||||
const CGEventFlagHelp = 0x00400000;
|
||||
const CGEventFlagSecondaryFn = 0x00800000;
|
||||
|
||||
// Identifies key events from numeric keypad area on extended keyboards.
|
||||
const CGEventFlagNumericPad = 0x00200000;
|
||||
|
||||
// Indicates if mouse/pen movement events are not being coalesced
|
||||
const CGEventFlagNonCoalesced = 0x00000100;
|
||||
}
|
||||
}
|
||||
|
||||
/// Key codes for keys that are independent of keyboard layout.
|
||||
///
|
||||
/// [Ref](https://github.com/phracker/MacOSX-SDKs/blob/master/MacOSX10.13.sdk/System/Library/Frameworks/Carbon.framework/Versions/A/Frameworks/HIToolbox.framework/Versions/A/Headers/Events.h)
|
||||
#[repr(C)]
|
||||
pub struct KeyCode;
|
||||
impl KeyCode {
|
||||
pub const RETURN: CGKeyCode = 0x24;
|
||||
pub const TAB: CGKeyCode = 0x30;
|
||||
pub const SPACE: CGKeyCode = 0x31;
|
||||
pub const DELETE: CGKeyCode = 0x33;
|
||||
pub const ESCAPE: CGKeyCode = 0x35;
|
||||
pub const COMMAND: CGKeyCode = 0x37;
|
||||
pub const SHIFT: CGKeyCode = 0x38;
|
||||
pub const CAPS_LOCK: CGKeyCode = 0x39;
|
||||
pub const OPTION: CGKeyCode = 0x3A;
|
||||
pub const CONTROL: CGKeyCode = 0x3B;
|
||||
pub const RIGHT_COMMAND: CGKeyCode = 0x36;
|
||||
pub const RIGHT_SHIFT: CGKeyCode = 0x3C;
|
||||
pub const RIGHT_OPTION: CGKeyCode = 0x3D;
|
||||
pub const RIGHT_CONTROL: CGKeyCode = 0x3E;
|
||||
pub const FUNCTION: CGKeyCode = 0x3F;
|
||||
pub const VOLUME_UP: CGKeyCode = 0x48;
|
||||
pub const VOLUME_DOWN: CGKeyCode = 0x49;
|
||||
pub const MUTE: CGKeyCode = 0x4A;
|
||||
pub const F1: CGKeyCode = 0x7A;
|
||||
pub const F2: CGKeyCode = 0x78;
|
||||
pub const F3: CGKeyCode = 0x63;
|
||||
pub const F4: CGKeyCode = 0x76;
|
||||
pub const F5: CGKeyCode = 0x60;
|
||||
pub const F6: CGKeyCode = 0x61;
|
||||
pub const F7: CGKeyCode = 0x62;
|
||||
pub const F8: CGKeyCode = 0x64;
|
||||
pub const F9: CGKeyCode = 0x65;
|
||||
pub const F10: CGKeyCode = 0x6D;
|
||||
pub const F11: CGKeyCode = 0x67;
|
||||
pub const F12: CGKeyCode = 0x6F;
|
||||
pub const F13: CGKeyCode = 0x69;
|
||||
pub const F14: CGKeyCode = 0x6B;
|
||||
pub const F15: CGKeyCode = 0x71;
|
||||
pub const F16: CGKeyCode = 0x6A;
|
||||
pub const F17: CGKeyCode = 0x40;
|
||||
pub const F18: CGKeyCode = 0x4F;
|
||||
pub const F19: CGKeyCode = 0x50;
|
||||
pub const F20: CGKeyCode = 0x5A;
|
||||
pub const HELP: CGKeyCode = 0x72;
|
||||
pub const HOME: CGKeyCode = 0x73;
|
||||
pub const PAGE_UP: CGKeyCode = 0x74;
|
||||
pub const FORWARD_DELETE: CGKeyCode = 0x75;
|
||||
pub const END: CGKeyCode = 0x77;
|
||||
pub const PAGE_DOWN: CGKeyCode = 0x79;
|
||||
pub const LEFT_ARROW: CGKeyCode = 0x7B;
|
||||
pub const RIGHT_ARROW: CGKeyCode = 0x7C;
|
||||
pub const DOWN_ARROW: CGKeyCode = 0x7D;
|
||||
pub const UP_ARROW: CGKeyCode = 0x7E;
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
pub struct ScrollEventUnit {}
|
||||
impl ScrollEventUnit {
|
||||
pub const PIXEL: CGScrollEventUnit = 0;
|
||||
pub const LINE: CGScrollEventUnit = 1;
|
||||
}
|
||||
|
||||
/// Constants that specify the different types of input events.
|
||||
///
|
||||
/// [Ref](http://opensource.apple.com/source/IOHIDFamily/IOHIDFamily-700/IOHIDSystem/IOKit/hidsystem/IOLLEvent.h)
|
||||
#[repr(u32)]
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum CGEventType {
|
||||
Null = 0,
|
||||
|
||||
// Mouse events.
|
||||
LeftMouseDown = 1,
|
||||
LeftMouseUp = 2,
|
||||
RightMouseDown = 3,
|
||||
RightMouseUp = 4,
|
||||
MouseMoved = 5,
|
||||
LeftMouseDragged = 6,
|
||||
RightMouseDragged = 7,
|
||||
|
||||
// Keyboard events.
|
||||
KeyDown = 10,
|
||||
KeyUp = 11,
|
||||
FlagsChanged = 12,
|
||||
|
||||
// Specialized control devices.
|
||||
ScrollWheel = 22,
|
||||
TabletPointer = 23,
|
||||
TabletProximity = 24,
|
||||
OtherMouseDown = 25,
|
||||
OtherMouseUp = 26,
|
||||
OtherMouseDragged = 27,
|
||||
|
||||
// Out of band event types. These are delivered to the event tap callback
|
||||
// to notify it of unusual conditions that disable the event tap.
|
||||
TapDisabledByTimeout = 0xFFFFFFFE,
|
||||
TapDisabledByUserInput = 0xFFFFFFFF,
|
||||
}
|
||||
|
||||
/// Constants used as keys to access specialized fields in low-level events.
|
||||
///
|
||||
/// [Ref](https://developer.apple.com/documentation/coregraphics/cgeventfield)
|
||||
pub struct EventField;
|
||||
impl EventField {
|
||||
/// Key to access an integer field that contains the mouse button event
|
||||
/// number. Matching mouse-down and mouse-up events will have the same
|
||||
/// event number.
|
||||
pub const MOUSE_EVENT_NUMBER: CGEventField = 0;
|
||||
|
||||
/// Key to access an integer field that contains the mouse button click
|
||||
/// state. A click state of 1 represents a single click. A click state of
|
||||
/// 2 represents a double-click. A click state of 3 represents a
|
||||
/// triple-click.
|
||||
pub const MOUSE_EVENT_CLICK_STATE: CGEventField = 1;
|
||||
|
||||
/// Key to access a double field that contains the mouse button pressure.
|
||||
/// The pressure value may range from 0 to 1, with 0 representing the
|
||||
/// mouse being up. This value is commonly set by tablet pens mimicking a
|
||||
/// mouse.
|
||||
pub const MOUSE_EVENT_PRESSURE: CGEventField = 2;
|
||||
|
||||
/// Key to access an integer field that contains the mouse button number.
|
||||
pub const MOUSE_EVENT_BUTTON_NUMBER: CGEventField = 3;
|
||||
|
||||
/// Key to access an integer field that contains the horizontal mouse
|
||||
/// delta since the last mouse movement event.
|
||||
pub const MOUSE_EVENT_DELTA_X: CGEventField = 4;
|
||||
|
||||
/// Key to access an integer field that contains the vertical mouse delta
|
||||
/// since the last mouse movement event.
|
||||
pub const MOUSE_EVENT_DELTA_Y: CGEventField = 5;
|
||||
|
||||
/// Key to access an integer field. The value is non-zero if the event
|
||||
/// should be ignored by the Inkwell subsystem.
|
||||
pub const MOUSE_EVENT_INSTANT_MOUSER: CGEventField = 6;
|
||||
|
||||
/// Key to access an integer field that encodes the mouse event subtype as
|
||||
/// a `kCFNumberIntType'.
|
||||
pub const MOUSE_EVENT_SUB_TYPE: CGEventField = 7;
|
||||
|
||||
/// Key to access an integer field, non-zero when this is an autorepeat of
|
||||
/// a key-down, and zero otherwise.
|
||||
pub const KEYBOARD_EVENT_AUTOREPEAT: CGEventField = 8;
|
||||
|
||||
/// Key to access an integer field that contains the virtual keycode of the
|
||||
/// key-down or key-up event.
|
||||
pub const KEYBOARD_EVENT_KEYCODE: CGEventField = 9;
|
||||
|
||||
/// Key to access an integer field that contains the keyboard type
|
||||
/// identifier.
|
||||
pub const KEYBOARD_EVENT_KEYBOARD_TYPE: CGEventField = 10;
|
||||
|
||||
/// Key to access an integer field that contains scrolling data. This field
|
||||
/// typically contains the change in vertical position since the last
|
||||
/// scrolling event from a Mighty Mouse scroller or a single-wheel mouse
|
||||
/// scroller.
|
||||
pub const SCROLL_WHEEL_EVENT_DELTA_AXIS_1: CGEventField = 11;
|
||||
|
||||
/// Key to access an integer field that contains scrolling data. This field
|
||||
/// typically contains the change in horizontal position since the last
|
||||
/// scrolling event from a Mighty Mouse scroller.
|
||||
pub const SCROLL_WHEEL_EVENT_DELTA_AXIS_2: CGEventField = 12;
|
||||
|
||||
/// Key to access a field that contains scrolling data. The scrolling data
|
||||
/// represents a line-based or pixel-based change in vertical position
|
||||
/// since the last scrolling event from a Mighty Mouse scroller or a
|
||||
/// single-wheel mouse scroller. The scrolling data uses a fixed-point
|
||||
/// 16.16 signed integer format. If this key is passed to
|
||||
/// `CGEventGetDoubleValueField', the fixed-point value is converted to a
|
||||
/// double value.
|
||||
pub const SCROLL_WHEEL_EVENT_FIXED_POINT_DELTA_AXIS_1: CGEventField = 93;
|
||||
|
||||
/// Key to access a field that contains scrolling data. The scrolling data
|
||||
/// represents a line-based or pixel-based change in horizontal position
|
||||
/// since the last scrolling event from a Mighty Mouse scroller. The
|
||||
/// scrolling data uses a fixed-point 16.16 signed integer format. If this
|
||||
/// key is passed to `CGEventGetDoubleValueField', the fixed-point value is
|
||||
/// converted to a double value.
|
||||
pub const SCROLL_WHEEL_EVENT_FIXED_POINT_DELTA_AXIS_2: CGEventField = 94;
|
||||
|
||||
/// Key to access an integer field that contains pixel-based scrolling
|
||||
/// data. The scrolling data represents the change in vertical position
|
||||
/// since the last scrolling event from a Mighty Mouse scroller or a
|
||||
/// single-wheel mouse scroller.
|
||||
pub const SCROLL_WHEEL_EVENT_POINT_DELTA_AXIS_1: CGEventField = 96;
|
||||
|
||||
/// Key to access an integer field that contains pixel-based scrolling
|
||||
/// data. The scrolling data represents the change in horizontal position
|
||||
/// since the last scrolling event from a Mighty Mouse scroller.
|
||||
pub const SCROLL_WHEEL_EVENT_POINT_DELTA_AXIS_2: CGEventField = 97;
|
||||
|
||||
/// Key to access an integer field that indicates whether the event should
|
||||
/// be ignored by the Inkwell subsystem. If the value is non-zero, the
|
||||
/// event should be ignored.
|
||||
pub const SCROLL_WHEEL_EVENT_INSTANT_MOUSER: CGEventField = 14;
|
||||
|
||||
/// Key to access an integer field that contains the absolute X coordinate
|
||||
/// in tablet space at full tablet resolution.
|
||||
pub const TABLET_EVENT_POINT_X: CGEventField = 15;
|
||||
|
||||
/// Key to access an integer field that contains the absolute Y coordinate
|
||||
/// in tablet space at full tablet resolution.
|
||||
pub const TABLET_EVENT_POINT_Y: CGEventField = 16;
|
||||
|
||||
/// Key to access an integer field that contains the absolute Z coordinate
|
||||
/// in tablet space at full tablet resolution.
|
||||
pub const TABLET_EVENT_POINT_Z: CGEventField = 17;
|
||||
|
||||
/// Key to access an integer field that contains the tablet button state.
|
||||
/// Bit 0 is the first button, and a set bit represents a closed or pressed
|
||||
/// button. Up to 16 buttons are supported.
|
||||
pub const TABLET_EVENT_POINT_BUTTONS: CGEventField = 18;
|
||||
|
||||
/// Key to access a double field that contains the tablet pen pressure. A
|
||||
/// value of 0.0 represents no pressure, and 1.0 represents maximum
|
||||
/// pressure.
|
||||
pub const TABLET_EVENT_POINT_PRESSURE: CGEventField = 19;
|
||||
|
||||
/// Key to access a double field that contains the horizontal tablet pen
|
||||
/// tilt. A value of 0 represents no tilt, and 1 represents maximum tilt.
|
||||
pub const TABLET_EVENT_TILT_X: CGEventField = 20;
|
||||
|
||||
/// Key to access a double field that contains the vertical tablet pen
|
||||
/// tilt. A value of 0 represents no tilt, and 1 represents maximum tilt.
|
||||
pub const TABLET_EVENT_TILT_Y: CGEventField = 21;
|
||||
|
||||
/// Key to access a double field that contains the tablet pen rotation.
|
||||
pub const TABLET_EVENT_ROTATION: CGEventField = 22;
|
||||
|
||||
/// Key to access a double field that contains the tangential pressure on
|
||||
/// the device. A value of 0.0 represents no pressure, and 1.0 represents
|
||||
/// maximum pressure.
|
||||
pub const TABLET_EVENT_TANGENTIAL_PRESSURE: CGEventField = 23;
|
||||
|
||||
/// Key to access an integer field that contains the system-assigned unique
|
||||
/// device ID.
|
||||
pub const TABLET_EVENT_DEVICE_ID: CGEventField = 24;
|
||||
|
||||
/// Key to access an integer field that contains a vendor-specified value.
|
||||
pub const TABLET_EVENT_VENDOR_1: CGEventField = 25;
|
||||
|
||||
/// Key to access an integer field that contains a vendor-specified value.
|
||||
pub const TABLET_EVENT_VENDOR_2: CGEventField = 26;
|
||||
|
||||
/// Key to access an integer field that contains a vendor-specified value.
|
||||
pub const TABLET_EVENT_VENDOR_3: CGEventField = 27;
|
||||
|
||||
/// Key to access an integer field that contains the vendor-defined ID,
|
||||
/// typically the USB vendor ID.
|
||||
pub const TABLET_PROXIMITY_EVENT_VENDOR_ID: CGEventField = 28;
|
||||
|
||||
/// Key to access an integer field that contains the vendor-defined tablet
|
||||
/// ID, typically the USB product ID.
|
||||
pub const TABLET_PROXIMITY_EVENT_TABLET_ID: CGEventField = 29;
|
||||
|
||||
/// Key to access an integer field that contains the vendor-defined ID of
|
||||
/// the pointing device.
|
||||
pub const TABLET_PROXIMITY_EVENT_POINTER_ID: CGEventField = 30;
|
||||
|
||||
/// Key to access an integer field that contains the system-assigned
|
||||
/// device ID.
|
||||
pub const TABLET_PROXIMITY_EVENT_DEVICE_ID: CGEventField = 31;
|
||||
|
||||
/// Key to access an integer field that contains the system-assigned
|
||||
/// unique tablet ID.
|
||||
pub const TABLET_PROXIMITY_EVENT_SYSTEM_TABLET_ID: CGEventField = 32;
|
||||
|
||||
/// Key to access an integer field that contains the vendor-assigned
|
||||
/// pointer type.
|
||||
pub const TABLET_PROXIMITY_EVENT_VENDOR_POINTER_TYPE: CGEventField = 33;
|
||||
|
||||
/// Key to access an integer field that contains the vendor-defined
|
||||
/// pointer serial number.
|
||||
pub const TABLET_PROXIMITY_EVENT_VENDOR_POINTER_SERIAL_NUMBER: CGEventField = 34;
|
||||
|
||||
/// Key to access an integer field that contains the vendor-defined unique
|
||||
/// ID.
|
||||
pub const TABLET_PROXIMITY_EVENT_VENDOR_UNIQUE_ID: CGEventField = 35;
|
||||
|
||||
/// Key to access an integer field that contains the device capabilities
|
||||
/// mask.
|
||||
pub const TABLET_PROXIMITY_EVENT_CAPABILITY_MASK: CGEventField = 36;
|
||||
|
||||
/// Key to access an integer field that contains the pointer type.
|
||||
pub const TABLET_PROXIMITY_EVENT_POINTER_TYPE: CGEventField = 37;
|
||||
|
||||
/// Key to access an integer field that indicates whether the pen is in
|
||||
/// proximity to the tablet. The value is non-zero if the pen is in
|
||||
/// proximity to the tablet and zero when leaving the tablet.
|
||||
pub const TABLET_PROXIMITY_EVENT_ENTER_PROXIMITY: CGEventField = 38;
|
||||
|
||||
/// Key to access a field that contains the event target process serial
|
||||
/// number. The value is a 64-bit value.
|
||||
pub const EVENT_TARGET_PROCESS_SERIAL_NUMBER: CGEventField = 39;
|
||||
|
||||
/// Key to access a field that contains the event target Unix process ID.
|
||||
pub const EVENT_TARGET_UNIX_PROCESS_ID: CGEventField = 40;
|
||||
|
||||
/// Key to access a field that contains the event source Unix process ID.
|
||||
pub const EVENT_SOURCE_UNIX_PROCESS_ID: CGEventField = 41;
|
||||
|
||||
/// Key to access a field that contains the event source user-supplied
|
||||
/// data, up to 64 bits.
|
||||
pub const EVENT_SOURCE_USER_DATA: CGEventField = 42;
|
||||
|
||||
/// Key to access a field that contains the event source Unix effective UID.
|
||||
pub const EVENT_SOURCE_USER_ID: CGEventField = 43;
|
||||
|
||||
/// Key to access a field that contains the event source Unix effective
|
||||
/// GID.
|
||||
pub const EVENT_SOURCE_GROUP_ID: CGEventField = 44;
|
||||
|
||||
/// Key to access a field that contains the event source state ID used to
|
||||
/// create this event.
|
||||
pub const EVENT_SOURCE_STATE_ID: CGEventField = 45;
|
||||
|
||||
/// Key to access an integer field that indicates whether a scrolling event
|
||||
/// contains continuous, pixel-based scrolling data. The value is non-zero
|
||||
/// when the scrolling data is pixel-based and zero when the scrolling data
|
||||
/// is line-based.
|
||||
pub const SCROLL_WHEEL_EVENT_IS_CONTINUOUS: CGEventField = 88;
|
||||
|
||||
/// Added in 10.5; made public in 10.7.
|
||||
pub const MOUSE_EVENT_WINDOW_UNDER_MOUSE_POINTER: CGEventField = 91;
|
||||
pub const MOUSE_EVENT_WINDOW_UNDER_MOUSE_POINTER_THAT_CAN_HANDLE_THIS_EVENT: CGEventField = 92;
|
||||
}
|
||||
|
||||
// Constants that specify buttons on a one, two, or three-button mouse.
|
||||
#[repr(C)]
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum CGMouseButton {
|
||||
Left,
|
||||
Right,
|
||||
Center,
|
||||
}
|
||||
|
||||
/// Possible tapping points for events.
|
||||
#[repr(C)]
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum CGEventTapLocation {
|
||||
HID,
|
||||
Session,
|
||||
AnnotatedSession,
|
||||
}
|
||||
|
||||
// The next three enums are taken from:
|
||||
// [Ref](https://github.com/phracker/MacOSX-SDKs/blob/ef9fe35d5691b6dd383c8c46d867a499817a01b6/MacOSX10.15.sdk/System/Library/Frameworks/CoreGraphics.framework/Versions/A/Headers/CGEventTypes.h)
|
||||
/* Constants that specify where a new event tap is inserted into the list of
|
||||
active event taps. */
|
||||
#[repr(u32)]
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum CGEventTapPlacement {
|
||||
HeadInsertEventTap = 0,
|
||||
TailAppendEventTap,
|
||||
}
|
||||
|
||||
/* Constants that specify whether a new event tap is an active filter or a
|
||||
passive listener. */
|
||||
#[repr(u32)]
|
||||
#[derive(Clone, Copy, Debug)]
|
||||
pub enum CGEventTapOptions {
|
||||
Default = 0x00000000,
|
||||
ListenOnly = 0x00000001,
|
||||
}
|
||||
|
||||
pub type CGEventMask = u64;
|
||||
/* Generate an event mask for a single type of event. */
|
||||
macro_rules! CGEventMaskBit {
|
||||
($eventType:expr) => {
|
||||
1 << $eventType as CGEventMask
|
||||
};
|
||||
}
|
||||
|
||||
pub type CGEventTapProxy = *const c_void;
|
||||
pub type CGEventTapCallBackFn<'tap_life> =
|
||||
Box<dyn Fn(CGEventTapProxy, CGEventType, &CGEvent) -> Option<CGEvent> + 'tap_life>;
|
||||
type CGEventTapCallBackInternal = unsafe extern "C" fn(
|
||||
proxy: CGEventTapProxy,
|
||||
etype: CGEventType,
|
||||
event: ::sys::CGEventRef,
|
||||
user_info: *const c_void,
|
||||
) -> ::sys::CGEventRef;
|
||||
|
||||
#[no_mangle]
|
||||
unsafe extern "C" fn cg_event_tap_callback_internal(
|
||||
_proxy: CGEventTapProxy,
|
||||
_etype: CGEventType,
|
||||
_event: ::sys::CGEventRef,
|
||||
_user_info: *const c_void,
|
||||
) -> ::sys::CGEventRef {
|
||||
let callback = _user_info as *mut CGEventTapCallBackFn;
|
||||
let event = CGEvent::from_ptr(_event);
|
||||
let new_event = (*callback)(_proxy, _etype, &event);
|
||||
let event = match new_event {
|
||||
Some(new_event) => new_event,
|
||||
None => event,
|
||||
};
|
||||
ManuallyDrop::new(event).as_ptr()
|
||||
}
|
||||
|
||||
|
||||
/// ```no_run
|
||||
///extern crate core_foundation;
|
||||
///use core_foundation::runloop::{kCFRunLoopCommonModes, CFRunLoop};
|
||||
///use core_graphics::event::{CGEventTap, CGEventTapLocation, CGEventTapPlacement, CGEventTapOptions, CGEventType};
|
||||
///let current = CFRunLoop::get_current();
|
||||
///match CGEventTap::new(
|
||||
/// CGEventTapLocation::HID,
|
||||
/// CGEventTapPlacement::HeadInsertEventTap,
|
||||
/// CGEventTapOptions::Default,
|
||||
/// vec![CGEventType::MouseMoved],
|
||||
/// |_a, _b, d| {
|
||||
/// println!("{:?}", d.location());
|
||||
/// None
|
||||
/// },
|
||||
/// ) {
|
||||
/// Ok(tap) => unsafe {
|
||||
/// let loop_source = tap
|
||||
/// .mach_port
|
||||
/// .create_runloop_source(0)
|
||||
/// .expect("Somethings is bad ");
|
||||
/// current.add_source(&loop_source, kCFRunLoopCommonModes);
|
||||
/// tap.enable();
|
||||
/// CFRunLoop::run_current();
|
||||
/// },
|
||||
/// Err(_) => (assert!(false)),
|
||||
/// }
|
||||
/// ```
|
||||
pub struct CGEventTap<'tap_life> {
|
||||
pub mach_port: CFMachPort,
|
||||
pub callback_ref:
|
||||
Box<dyn Fn(CGEventTapProxy, CGEventType, &CGEvent) -> Option<CGEvent> + 'tap_life>,
|
||||
}
|
||||
|
||||
impl<'tap_life> CGEventTap<'tap_life> {
|
||||
pub fn new<F: Fn(CGEventTapProxy, CGEventType, &CGEvent) -> Option<CGEvent> + 'tap_life>(
|
||||
tap: CGEventTapLocation,
|
||||
place: CGEventTapPlacement,
|
||||
options: CGEventTapOptions,
|
||||
events_of_interest: std::vec::Vec<CGEventType>,
|
||||
callback: F,
|
||||
) -> Result<CGEventTap<'tap_life>, ()> {
|
||||
let event_mask: CGEventMask = events_of_interest
|
||||
.iter()
|
||||
.fold(CGEventType::Null as CGEventMask, |mask, &etype| {
|
||||
mask | CGEventMaskBit!(etype)
|
||||
});
|
||||
let cb = Box::new(Box::new(callback) as CGEventTapCallBackFn);
|
||||
let cbr = Box::into_raw(cb);
|
||||
unsafe {
|
||||
let event_tap_ref = CGEventTapCreate(
|
||||
tap,
|
||||
place,
|
||||
options,
|
||||
event_mask,
|
||||
cg_event_tap_callback_internal,
|
||||
cbr as *const c_void,
|
||||
);
|
||||
|
||||
if !event_tap_ref.is_null() {
|
||||
Ok(Self {
|
||||
mach_port: (CFMachPort::wrap_under_create_rule(event_tap_ref)),
|
||||
callback_ref: Box::from_raw(cbr),
|
||||
})
|
||||
} else {
|
||||
Box::from_raw(cbr);
|
||||
Err(())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn enable(&self) {
|
||||
unsafe { CGEventTapEnable(self.mach_port.as_concrete_TypeRef(), true) }
|
||||
}
|
||||
}
|
||||
|
||||
foreign_type! {
|
||||
#[doc(hidden)]
|
||||
type CType = ::sys::CGEvent;
|
||||
fn drop = |p| CFRelease(p as *mut _);
|
||||
fn clone = |p| CFRetain(p as *const _) as *mut _;
|
||||
pub struct CGEvent;
|
||||
pub struct CGEventRef;
|
||||
}
|
||||
|
||||
impl CGEvent {
|
||||
pub fn type_id() -> CFTypeID {
|
||||
unsafe {
|
||||
CGEventGetTypeID()
|
||||
}
|
||||
}
|
||||
|
||||
pub fn new(source: CGEventSource) -> Result<CGEvent, ()> {
|
||||
unsafe {
|
||||
let event_ref = CGEventCreate(source.as_ptr());
|
||||
if !event_ref.is_null() {
|
||||
Ok(Self::from_ptr(event_ref))
|
||||
} else {
|
||||
Err(())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn new_keyboard_event(
|
||||
source: CGEventSource,
|
||||
keycode: CGKeyCode,
|
||||
keydown: bool
|
||||
) -> Result<CGEvent, ()> {
|
||||
unsafe {
|
||||
let event_ref = CGEventCreateKeyboardEvent(source.as_ptr(), keycode, keydown);
|
||||
if !event_ref.is_null() {
|
||||
Ok(Self::from_ptr(event_ref))
|
||||
} else {
|
||||
Err(())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn new_mouse_event(
|
||||
source: CGEventSource,
|
||||
mouse_type: CGEventType,
|
||||
mouse_cursor_position: CGPoint,
|
||||
mouse_button: CGMouseButton
|
||||
) -> Result<CGEvent, ()> {
|
||||
unsafe {
|
||||
let event_ref = CGEventCreateMouseEvent(source.as_ptr(), mouse_type,
|
||||
mouse_cursor_position, mouse_button);
|
||||
if !event_ref.is_null() {
|
||||
Ok(Self::from_ptr(event_ref))
|
||||
} else {
|
||||
Err(())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "highsierra")]
|
||||
pub fn new_scroll_event(
|
||||
source: CGEventSource,
|
||||
units: CGScrollEventUnit,
|
||||
wheel_count: u32,
|
||||
wheel1: i32,
|
||||
wheel2: i32,
|
||||
wheel3: i32,
|
||||
) -> Result<CGEvent, ()> {
|
||||
unsafe {
|
||||
let event_ref = CGEventCreateScrollWheelEvent2(
|
||||
source.as_ptr(),
|
||||
units,
|
||||
wheel_count,
|
||||
wheel1,
|
||||
wheel2,
|
||||
wheel3,
|
||||
);
|
||||
if !event_ref.is_null() {
|
||||
Ok(Self::from_ptr(event_ref))
|
||||
} else {
|
||||
Err(())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn post(&self, tap_location: CGEventTapLocation) {
|
||||
unsafe {
|
||||
CGEventPost(tap_location, self.as_ptr());
|
||||
}
|
||||
}
|
||||
|
||||
pub fn location(&self) -> CGPoint {
|
||||
unsafe {
|
||||
CGEventGetLocation(self.as_ptr())
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "elcapitan")]
|
||||
pub fn post_to_pid(&self, pid: libc::pid_t) {
|
||||
unsafe {
|
||||
CGEventPostToPid(pid, self.as_ptr());
|
||||
}
|
||||
}
|
||||
|
||||
pub fn set_flags(&self, flags: CGEventFlags) {
|
||||
unsafe {
|
||||
CGEventSetFlags(self.as_ptr(), flags);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_flags(&self) -> CGEventFlags {
|
||||
unsafe {
|
||||
CGEventGetFlags(self.as_ptr())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn set_type(&self, event_type: CGEventType) {
|
||||
unsafe {
|
||||
CGEventSetType(self.as_ptr(), event_type);
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_type(&self) -> CGEventType {
|
||||
unsafe {
|
||||
CGEventGetType(self.as_ptr())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn set_string_from_utf16_unchecked(&self, buf: &[u16]) {
|
||||
let buflen = buf.len() as libc::c_ulong;
|
||||
unsafe {
|
||||
CGEventKeyboardSetUnicodeString(self.as_ptr(), buflen, buf.as_ptr());
|
||||
}
|
||||
}
|
||||
|
||||
pub fn set_string(&self, string: &str) {
|
||||
let buf: Vec<u16> = string.encode_utf16().collect();
|
||||
self.set_string_from_utf16_unchecked(&buf);
|
||||
}
|
||||
|
||||
pub fn get_integer_value_field(&self, field: CGEventField) -> i64 {
|
||||
unsafe { CGEventGetIntegerValueField(self.as_ptr(), field) }
|
||||
}
|
||||
|
||||
pub fn set_integer_value_field(&self, field: CGEventField, value: i64) {
|
||||
unsafe { CGEventSetIntegerValueField(self.as_ptr(), field, value) }
|
||||
}
|
||||
|
||||
pub fn get_double_value_field(&self, field: CGEventField) -> f64 {
|
||||
unsafe { CGEventGetDoubleValueField(self.as_ptr(), field) }
|
||||
}
|
||||
|
||||
pub fn set_double_value_field(&self, field: CGEventField, value: f64) {
|
||||
unsafe { CGEventSetDoubleValueField(self.as_ptr(), field, value) }
|
||||
}
|
||||
}
|
||||
|
||||
#[link(name = "CoreGraphics", kind = "framework")]
|
||||
extern {
|
||||
/// Return the type identifier for the opaque type `CGEventRef'.
|
||||
fn CGEventGetTypeID() -> CFTypeID;
|
||||
|
||||
/// Return a new event using the event source `source'. If `source' is NULL,
|
||||
/// the default source is used.
|
||||
fn CGEventCreate(source: ::sys::CGEventSourceRef) -> ::sys::CGEventRef;
|
||||
|
||||
/// Return a new keyboard event.
|
||||
///
|
||||
/// The event source may be taken from another event, or may be NULL. Based
|
||||
/// on the virtual key code values entered, the appropriate key down, key up,
|
||||
/// or flags changed events are generated.
|
||||
///
|
||||
/// All keystrokes needed to generate a character must be entered, including
|
||||
/// SHIFT, CONTROL, OPTION, and COMMAND keys. For example, to produce a 'Z',
|
||||
/// the SHIFT key must be down, the 'z' key must go down, and then the SHIFT
|
||||
/// and 'z' key must be released:
|
||||
fn CGEventCreateKeyboardEvent(source: ::sys::CGEventSourceRef, keycode: CGKeyCode,
|
||||
keydown: bool) -> ::sys::CGEventRef;
|
||||
|
||||
/// Return a new mouse event.
|
||||
///
|
||||
/// The event source may be taken from another event, or may be NULL.
|
||||
/// `mouseType' should be one of the mouse event types. `mouseCursorPosition'
|
||||
/// should be the position of the mouse cursor in global coordinates.
|
||||
/// `mouseButton' should be the button that's changing state; `mouseButton'
|
||||
/// is ignored unless `mouseType' is one of `kCGEventOtherMouseDown',
|
||||
/// `kCGEventOtherMouseDragged', or `kCGEventOtherMouseUp'.
|
||||
///
|
||||
/// The current implementation of the event system supports a maximum of
|
||||
/// thirty-two buttons. Mouse button 0 is the primary button on the mouse.
|
||||
/// Mouse button 1 is the secondary mouse button (right). Mouse button 2 is
|
||||
/// the center button, and the remaining buttons are in USB device order.
|
||||
fn CGEventCreateMouseEvent(source: ::sys::CGEventSourceRef, mouseType: CGEventType,
|
||||
mouseCursorPosition: CGPoint, mouseButton: CGMouseButton) -> ::sys::CGEventRef;
|
||||
|
||||
/// A non-variadic variant version of CGEventCreateScrollWheelEvent.
|
||||
///
|
||||
/// Returns a new Quartz scrolling event.
|
||||
///
|
||||
/// This function allows you to create a scrolling event and customize the
|
||||
/// event before posting it to the event system.
|
||||
#[cfg(feature = "highsierra")]
|
||||
fn CGEventCreateScrollWheelEvent2(
|
||||
source: ::sys::CGEventSourceRef,
|
||||
units: CGScrollEventUnit,
|
||||
wheelCount: u32,
|
||||
wheel1: i32,
|
||||
wheel2: i32,
|
||||
wheel3: i32,
|
||||
) -> ::sys::CGEventRef;
|
||||
|
||||
/// Post an event into the event stream at a specified location.
|
||||
///
|
||||
/// This function posts the specified event immediately before any event taps
|
||||
/// instantiated for that location, and the event passes through any such
|
||||
/// taps.
|
||||
fn CGEventPost(tapLocation: CGEventTapLocation, event: ::sys::CGEventRef);
|
||||
|
||||
#[cfg(feature = "elcapitan")]
|
||||
/// Post an event to a specified process ID
|
||||
fn CGEventPostToPid(pid: libc::pid_t, event: ::sys::CGEventRef);
|
||||
|
||||
/// Set the event flags of an event.
|
||||
fn CGEventSetFlags(event: ::sys::CGEventRef, flags: CGEventFlags);
|
||||
|
||||
/// Return the event flags of an event.
|
||||
fn CGEventGetFlags(event: ::sys::CGEventRef) -> CGEventFlags;
|
||||
|
||||
/// Return the location of an event in global display coordinates.
|
||||
/// CGPointZero is returned if event is not a valid ::sys::CGEventRef.
|
||||
fn CGEventGetLocation(event: ::sys::CGEventRef) -> CGPoint;
|
||||
|
||||
/// Set the event type of an event.
|
||||
fn CGEventSetType(event: ::sys::CGEventRef, eventType: CGEventType);
|
||||
|
||||
/// Return the event type of an event (left mouse down, for example).
|
||||
fn CGEventGetType(event: ::sys::CGEventRef) -> CGEventType;
|
||||
|
||||
/// Set the Unicode string associated with a keyboard event.
|
||||
///
|
||||
/// By default, the system translates the virtual key code in a keyboard
|
||||
/// event into a Unicode string based on the keyboard ID in the event
|
||||
/// source. This function allows you to manually override this string.
|
||||
/// Note that application frameworks may ignore the Unicode string in a
|
||||
/// keyboard event and do their own translation based on the virtual
|
||||
/// keycode and perceived event state.
|
||||
fn CGEventKeyboardSetUnicodeString(event: ::sys::CGEventRef,
|
||||
length: libc::c_ulong,
|
||||
string: *const u16);
|
||||
|
||||
/// Return the integer value of a field in an event.
|
||||
fn CGEventGetIntegerValueField(event: ::sys::CGEventRef, field: CGEventField) -> i64;
|
||||
|
||||
/// Set the integer value of a field in an event.
|
||||
///
|
||||
/// Before calling this function, the event type must be set using a typed
|
||||
/// event creation function such as `CGEventCreateMouseEvent', or by
|
||||
/// calling `CGEventSetType'.
|
||||
///
|
||||
/// If you are creating a mouse event generated by a tablet, call this
|
||||
/// function and specify the field `kCGMouseEventSubtype' with a value of
|
||||
/// `kCGEventMouseSubtypeTabletPoint' or
|
||||
/// `kCGEventMouseSubtypeTabletProximity' before setting other parameters.
|
||||
fn CGEventSetIntegerValueField(event: ::sys::CGEventRef, field: CGEventField, value: i64);
|
||||
|
||||
/// Return the floating-point value of a field in an event.
|
||||
///
|
||||
/// In cases where the field value is represented within the event by a fixed
|
||||
/// point number or an integer, the result is scaled to the appropriate range
|
||||
/// as part of creating the floating-point representation.
|
||||
fn CGEventGetDoubleValueField(event: ::sys::CGEventRef, field: CGEventField) -> f64;
|
||||
|
||||
/// Set the floating-point value of a field in an event.
|
||||
///
|
||||
/// Before calling this function, the event type must be set using a typed
|
||||
/// event creation function such as `CGEventCreateMouseEvent', or by calling
|
||||
/// `CGEventSetType'.
|
||||
///
|
||||
/// In cases where the field’s value is represented within the event by a
|
||||
/// fixed point number or integer, the value parameter is scaled as needed
|
||||
/// and converted to the appropriate type.
|
||||
fn CGEventSetDoubleValueField(event: ::sys::CGEventRef, field: CGEventField, value: f64);
|
||||
|
||||
// ::sys::CGEventTapRef is actually an CFMachPortRef
|
||||
fn CGEventTapCreate(
|
||||
tap: CGEventTapLocation,
|
||||
place: CGEventTapPlacement,
|
||||
options: CGEventTapOptions,
|
||||
eventsOfInterest: CGEventMask,
|
||||
callback: CGEventTapCallBackInternal,
|
||||
userInfo: *const c_void,
|
||||
) -> CFMachPortRef;
|
||||
|
||||
fn CGEventTapEnable(tap: CFMachPortRef, enable: bool);
|
||||
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue