
keyboard——python中的键盘事件捕捉库
最近在做一键截图的脚本,这种东西其实10年之前玩过游戏都很熟悉,就类似脚本精灵,读取一些按键/自动执行一些按键。
在Github上官方就有很详细的介绍
安装:
pip install keyboard
这次主要还是读取键盘,而且是读取小键盘。
这里涉及到一个问题小键盘和大键盘都是有数字的,在名字属性上一摸一样,所以一般使用ScanCode键盘扫描码或者按键事件中的is_keypad来做判断。
这个库有个很好用的功能,在shell中输入下方代码,就可以直接答应事件信息一目了然,想识别哪个键按下看得很清楚。
python -m keyboard
{"event_type": "down", "scan_code": 29, "name": "ctrl", "time": 1736676278.0122712, "is_keypad": false}
{"event_type": "down", "scan_code": 46, "name": "c", "time": 1736676278.0431879, "is_keypad": false}
使用
首先,在下方官方演示代码中提到,在监听键盘时候,我们添加了一个监听任务(热键),之后程序就会自动关闭,如果我们想要之后没有代码,程序会关闭。这时不要使用while True: pass,这样会占用100%的CPU,所以使用keyboard.wait(),库内代码会执行一个休眠的任务。
Preventing the program from closing防止程序关闭
import keyboard
keyboard.add_hotkey('space', lambda: print('space was pressed!'))
# If the program finishes, the hotkey is not in effect anymore.
# Don't do this! This will use 100% of your CPU.
#while True: pass
# Use this instead
keyboard.wait()
# or this
import time
while True:
time.sleep(1000000)
当然你也可是使用更简单的监听一次某个按键,下面演示的是空格。与上面不一样的是,上面的代码会持续监听直到你手动关闭程序。
import keyboard
# Don't do this! This will use 100% of your CPU until you press the key.
#
#while not keyboard.is_pressed('space'):
# continue
#print('space was pressed, continuing...')
# Do this instead
keyboard.wait('space')
print('space was pressed, continuing...')
详细讲下其中的几个我用到的方法。
hook方法主要是启动一个获得所有键盘事件的钩子,只要运行,就完成了注册,这个callback回调函数需要一个形参来接受事件,传递给回调的事件的类型为keyboard.KeyboardEvent,事件类型如右图,而且在后续的使用中发现,即使是在被callback阻塞的情况下,它依旧会捕捉事件,但是不会立刻运行。suppress代表是否抑制按键被其他程序使用,默认就行,on_remove是在被钩子被移除时执行的函数,默认为空。
unhook解除钩子方法有两种一种是全部移除,一种是指定移除。
is_pressed是一种最常见的捕捉方式,提供一种不阻塞的按键监听,只会返回当前按键是否按下,一般用在循环退出的判断。
wait也很易用,阻塞监听,用于退出比较多。
keyboard.hook(callback, suppress=False, on_remove=<lambda>)
keyboard.unhook_all_hotkeys()
keyboard.unhook(remove) # remove = keyboard.hook(callback)
keyboard.is_pressed(hotkey) #hotkey = "q"
keyboard.wait(hotkey)
下面是一段如何检测小键盘的按键的demo。
import keyboard
import time
def print_5_times():
for i in range(5):
print(i)
time.sleep(0.1)
def thats_what_I_really_want(keyboard_event):
scan_code = keyboard_event.scan_code
name = keyboard_event.name
event_type = keyboard_event.event_type
# print(scan_code,name)
is_keypad = keyboard_event.is_keypad
if event_type == "down":
if name == "5" and is_keypad == True:
print("5被按下了")
print_5_times()
elif name == "5" and is_keypad == False:
print("这不是我要的5")
else:
print("5没有被按下")
keyboard.hook(lambda e: thats_what_I_really_want(e),suppress=True)
keyboard.wait()