Simulating Key Press Events in MAC Os X

Simulating key press events in Mac OS X

Here's code to simulate a Cmd-S action:

CGKeyCode inputKeyCode = kVK_ANSI_S;
CGEventSourceRef source = CGEventSourceCreate(kCGEventSourceStateCombinedSessionState);
CGEventRef saveCommandDown = CGEventCreateKeyboardEvent(source, inputKeyCode, YES);
CGEventSetFlags(saveCommandDown, kCGEventFlagMaskCommand);
CGEventRef saveCommandUp = CGEventCreateKeyboardEvent(source, inputKeyCode, NO);

CGEventPost(kCGAnnotatedSessionEventTap, saveCommandDown);
CGEventPost(kCGAnnotatedSessionEventTap, saveCommandUp);

CFRelease(saveCommandUp);
CFRelease(saveCommandDown);
CFRelease(source);

A CGKeyCode is nothing more than an unsigned integer:

typedef uint16_t CGKeyCode;  //From CGRemoteOperation.h

Your real issue will be turning a character (probably an NSString) into a keycode. Fortunately, the Shortcut Recorder project has code that will do just that in the SRKeyCodeTransformer.m file. It's great for transforming a string to a keycode and back again.

Simulate Media-Key press in MacOS

The suggested duplicate question emulate media key press on Mac identified by https://stackoverflow.com/users/4244136/willeke in comments above includes a python solution to my question. I translated it to Swift and posted the working code there. Thanks!

Simulate key press events for ioquake3 in Mac OSX

I solved my problem and everyone who is interested, here is the solution:

I will describe a simple example which makes things clear. As mentioned before i use the Quartz Event Services, to generate the key press event. If you want to constantly move the character in ioquake3 forward, you have to constantly produce key "down" event, like this.

CGKeyCode keyCode = 126;
CGEventRef eventRef = CGEventCreateKeyboardEvent (NULL, keyCode, true);
CGEventPost(kCGSessionEventTap, eventRef);
CFRelease(eventRef);

If you want to stop the character you have to generate one key "up" event:

CGKeyCode keyCode = 126;
CGEventRef eventRef = CGEventCreateKeyboardEvent (NULL, keyCode, false);
CGEventPost(kCGSessionEventTap, eventRef);
CFRelease(eventRef);

Apparently i did not understand how to use key press events in the right way.

How to simulate a low level keypress on os x?

What's wrong with Quartz Event Services?

I think you are on the right track, but you should use CGEventCreateKeyboardEvent instead of CGPostKeyboardEvent because the latter is deprecated since Mac OS X 10.6.

Simulate keypress for system wide hotkeys

From the documentation for CGEventCreateKeyboardEvent:

All keystrokes needed to generate a character must be entered, including modifier 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:

So, you can't just press and release space with the option modifier to trigger an option-space; you have to press option, press space, release space, release option.

As a side note, opt-space doesn't do anything by default; cmd-space is the Spotlight search hotkey, and cmd-opt-space is the Spotlight window hotkey.

So, this code will pop up the Spotlight search:

- (void)execute {
CGEventSourceRef src =
CGEventSourceCreate(kCGEventSourceStateHIDSystemState);

CGEventRef cmdd = CGEventCreateKeyboardEvent(src, 0x38, true);
CGEventRef cmdu = CGEventCreateKeyboardEvent(src, 0x38, false);
CGEventRef spcd = CGEventCreateKeyboardEvent(src, 0x31, true);
CGEventRef spcu = CGEventCreateKeyboardEvent(src, 0x31, false);

CGEventSetFlags(spcd, kCGEventFlagMaskCommand);
CGEventSetFlags(spcu, kCGEventFlagMaskCommand);

CGEventTapLocation loc = kCGHIDEventTap; // kCGSessionEventTap also works
CGEventPost(loc, cmdd);
CGEventPost(loc, spcd);
CGEventPost(loc, spcu);
CGEventPost(loc, cmdu);

CFRelease(cmdd);
CFRelease(cmdu);
CFRelease(spcd);
CFRelease(spcu);
CFRelease(src);
}

How to simulate typing/keypresses in C++ on Mac OS?

Its possible to get any character you want. You are almost on correct path.
I think you just need to specify what unicode character you are interested in.
So instead of sending key if you send unicode and use kVK_Space as keycode you should have what you need and before posting the event you can call following code one that event object

if (unicode){
unichar str[2] = {0};
str[0] = (unichar)unicode;
memcpy(str, &unicode, 4);
CGEventKeyboardSetUnicodeString(theEvent, 1, str);
}


Related Topics



Leave a reply



Submit