我对的行为有问题:
比如说,我按下Cmd-Shift-P键组合。当我释放“P”键时,热键事件就会触发。我需要在所有按键都松开(即:Cmd和Shift键也被释放)时触发或手动触发事件。
很容易监控热键,但是我没有看到监控单个按键的内容。如果我能监控修改器键状态,那就可以了。
有什么提示吗?
提前致谢!
更新:
我尝试使用和,但是虽然有效果,但这两个都没有效果,尽管我以完全相同的方式设置了它们。
EventTypeSpec eventTypes[] = {{kEventClassKeyboard, kEventHotKeyReleased}, {kEventClassKeyboard, kEventRawKeyUp}};
// Changing the order in the list does not help, nor does removing kEventHotKeyReleased
OSStatus err = InstallApplicationEventHandler(&globalHotkeyHandler, GetEventTypeCount(eventTypes), eventTypes, NULL, NULL);
// err == noErr after this line
我无法理解为什么kEventRawKeyUp
不会调用globalHotKeyHandler
方法,但是会调用kEventHotKeyReleased
方法。下面是我的globalHotKeyHandler
方法:
OSStatus globalHotkeyHandler(EventHandlerCallRef nextHandler, EventRef anEvent, void *userData) {
NSLog(@"Something happened!");
}
我是否需要进行其他调用或者我忘记了什么?
N.B: 乍一看,似乎可能是辅助设备访问被禁用了,但实际上并不是。所以我很困惑。
更新2:
我对Leibowitzn建议的CGEventTap
进行了一些调查,并得出了以下设置:
CFMachPortRef keyUpEventTap = CGEventTapCreate(kCGHIDEventTap,kCGHeadInsertEventTap,kCGEventTapOptionListenOnly,kCGEventKeyUp,&keyUpCallback,NULL);
CFRunLoopSourceRef keyUpRunLoopSourceRef = CFMachPortCreateRunLoopSource(NULL, keyUpEventTap, 0);
CFRelease(keyUpEventTap);
CFRunLoopAddSource(CFRunLoopGetCurrent(), keyUpRunLoopSourceRef, kCFRunLoopDefaultMode);
CFRelease(keyUpRunLoopSourceRef);
...和回调函数:
CGEventRef keyUpCallback (CGEventTapProxy proxy, CGEventType type, CGEventRef event, void *refcon) {
NSLog(@"KeyUp event tapped!");
return event;
}
正如您所看到的,我正在使用kCGEventKeyUp
作为事件挂钩的掩码,但不知何故,我收到了鼠标按下事件??!?
更新3:
好了,请忘记那个问题,我忽略了文档中说要使用CGEventMaskBit(kCGEventKeyUp)作为此参数的行,因此正确的调用是:
CGEventTapCreate(kCGHIDEventTap,kCGHeadInsertEventTap,kCGEventTapOptionListenOnly,CGEventMaskBit(kCGEventKeyUp),&keyUpCallback,NULL);
我还有一个问题:修饰键不会触发 kCGEventKeyUp 事件...
更新 4:
好了,再忘掉它吧...今天我提出问题后5分钟必须回答自己的问题!
要拦截修饰键,请使用 kCGEventFlagsChanged
事件:
CGEventTapCreate(kCGHIDEventTap,kCGHeadInsertEventTap,kCGEventTapOptionListenOnly,CGEventMaskBit(kCGEventFlagsChanged),&callbackFunction,NULL);
因此,本质上我已经实现了键和修饰键状态检测,但是我仍然想知道为什么kEventRawKeyUp
不起作用...
N.B:还要注意的是,我正在Tiger上开发,目标是尽可能支持新旧版本的操作系统。CGEventTap仅适用于10.4+,因此我现在将使用它,但欢迎提供向后兼容的解决方案。