I am writing a python code that tracks the mouse and the keyboard. I want the tracking of both to be in a single while loop like the following:
while True:
mouse_x, mouse_y = get_mouse_pos()
key_pressed = get_key_pressed()
print(key_pressed " is down")
print(f"The mouse position is: {mouse_x}, {mouse_y}")
Is there any way to do so without opening a thread for the keyboard reading?
I couldn't find a method that reads the keyboard without waiting for an input. I tried kbhit()
in msvcrt
module, but it only returns 0 no matter what I press, and the keyboard
module can read only a specific key non blockingly as far as I know.
CodePudding user response:
As far as I know, you will need to use two threads to monitor both the keyboard and the mouse at the same time, without blocking. You can create event listeners to monitor for both.
Note that I have incorporated an exit key x
which will exit the program when pressed.
Here is an example of how that could be achieved:
Code:
from pynput import mouse, keyboard
import sys
import threading
exit_program = False
def on_press(key):
global exit_program
try:
print(f'Key {key.char} was pressed.')
if key.char == "x":
exit_program = True
sys.exit()
except AttributeError:
print(f'Special key {key} was pressed.')
def on_move(x, y):
global exit_program
if exit_program:
sys.exit()
else:
print(f'Mouse moved to (x:{x} , y:{y})')
# Collect events from both keyboard and mouse
def start_listener_keyboard():
with keyboard.Listener(on_press=on_press) as listener:
listener.join()
def start_listener_mouse():
with mouse.Listener(on_move=on_move) as listener:
listener.join()
threading.Thread(target=start_listener_keyboard).start()
threading.Thread(target=start_listener_mouse).start()
Output:
Mouse moved to (x:1543 , y:210)
Mouse moved to (x:1543 , y:208)
Mouse moved to (x:1544 , y:206)
Mouse moved to (x:1544 , y:205)
Mouse moved to (x:1544 , y:201)
Mouse moved to (x:1544 , y:197)
Mouse moved to (x:1544 , y:195)
Mouse moved to (x:1544 , y:193)
Key d was pressed.
Mouse moved to (x:1544 , y:192)
Mouse moved to (x:1544 , y:188)
Mouse moved to (x:1543 , y:187)
Special key Key.backspace was pressed.
Key x was pressed.
CodePudding user response:
I found I can use pygame.event.get() to iterate through the events, catch a key down or a key up event, and get the unicode of the key that was down/up.
for event in pygame.event.get():
if event.type == pygame.QUIT:
break
elif event.type == pygame.KEYDOWN:
print(str(event.unicode) " is down")
elif event.type == pygame.KEYUP:
print(str(event.unicode) " is up")