在python中轮询键盘(检测按键)

2025-02-13 08:36:00
admin
原创
41
摘要:问题描述:如何从控制台 Python 应用程序轮询键盘?具体来说,我想在许多其他 I/O 活动(套接字选择、串行端口访问等)中执行类似操作:while True: # doing amazing pythonic embedded stuff # ... # periodically...

问题描述:

如何从控制台 Python 应用程序轮询键盘?具体来说,我想在许多其他 I/O 活动(套接字选择、串行端口访问等)中执行类似操作:

while True:
    # doing amazing pythonic embedded stuff
    # ...

    # periodically do a non-blocking check to see if
    # we are being told to do something else
    x = keyboard.read(1000, timeout = 0)

    if len(x):
        # ok, some key got pressed
        # do something

在 Windows 上执行此操作的正确 Python 方式是什么?此外,尽管不需要,但移植到 Linux 也不错。


解决方案 1:

标准方法是使用选择模块。

但是,这在 Windows 上不起作用。为此,您可以使用msvcrt模块的键盘轮询。

通常,这是通过多个线程来完成的——每个被“监视”的设备一个线程加上可能需要被设备中断的后台进程。

解决方案 2:

使用 curses 模块的解决方案。打印与按下的每个键相对应的数值:

import curses

def main(stdscr):
    # do not wait for input when calling getch
    stdscr.nodelay(1)
    while True:
        # get keyboard input, returns -1 if none available
        c = stdscr.getch()
        if c != -1:
            # print numeric value
            stdscr.addstr(str(c) + ' ')
            stdscr.refresh()
            # return curser to start position
            stdscr.move(0, 0)

if __name__ == '__main__':
    curses.wrapper(main)

解决方案 3:

好吧,由于我尝试在评论中发布解决方案失败了,所以这就是我想说的。我可以使用以下代码从本机 Python(在 Windows 上,但不是在其他任何地方)完成我想要的操作:

import msvcrt 

def kbfunc(): 
   x = msvcrt.kbhit()
   if x: 
      ret = ord(msvcrt.getch()) 
   else: 
      ret = 0 
   return ret

解决方案 4:

这些答案对我来说都不太适用。这个包 pynput 正好满足了我的需要。

https://pypi.python.org/pypi/pynput

from pynput.keyboard import Key, Listener

def on_press(key):
    print('{0} pressed'.format(
        key))

def on_release(key):
    print('{0} release'.format(
        key))
    if key == Key.esc:
        # Stop listener
        return False

# Collect events until released
with Listener(
        on_press=on_press,
        on_release=on_release) as listener:
    listener.join()

解决方案 5:

import sys
import select

def heardEnter():
    i,o,e = select.select([sys.stdin],[],[],0.0001)
    for s in i:
        if s == sys.stdin:
            input = sys.stdin.readline()
            return True
    return False

解决方案 6:

来自评论:

import msvcrt # built-in module

def kbfunc():
    return ord(msvcrt.getch()) if msvcrt.kbhit() else 0

谢谢你的帮助。我最终编写了一个名为 PyKeyboardAccess.dll 的 C DLL 并访问 crt conio 函数,导出此例程:

#include <conio.h>

int kb_inkey () {
   int rc;
   int key;

   key = _kbhit();

   if (key == 0) {
      rc = 0;
   } else {
      rc = _getch();
   }

   return rc;
}

我使用 ctypes 模块(内置于 python 2.5)在 python 中访问它:

import ctypes
import time

# first, load the DLL
try:
    kblib = ctypes.CDLL("PyKeyboardAccess.dll")
except:
    raise ("Error Loading PyKeyboardAccess.dll")

# now, find our function
try:
    kbfunc = kblib.kb_inkey
except:
    raise ("Could not find the kb_inkey function in the dll!")

# Ok, now let's demo the capability  
while True:
    x = kbfunc()

    if x != 0:
        print "Got key: %d" % x
    else:
        time.sleep(.01)

解决方案 7:

kbhit我在http://home.wlu.edu/~levys/software/kbhit.py上发现了一个跨平台实现(进行了编辑以删除不相关的代码):

import os
if os.name == 'nt':
    import msvcrt
else:
    import sys, select

def kbhit():
    ''' Returns True if a keypress is waiting to be read in stdin, False otherwise.
    '''
    if os.name == 'nt':
        return msvcrt.kbhit()
    else:
        dr,dw,de = select.select([sys.stdin], [], [], 0)
        return dr != []

确保read()等待字符——该函数将一直返回,True直到您这样做!

解决方案 8:

您可以看看pygame如何处理这个问题以窃取一些想法。

解决方案 9:

我用它来检查按键,非常简单:

#!/usr/bin/python3
# -*- coding: UTF-8 -*-

import curses, time

def main(stdscr):
    """checking for keypress"""
    stdscr.nodelay(True)  # do not wait for input when calling getch
    return stdscr.getch()

while True:
    print("key:", curses.wrapper(main)) # prints: 'key: 97' for 'a' pressed
                                        # '-1' on no presses
    time.sleep(1)

虽然 curses 在 Windows 上无法运行,但有一个 'unicurses' 版本,据说可以在 Linux、Windows、Mac 上运行,但我无法让它运行

解决方案 10:

另一个选择是使用sshkeyboard库来对按键做出反应,而不是定期轮询它们,并且可能会错过按键:

from sshkeyboard import listen_keyboard, stop_listening

def press(key):
    print(f"'{key}' pressed")
    if key == "z":
        stop_listening()

listen_keyboard(on_press=press)

只需pip install sshkeyboard使用它。

解决方案 11:

这可以使用 python 中的“pynput”模块来完成,您按下一个键就会打印出来,就这么简单!

  1. PIP 在命令提示符中安装模块,输入以下文本并按回车键

pip install pynput

  1. 运行以下代码:

from pynput.keyboard import Key, Listener

def pressed(key):
    print('Pressed:',key)

def released(key):
    print('Released:',key)
    if key == Key.enter:
        # Stop detecting when enter key is pressed
        return False

# Below loop for Detcting keys runs until enter key is pressed
with Listener(on_press=pressed, on_release=released) as detector:
    detector.join()
  1. Key.enter您可以通过将代码第 8 行中的任意键更改为其他键来结束循环。

解决方案 12:

如果结合使用 time.sleep、threading.Thread 和 sys.stdin.read,您可以轻松等待指定的时间输入然后继续,而且这也应该是跨平台兼容的。

t = threading.Thread(target=sys.stdin.read(1) args=(1,))
t.start()
time.sleep(5)
t.join()

你也可以将其放入如下函数中

def timed_getch(self, bytes=1, timeout=1):
    t = threading.Thread(target=sys.stdin.read, args=(bytes,))
    t.start()
    time.sleep(timeout)
    t.join()
    del t

虽然这不会返回任何东西,所以你应该使用多处理池模块,你可以在这里找到它:如何从 python 中的线程获取返回值?

相关推荐
  政府信创国产化的10大政策解读一、信创国产化的背景与意义信创国产化,即信息技术应用创新国产化,是当前中国信息技术领域的一个重要发展方向。其核心在于通过自主研发和创新,实现信息技术应用的自主可控,减少对外部技术的依赖,并规避潜在的技术制裁和风险。随着全球信息技术竞争的加剧,以及某些国家对中国在科技领域的打压,信创国产化显...
工程项目管理   1565  
  为什么项目管理通常仍然耗时且低效?您是否还在反复更新电子表格、淹没在便利贴中并参加每周更新会议?这确实是耗费时间和精力。借助软件工具的帮助,您可以一目了然地全面了解您的项目。如今,国内外有足够多优秀的项目管理软件可以帮助您掌控每个项目。什么是项目管理软件?项目管理软件是广泛行业用于项目规划、资源分配和调度的软件。它使项...
项目管理软件   1354  
  信创国产芯片作为信息技术创新的核心领域,对于推动国家自主可控生态建设具有至关重要的意义。在全球科技竞争日益激烈的背景下,实现信息技术的自主可控,摆脱对国外技术的依赖,已成为保障国家信息安全和产业可持续发展的关键。国产芯片作为信创产业的基石,其发展水平直接影响着整个信创生态的构建与完善。通过不断提升国产芯片的技术实力、产...
国产信创系统   21  
  信创生态建设旨在实现信息技术领域的自主创新和安全可控,涵盖了从硬件到软件的全产业链。随着数字化转型的加速,信创生态建设的重要性日益凸显,它不仅关乎国家的信息安全,更是推动产业升级和经济高质量发展的关键力量。然而,在推进信创生态建设的过程中,面临着诸多复杂且严峻的挑战,需要深入剖析并寻找切实可行的解决方案。技术创新难题技...
信创操作系统   27  
  信创产业作为国家信息技术创新发展的重要领域,对于保障国家信息安全、推动产业升级具有关键意义。而国产芯片作为信创产业的核心基石,其研发进展备受关注。在信创国产芯片的研发征程中,面临着诸多复杂且艰巨的难点,这些难点犹如一道道关卡,阻碍着国产芯片的快速发展。然而,科研人员和相关企业并未退缩,积极探索并提出了一系列切实可行的解...
国产化替代产品目录   28  
热门文章
项目管理软件有哪些?
云禅道AD
禅道项目管理软件

云端的项目管理软件

尊享禅道项目软件收费版功能

无需维护,随时随地协同办公

内置subversion和git源码管理

每天备份,随时转为私有部署

免费试用