From c8a4f387aecbe89ed49d904bc28e1a2acc64a5ae Mon Sep 17 00:00:00 2001 From: Gabriel <68819302+obsidianical@users.noreply.github.com> Date: Sun, 12 Jun 2022 00:50:02 +0200 Subject: [PATCH] what --- .gitignore | 15 ++++++++ Cargo.toml | 11 ++++++ README.md | 3 +- src/bin/easymacroplay.rs | 59 ++++++++++++++++++++++++++++++ src/bin/easymacrorec.rs | 5 +++ src/lib.rs | 12 +++++++ src/main.rs | 78 ---------------------------------------- src/modifiers.rs | 57 ----------------------------- src/virt_kb.rs | 37 ------------------- 9 files changed, 104 insertions(+), 173 deletions(-) create mode 100644 Cargo.toml create mode 100644 src/bin/easymacroplay.rs create mode 100644 src/bin/easymacrorec.rs create mode 100644 src/lib.rs delete mode 100644 src/main.rs delete mode 100644 src/modifiers.rs delete mode 100644 src/virt_kb.rs diff --git a/.gitignore b/.gitignore index 22d3516..c1654c4 100644 --- a/.gitignore +++ b/.gitignore @@ -13,3 +13,18 @@ Cargo.lock # Added by cargo /target + + +# Added by cargo +# +# already existing elements were commented out + +#/target + + +# Added by cargo +# +# already existing elements were commented out + +#/target +/Cargo.lock diff --git a/Cargo.toml b/Cargo.toml new file mode 100644 index 0000000..3c9b4e0 --- /dev/null +++ b/Cargo.toml @@ -0,0 +1,11 @@ +[package] +name = "easymacros" +version = "0.1.0" +edition = "2021" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +x11 = { version = "2.19.1", features = ["xlib", "xtest"] } +x11-keysymdef = "0.2.0" +clap = { version = "3.1.18", features = ["derive"] } \ No newline at end of file diff --git a/README.md b/README.md index 6a94f08..ccf4340 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,3 @@ # easymacros -A thing to make macros easily. Inspired by how vim macros work. + +This program is inspired by xmacro, however it isn't xmacro. This project is not using X directly, but evde diff --git a/src/bin/easymacroplay.rs b/src/bin/easymacroplay.rs new file mode 100644 index 0000000..03c18c0 --- /dev/null +++ b/src/bin/easymacroplay.rs @@ -0,0 +1,59 @@ +use std::ffi::CString; +use std::os::raw::c_int; +use x11::xlib::{XCloseDisplay, XFlush, XOpenDisplay}; +use easymacros::add; +use clap::Parser; +use x11::keysym::{XK_d, XK_Super_L}; +use x11::xtest::{XTestFakeButtonEvent, XTestFakeKeyEvent, XTestFakeMotionEvent, XTestGrabControl}; +use x11_keysymdef::lookup_by_name; + +/// Macro program inspired by xmacro. +#[derive(Parser, Debug)] +#[clap(author, version, about, long_about = None)] +struct Args { + /// Display + #[clap(short, long)] + display: String, +} + +fn main () { + let args = Args::parse(); + + // let display_ptr = args.display.as_bytes().as_ptr() as *const i8; + println!("Display name: {}", args.display); + let display_name = CString::new(args.display).unwrap(); + println!("Display name cstr: {:?}", display_name); + let display_ptr: *const u8 = display_name.as_bytes().as_ptr(); + println!("Display name ptr: {:?}", display_ptr); + let display = unsafe { XOpenDisplay(display_ptr as *const i8) }; + println!("Display name ptr: {:?}", display); + + let super_l = lookup_by_name("Super_L").unwrap(); + let d = lookup_by_name("d").unwrap(); + + unsafe { + // XTestFakeKeyEvent(display, super_l.keysym, 1, 0); + // XTestFakeKeyEvent(display, d.keysym, 1, 10); + // + // XTestFakeKeyEvent(display, d.keysym, 0, 20); + // XTestFakeKeyEvent(display, super_l.keysym, 0, 30); + XTestGrabControl(display, c_int::from(false)); + XTestFakeKeyEvent(display, XK_Super_L, c_int::from(true), 0); + XFlush(display); + XTestFakeKeyEvent(display, XK_d, c_int::from(true), 0); + XFlush(display); + XTestFakeKeyEvent(display, XK_d, c_int::from(false), 0); + XFlush(display); + XTestFakeKeyEvent(display, XK_Super_L, c_int::from(false), 0); + XFlush(display); + + XTestFakeMotionEvent(display, -1, 200, 200, 0); + XFlush(display); + + XCloseDisplay(display); + } + + + println!("play: {}", add(5, 10)); +} + diff --git a/src/bin/easymacrorec.rs b/src/bin/easymacrorec.rs new file mode 100644 index 0000000..08df7b8 --- /dev/null +++ b/src/bin/easymacrorec.rs @@ -0,0 +1,5 @@ +use easymacros::add; + +fn main() { + println!("rec: {}", add(2, 2)); +} \ No newline at end of file diff --git a/src/lib.rs b/src/lib.rs new file mode 100644 index 0000000..2816d93 --- /dev/null +++ b/src/lib.rs @@ -0,0 +1,12 @@ +pub fn add(a: i32, b: i32) -> i32 { + a + b +} + +#[cfg(test)] +mod tests { + #[test] + fn it_works() { + let result = 2 + 2; + assert_eq!(result, 4); + } +} diff --git a/src/main.rs b/src/main.rs deleted file mode 100644 index e96d63c..0000000 --- a/src/main.rs +++ /dev/null @@ -1,78 +0,0 @@ -use std::sync::{Arc, mpsc, Mutex}; -use std::sync::mpsc::Receiver; -use std::thread; -use evdev::{Device, enumerate, InputEvent}; -use crate::modifiers::ModifierStates; -use crate::virt_kb::VirtKb; - -mod modifiers; -mod virt_kb; - -fn main() { - let devices = enumerate(); - let kb_name = "py-evdev-uinput"; - - let mut kbs = { - let mut r = Vec::new(); - - for dev in devices { - if let Some(keyboard) = dev.name() { - if keyboard == kb_name { - r.push(dev); - } - } - } - - r - }; - - - let virt_kb = VirtKb::new(&kbs); - let mod_states = ModifierStates::new(); - - let reader = KeyReader::new(kbs); - let event_receiver = reader.init(); - - -} - -struct KeyReader { - keyboards: Arc>>, -} - -impl KeyReader { - pub fn new(kbs: Vec) -> Self { - let mut kbs = kbs; - - for kb in kbs.iter_mut() { - match kb.grab() { - Ok(_) => println!("Keyboard {} grabbed!", kb.name().get_or_insert("[Unnamed]")), - Err(_) => println!("Failed to grab keyboard {}.", kb.name().get_or_insert("[Unnamed]")), - } - } - - Self { keyboards: Arc::new(Mutex::new(kbs)) } - } - - pub fn init(&self) -> Receiver>{ - let (tx, rx) = mpsc::channel(); - - let keyboards = self.keyboards.clone(); - thread::spawn(move || { - let mut kbs_locked = keyboards.lock().unwrap(); - loop { - for kb in kbs_locked.iter_mut() { - let mut events = kb - .fetch_events() - .unwrap() - .collect::>(); - - tx.send(events) - .expect("Couldn't send keyboard events from reader to main thread."); - } - } - }); - - rx - } -} \ No newline at end of file diff --git a/src/modifiers.rs b/src/modifiers.rs deleted file mode 100644 index a99fd02..0000000 --- a/src/modifiers.rs +++ /dev/null @@ -1,57 +0,0 @@ -use evdev::{InputEvent, Key}; - -#[derive(Debug)] -pub struct ModifierStates { - ctrl: bool, - alt: bool, - shift: bool, - meta: bool, -} - -impl ModifierStates { - pub fn new() -> Self { - ModifierStates { - ctrl: false, - alt: false, - shift: false, - meta: false - } - } - pub fn update(&mut self, event: InputEvent) { - let code = event.code(); - let val = event.value(); - - self.update_ctrl(code, val); - self.update_alt(code, val); - self.update_shift(code, val); - self.update_meta(code, val); - } - pub fn mod_pressed(&self) -> bool { - self.ctrl || self.alt || self.shift || self.meta - } - - fn update_ctrl(&mut self, code: u16, val: i32) { - if code == Key::KEY_LEFTCTRL.code() || code == Key::KEY_RIGHTCTRL.code() { - self.ctrl = val != 0; - } - } - - fn update_alt(&mut self, code: u16, val: i32) { - if code == Key::KEY_LEFTALT.code() || code == Key::KEY_RIGHTALT.code() { - self.ctrl = val != 0; - } - } - - fn update_shift(&mut self, code: u16, val: i32) { - if code == Key::KEY_LEFTSHIFT.code() || code == Key::KEY_RIGHTSHIFT.code() { - self.ctrl = val != 0; - } - } - - fn update_meta(&mut self, code: u16, val: i32) { - if code == Key::KEY_LEFTMETA.code() || code == Key::KEY_RIGHTMETA.code() { - self.ctrl = val != 0; - } - } -} - diff --git a/src/virt_kb.rs b/src/virt_kb.rs deleted file mode 100644 index 46d0996..0000000 --- a/src/virt_kb.rs +++ /dev/null @@ -1,37 +0,0 @@ -use std::sync::mpsc; -use std::sync::mpsc::{Sender, SendError}; -use std::thread; -use evdev::{Device, InputEvent}; -use evdev::uinput::VirtualDeviceBuilder; - -pub struct VirtKb { - tx: Sender>, -} - -impl VirtKb { - pub fn new(physical_kbs: &Vec) -> Self { - let (tx, rx) = mpsc::channel::>(); - - let mut virt_kb_builder = VirtualDeviceBuilder::new() - .expect("Failed to create UInput device") - .name("EasyMacros"); - - for phys_kb in physical_kbs { - virt_kb_builder = virt_kb_builder.with_keys(phys_kb.supported_keys().unwrap()).unwrap(); - } - - let mut virt_kb = virt_kb_builder.build().expect("Failed to build virt_kb"); - - thread::spawn(move || { - for received in rx { - virt_kb.emit(&received).expect("Virtual keyboard failed to send events"); - } - }); - - Self { tx } - } - - pub fn send_events(&self, events: Vec) -> Result<(), SendError>> { - self.tx.send(events) - } -} \ No newline at end of file