【发布时间】:2008-11-27 15:27:46
【问题描述】:
创建半透明窗口 (based on example code by Matt Gemmell) 后,我想在此窗口中获取键盘事件。当我的应用程序是活动应用程序时,似乎只有键盘事件,而我想要键盘事件,即使我的应用程序不活动但窗口可见。
基本上我想要 Quicksilver 应用程序(由 blacktree)提供的行为。
有人对如何做到这一点有任何提示吗?
【问题讨论】:
创建半透明窗口 (based on example code by Matt Gemmell) 后,我想在此窗口中获取键盘事件。当我的应用程序是活动应用程序时,似乎只有键盘事件,而我想要键盘事件,即使我的应用程序不活动但窗口可见。
基本上我想要 Quicksilver 应用程序(由 blacktree)提供的行为。
有人对如何做到这一点有任何提示吗?
【问题讨论】:
有两种选择:
GetEventMonitorTarget() 和附加的 Carbon 运行循环来抓取键盘事件。示例代码可在 CocoaDev 的 this page 上获得。
CGEventTapCreate 注册事件陷阱。示例代码可在 Apple 开发人员邮件列表中的 this thread 中找到。
编辑:请注意,只有在通用访问首选项窗格中选中“启用辅助设备访问”时,这些方法才有效。
【讨论】:
可能更适合您的更简单的方法是让您的应用仅在后台运行。 LSUIElement plist 键的 CocoaDev 上的讨论解释了如何设置它。基本上,您的应用程序不会出现在 Dock 或应用程序切换器中,并且在激活时不会替换当前应用程序的菜单栏。从用户的角度来看,它永远不是“活动”应用程序,但您打开的任何窗口都可以被激活并正常响应事件。唯一需要注意的是你永远不会显示你的菜单栏,所以你可能必须设置一个 NSStatusItem (显示在菜单栏右侧的图标菜单之一)来控制(即退出,调出首选项等)您的应用程序。
编辑:我完全忘记了 Interface Builder 中的非激活面板复选框。您需要使用 NSPanel 而不是 NSWindow 来获得此选择。此设置允许您的面板在不激活您的应用程序的情况下接受点击和键盘输入。我敢打赌,QuickSilver 在他们的 UI 中使用了这个设置和 Carbon Hot Keys API 的某种组合。
【讨论】:
更新:
Apple 实际上似乎从 10.5 BTW 开始再次改变了一切(我最近升级了,我的示例代码没有像以前那样工作)。
现在,您确实只能捕获设置事件点击的 keydown 事件,前提是您是 root 或启用了辅助设备,无论您计划捕获哪个级别以及是否选择捕获(这允许您修改甚至丢弃事件)或只听。当 flags 发生变化(实际上甚至改变这些)和其他事件时,您仍然可以获得信息,但在其他情况下没有 keydown。
但是,使用 carbon 事件处理程序和方法 RegisterEventHotKey() 允许您注册一个热键,并且在按下它时您会收到通知,您既不需要是 root 也不需要启用辅助设备之类的东西.我认为 Quicksilver 可能就是这样做的。
【讨论】: