Python 键盘按下和释放监听器

7 投票
2 回答
28041 浏览
提问于 2025-04-18 10:41

我正在用Python代码控制一个遥控玩具车。目前的代码如下:

def getkey():
        fd = sys.stdin.fileno()
        old = termios.tcgetattr(fd)
        new = termios.tcgetattr(fd)
        new[3] = new[3] & ~TERMIOS.ICANON & ~TERMIOS.ECHO
        new[6][TERMIOS.VMIN] = 1
        new[6][TERMIOS.VTIME] = 0
        termios.tcsetattr(fd, TERMIOS.TCSANOW, new)
        c = None
        try:
                c = os.read(fd, 1)
        finally:
                termios.tcsetattr(fd, TERMIOS.TCSAFLUSH, old)
        return c

def car():
    while True:
        key = getkey()
        if key == 's': #Down arrow
            print "Down"
            Backward()
        elif key == 'w': #Up arrow
            print "Up"
            forward()
        elif key == 'a': 
            print "left"
            Left()
        elif key == 'd': 
            print "Right"
            Right()
        elif key == 'q': #Quit
            print "That's It"
            break
def forward():
    GPIO.output(11,True)  #Move forward

当我按下'w'键时,forward()这个方法会被调用,车子就会向前移动,但它不会停下来,直到我退出程序或者从其他方法调用GPIO.output(11, False)

有没有什么方法可以监听键盘,检测某个特定键的释放?

比如说,按下'w'键时调用这个方法,而松开时调用另一个方法。

伪代码:

if w_isPressed()
   forward()
else if w_isReleased()
    stop()

2 个回答

2

我遇到过类似的问题(我不是Python专家),但这个方法对我有效。

import pynput
from pynput import keyboard 

def on_press(key):
    try:
        print('Key {0} pressed'.format(key.char))
        #Add your code to drive motor
    except AttributeError:
        print('Key {0} pressed'.format(key))
        #Add Code
def on_release(key):
    print('{0} released'.format(key))
    #Add your code to stop motor
    if key == keyboard.Key.esc:
        # Stop listener
        # Stop the Robot Code
        return False

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

我看到过 Pygame 这个游戏开发库在类似的场景中被成功使用,它不仅能处理实时系统和生产中的机器,还能做一些不只是玩具的例子。我觉得在这里它也是一个合适的选择。你可以查看 pygame.key 模块,了解如何处理键盘输入。

简单来说,如果你对游戏开发不太熟悉,基本上就是在一个“无限”的游戏循环中不断检查事件,比如输入状态的变化,然后做出相应的反应。通常会根据经过的时间来更新系统的参数。有很多关于这方面的教程和 Pygame 的资料,Pygame 的文档也很不错。

这里有一个简单的例子,告诉你该怎么做:

import pygame

pygame.init()

# to spam the pygame.KEYDOWN event every 100ms while key being pressed
pygame.key.set_repeat(100, 100)

while 1:
    for event in pygame.event.get():
        if event.type == pygame.KEYDOWN:
            if event.key == pygame.K_w:
                print 'go forward'
            if event.key == pygame.K_s:
                print 'go backward'
        if event.type == pygame.KEYUP:
            print 'stop'

你需要根据你的汽车移动实现,来使用 pygame.KEYDOWNpygame.KEYUPpygame.key.set_repeat

撰写回答