You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何限制Python的keyboard.add_hotkey()每次按键仅触发一次?

问题

现有如下代码:

import keyboard
def on_c_pressed():
    print("C key was pressed")

keyboard.add_hotkey('c', on_c_pressed)

运行时发现,按下并释放C键的过程中,on_c_pressed()函数会被快速重复触发。已知可以通过全局变量标记,配合on_c_pressed()和on_c_released()实现单次触发,但这种方式较为繁琐。请问有没有更简洁的方法或替代库,能实现每次按键仅检测一次按键状态?

解决方案

1. 用keyboard库原生的on_press_key方法

keyboard库自带的on_press_key方法默认只会在按键按下瞬间触发一次,不会重复执行,直接替换原有代码即可:

import keyboard

def on_c_pressed(event):
    print("C key was pressed")

# 绑定按键按下事件
keyboard.on_press_key('c', on_c_pressed)
# 保持程序运行,避免直接退出
keyboard.wait()

这种方式不需要额外状态管理,逻辑最简洁。

2. 换用pynput库实现

pynput是常用的输入监控库,天然支持单次按键触发,回调函数仅在按键按下时执行一次:

from pynput.keyboard import Listener

def on_press(key):
    try:
        # 判断按下的是C键
        if key.char == 'c':
            print("C key was pressed")
            # 如果只需要触发一次,可在这里调用 listener.stop() 停止监听
    except AttributeError:
        # 处理特殊按键(如Shift、Ctrl等非字符按键)
        pass

# 启动监听器并保持运行
with Listener(on_press=on_press) as listener:
    listener.join()

3. 优化原有add_hotkey的实现(不换库的小技巧)

如果坚持使用add_hotkey,可以通过装饰器封装状态,替代全局变量,代码更整洁:

import keyboard
from functools import wraps

def single_press_trigger(func):
    pressed_flag = False
    @wraps(func)
    def wrapper():
        nonlocal pressed_flag
        if not pressed_flag:
            pressed_flag = True
            func()
        # 绑定释放事件重置标记
        keyboard.add_hotkey('c', lambda: globals().update({'pressed_flag': False}), trigger_on_release=True)
    return wrapper

@single_press_trigger
def on_c_pressed():
    print("C key was pressed")

keyboard.add_hotkey('c', on_c_pressed)
keyboard.wait()

内容的提问来源于stack exchange,提问作者Anonymous

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.06 20:42:31