聆听键盘事件而不会陷入陷阱? [英] Listening to keyboard events without trapping them?

查看:98
本文介绍了聆听键盘事件而不会陷入陷阱?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在编写一个命令行应用程序,该应用程序侦听X Windows中的Control键释放事件,并在检测到它们时提醒另一个进程.

I'm writing an command-line application which listens for Control key release events in X Windows and alerts another process when it detects them.

作为GNU/Linux的新手,我宁愿避免与GCC混为一谈,因此我正在寻找基于脚本的解决方案.由于我对Python有所了解,因此选择基于Python的解决方案似乎很自然,并在为示例搜罗Internet并阅读Python Xlib文档之后,将这些程序组合在一起,但仍需注意:陷阱事件,而不仅仅是侦听它们(我的意思是,此类事件不再传递给最初定向到的应用程序).

Being new to GNU/Linux, I'd prefer avoiding to fumble with GCC and therefore I'm looking for a scripting-based solution. Since I know a bit of Python, it seemed natural to go for a Python-based solution, and after scavenging the Internet for examples and reading Python Xlib docs, I've put together this programs which works, but with a caveat: it traps events instead of just listening for them (I mean such events are not passed anymore to the application which they were directed to in the first place).

我已经通过运行"xev"来跟踪控制键代码.由于我已经重新映射了修饰键,因此在您的系统上它们可能有所不同.

I've tracked down Control key codes by running "xev". Since I've remapped my modifier keys, on your system they may be different.

为简单起见,我省略了处理外部流程的代码.

To keep things simple, I've left out the code which deals with the external process.

谢谢您的帮助.

软件:

  • Python 2.7.2

  • Python 2.7.2

Python Xlib 0.15 RC1

Python Xlib 0.15 RC1

Perl v5.10.1

Perl v5.10.1

Debian GNU/Linux版本:6.0.3

Debian GNU/Linux version: 6.0.3

内核版本:Linux debian 2.6.32-5-686

Kernel version: Linux debian 2.6.32-5-686

我不明白的是,除非处理键盘事件,否则它们不会被捕获(在我的程序中,这意味着执行了"print"KeyRelease""行).由于在我的代码中,我既不会在Xlib上也不会在事件对象上调用任何方法,所以我不了解处理的区别在哪里.

What I can't figure out is that keyboard events do not get trapped unless they are processed (in my programs, this means the line 'print "KeyRelease"' gets executed). Since in my code I don't call any method either on Xlib or on the event object, I don't understand where the difference in processing lies.

除使用Xlib外,还欢迎您提出有关替代解决方案的建议.

Suggestions about alternative solutions besides using Xlib are also welcome.

我也了解Perl,只要它们不需要最新版本的系统库,关于Perl库的建议也将受到欢迎,因为Debian在其存储库中的可用软件包方面远远落后于其他人,并且如果它们具有许多依赖关系,则编译和安装最新版本的库可能会很困难(我曾尝试安装PyGTK,但由于未能引用我已安装的最新GLib而放弃了.)

I know Perl too, and suggestions about Perl libraries which could help are welcome too, as long as they don't require recent versions of system libraries, since Debian notoriously lags behind when it comes to packages available in its repositories, and compiling and installing last versions of libraries can be difficult if they have many dependencies (I've tried installing PyGTK, but gave up after failing to reference an up-to-date GLib I had installed).

    #!/usr/bin/env python

    from Xlib.display import Display
    from Xlib import X

    Control_R  = 64 # Keycode for right Control.
    Control_L  = 108 # Keycode for left Control.
    keycodes = [Control_R, Control_L] # Keycodes we are listening for.

    # Handle X events.
    def handle_event(event):
        # Let us know whether this event is about a Key Release of
        # one of the key we are interest in.
        if event.type == X.KeyRelease:
            keycode = event.detail
            if keycode in keycodes:
                print "KeyRelease"

    # Objects needed to call Xlib.
    display = Display()
    root = display.screen().root

    # Tell the X server we want to catch KeyRelease events.
    root.change_attributes(event_mask = X.KeyReleaseMask)

    # Grab those keys.
    for keycode in keycodes:
        root.grab_key(keycode, X.AnyModifier, 1, X.GrabModeAsync, X.GrabModeAsync)

    # Event loop.
    while 1:
        event = root.display.next_event()
        handle_event(event)

推荐答案

感谢Croad Langshan提到的pykeylogger库,以及该库的作者Tim Alexander提供的有用示例代码,我已经能够将我的程序更改为:

Thanks to the pykeylogger library mentioned by Croad Langshan, and to the helpful example code provided by Tim Alexander, the author of such library, I've been able to change my program to:

    #!/usr/bin/env python

    from pyxhook import HookManager

    watched_keys = ["Control_R", "Control_L"]

    def handle_event (event):
        if event.Key in watched_keys:
            print "KeyRelease"


    hm = HookManager()
    hm.HookKeyboard()
    hm.KeyUp = handle_event
    hm.start()

该程序可以毫无问题地实现我的目标.您可以阅读事件"对象的字段以获取有关事件的更多信息(请参见"pyxhook.py"的源代码).

This program accomplishes my goal without any issue. You can read the fields of the "event" object for further information about the event (see source code of "pyxhook.py").

这篇关于聆听键盘事件而不会陷入陷阱?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆