Skip to content

Commit

Permalink
This commit fixes #148: Volume keys don't work on Mac.
Browse files Browse the repository at this point in the history
Also added brightness, keyboard illumination, play/pause, next/previous
  • Loading branch information
gurel committed Mar 21, 2016
1 parent d2d859a commit 163feb5
Show file tree
Hide file tree
Showing 2 changed files with 75 additions and 21 deletions.
27 changes: 14 additions & 13 deletions src/keycode.h
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,8 @@ extern "C"

#include <Carbon/Carbon.h> /* Really only need <HIToolbox/Events.h> */
#include <ApplicationServices/ApplicationServices.h>

#import <IOKit/hidsystem/ev_keymap.h>

enum _MMKeyCode {
K_NOT_A_KEY = 9999,
K_BACKSPACE = kVK_Delete,
Expand Down Expand Up @@ -49,24 +50,24 @@ enum _MMKeyCode {
K_SPACE = kVK_Space,
K_PRINTSCREEN = K_NOT_A_KEY,

K_AUDIO_VOLUME_MUTE = kVK_Mute,
K_AUDIO_VOLUME_DOWN = kVK_VolumeDown,
K_AUDIO_VOLUME_UP = kVK_VolumeUp,
K_AUDIO_PLAY = K_NOT_A_KEY,
K_AUDIO_VOLUME_MUTE = NX_KEYTYPE_MUTE,
K_AUDIO_VOLUME_DOWN = NX_KEYTYPE_SOUND_DOWN,
K_AUDIO_VOLUME_UP = NX_KEYTYPE_SOUND_UP,
K_AUDIO_PLAY = NX_KEYTYPE_PLAY,
K_AUDIO_STOP = K_NOT_A_KEY,
K_AUDIO_PAUSE = K_NOT_A_KEY,
K_AUDIO_PREV = K_NOT_A_KEY,
K_AUDIO_NEXT = K_NOT_A_KEY,
K_AUDIO_PAUSE = NX_KEYTYPE_PLAY,
K_AUDIO_PREV = NX_KEYTYPE_PREVIOUS,
K_AUDIO_NEXT = NX_KEYTYPE_NEXT,
K_AUDIO_REWIND = K_NOT_A_KEY,
K_AUDIO_FORWARD = K_NOT_A_KEY,
K_AUDIO_REPEAT = K_NOT_A_KEY,
K_AUDIO_RANDOM = K_NOT_A_KEY,

K_LIGHTS_MON_UP = K_NOT_A_KEY,
K_LIGHTS_MON_DOWN = K_NOT_A_KEY,
K_LIGHTS_KBD_TOGGLE = K_NOT_A_KEY,
K_LIGHTS_KBD_UP = K_NOT_A_KEY,
K_LIGHTS_KBD_DOWN = K_NOT_A_KEY
K_LIGHTS_MON_UP = NX_KEYTYPE_BRIGHTNESS_UP,
K_LIGHTS_MON_DOWN = NX_KEYTYPE_BRIGHTNESS_DOWN,
K_LIGHTS_KBD_TOGGLE = NX_KEYTYPE_ILLUMINATION_TOGGLE,
K_LIGHTS_KBD_UP = NX_KEYTYPE_ILLUMINATION_UP,
K_LIGHTS_KBD_DOWN = NX_KEYTYPE_ILLUMINATION_DOWN
};

typedef CGKeyCode MMKeyCode;
Expand Down
69 changes: 61 additions & 8 deletions src/keypress.c
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@

#if defined(IS_MACOSX)
#include <ApplicationServices/ApplicationServices.h>
#import <IOKit/hidsystem/IOHIDLib.h>
#import <IOKit/hidsystem/ev_keymap.h>
#elif defined(USE_X11)
#include <X11/extensions/XTest.h>
#include "xdisplay.h"
Expand All @@ -26,6 +28,45 @@
microsleep(DEADBEEF_UNIFORM(0.0, 62.5)))
#endif

#if defined(IS_MACOSX)
bool keyCodeRequiresSystemDefinedEvent(MMKeyCode code) {
return code == NX_KEYTYPE_SOUND_UP ||
code == NX_KEYTYPE_SOUND_DOWN ||
code == NX_KEYTYPE_MUTE ||
code == NX_KEYTYPE_PLAY ||
code == NX_KEYTYPE_BRIGHTNESS_UP ||
code == NX_KEYTYPE_BRIGHTNESS_DOWN ||
code == NX_KEYTYPE_PLAY ||
code == NX_KEYTYPE_PREVIOUS ||
code == NX_KEYTYPE_NEXT ||
code == NX_KEYTYPE_ILLUMINATION_UP ||
code == NX_KEYTYPE_ILLUMINATION_DOWN ||
code == NX_KEYTYPE_ILLUMINATION_TOGGLE
;
}
static io_connect_t _getAuxiliaryKeyDriver(void)
{
static mach_port_t sEventDrvrRef = 0;
mach_port_t masterPort, service, iter;
kern_return_t kr;

if (!sEventDrvrRef)
{
kr = IOMasterPort( bootstrap_port, &masterPort );
assert(KERN_SUCCESS == kr);
kr = IOServiceGetMatchingServices(masterPort, IOServiceMatching( kIOHIDSystemClass), &iter );
assert(KERN_SUCCESS == kr);
service = IOIteratorNext( iter );
assert(service);
kr = IOServiceOpen(service, mach_task_self(), kIOHIDParamConnectType, &sEventDrvrRef );
assert(KERN_SUCCESS == kr);
IOObjectRelease(service);
IOObjectRelease(iter);
}
return sEventDrvrRef;
}
#endif

#if defined(IS_WINDOWS)
void win32KeyEvent(int key, MMKeyFlags flags)
{
Expand All @@ -43,14 +84,26 @@ void win32KeyEvent(int key, MMKeyFlags flags)
void toggleKeyCode(MMKeyCode code, const bool down, MMKeyFlags flags)
{
#if defined(IS_MACOSX)
CGEventRef keyEvent = CGEventCreateKeyboardEvent(NULL,
(CGKeyCode)code, down);
assert(keyEvent != NULL);

CGEventSetType(keyEvent, down ? kCGEventKeyDown : kCGEventKeyUp);
CGEventSetFlags(keyEvent, flags);
CGEventPost(kCGSessionEventTap, keyEvent);
CFRelease(keyEvent);
if (keyCodeRequiresSystemDefinedEvent(code)) {
NXEventData event;
kern_return_t kr;
IOGPoint loc = { 0, 0 };
UInt32 evtInfo = code << 16 | (down?NX_KEYDOWN:NX_KEYUP) << 8;
bzero(&event, sizeof(NXEventData));
event.compound.subType = NX_SUBTYPE_AUX_CONTROL_BUTTONS;
event.compound.misc.L[0] = evtInfo;
kr = IOHIDPostEvent( _getAuxiliaryKeyDriver(), NX_SYSDEFINED, loc, &event, kNXEventDataVersion, 0, FALSE );
assert( KERN_SUCCESS == kr );
} else {
CGEventRef keyEvent = CGEventCreateKeyboardEvent(NULL,
(CGKeyCode)code, down);
assert(keyEvent != NULL);

CGEventSetType(keyEvent, down ? kCGEventKeyDown : kCGEventKeyUp);
CGEventSetFlags(keyEvent, flags);
CGEventPost(kCGSessionEventTap, keyEvent);
CFRelease(keyEvent);
}
#elif defined(IS_WINDOWS)
const DWORD dwFlags = down ? 0 : KEYEVENTF_KEYUP;

Expand Down

0 comments on commit 163feb5

Please sign in to comment.