Home > Blockchain >  python read keyboard key bad performance
python read keyboard key bad performance

Time:12-17

I'm working on a programm where I need a user input for selection while not focused on the console window. The method I want to use is with keyboard inputs on the numpad. I've found this library Python keyboard lib to achieve this. My problem here is that it takes very long time for python to register the key press and gives a feel of poor performance. I need to know whether numpad 4 or numpad 6 is pressed for navigation. In the wiki of the lib was mentioned that you shouldn't use:

while True:
if keyboard.is_pressed('space'):
    print('space was pressed!')

This will use 100% of your CPU and print the message many times.

So, this is my code:

print("Choose Attacker or Defender operator:")
print("  Attacker    Defender")
att_state = False
def_state = False
while True:
    if keyboard.read_key() == "4":
        clear()
        print("->Attacker    Defender")
        def_state = False
        att_state = True
    if keyboard.read_key() == "6":
        clear()
        print("  Attacker  ->Defender")
        att_state = False
        def_state = True
    if keyboard.read_key() == "5" and att_state:
        clear()
        printAllOp(attackers)
        break
    if keyboard.read_key() == "5" and def_state:
        clear()
        printAllOp(defenders)
        break

selection = 0
while att_state:
    if keyboard.read_key() == "4":
        if selection > 0:
            selection -= 1
            clear()
            printAllOp(attackers, selection)
    if keyboard.read_key() == "6":
        if selection < 31:
            selection  = 1
            clear()
            printAllOp(attackers, selection)
    if keyboard.read_key() == "2":
        if selection < 23:
            selection  = 7
            clear()
            printAllOp(attackers, selection)
    if keyboard.read_key() == "8":
        if selection > 6:
            selection -= 7
            clear()
            printAllOp(attackers, selection)
    if keyboard.read_key() == "5":
        clear()
        searchOp(attackers, selection, att_source)
        att_state = False
        break

I've also realized that the performance is different when using if and elif that's why everything is written with ifs for now.

CodePudding user response:

You can put microseconds or millisecond sleep for each while iteration, for 10 microseconds sleep,

import time

while True:
    if keyboard.is_pressed('space'):
        print('space was pressed!')
    time.sleep(seconds/100000.0)

This should reduce your CPU usage hence, it should increase the overall performance.

Even better, use keyboard hooks like keyboard.on_press. That's the right way of doing it.

Additionally, if it is ok for you to bind to an OS (Windows or particular version of Linux distribution), you can compile your python as binary, which is very simple to do using PyInstaller.

CodePudding user response:

You should not be using keyboard.read_key() at all, instead use keyboard.add_hotkey() to register callbacks which modify a global state.

Example:

att_state = False
def_state = False

def set_state(new_state):
    att_state = (new_state == 'att')
    def_state = not att_state
    # add code to update display

# Register callbacks for 4 and 6
keyboard.add_hotkey('4', lambda: set_state('att'))
keyboard.add_hotkey('6', lambda: set_state('def'))

# Process keystrokes until '5' is pressed
keyboard.wait(hotkey='5')

Note: I have never used this library and did not test this code (no Windows) so buyer beware :)

  • Related