performance – Python pynput keyboard + mouse input printer

I needed to have input shown for some things in a game I play on Linux, but Linux doesn’t seem to have any good input display programs. I decided it would be good enough to have python print to a pair of xterm windows (one for keyboard and one for mouse) using pynput. I do this using two different python programs because the only way I found to have one python programs deal with two terminals is to constantly write to a file and use tail -f, and I didn’t want to do that.

Because both programs ended up being so small and simple, I tried to write it so that the key/mouse listeners would run their functions as fast as possible. But I might have missed some things that could be done. I’m wondering if anyone knows of any other ways to optimize this for response time. I know it won’t make anything close to a noticeable difference, I’m just asking out of curiosity.

*Edited because I thought of ways to make it faster

mouse_listener.py

from pynput import mouse

def main():
    
    print_count = 0
    
    def on_click(x,
        y,
        button,
        pressed,
        local_print=print,
        dashes="--- ",
        no_dashes="    ",
        pressed_str=" mouse pressed",
        released_str=" mouse released"
        ):
        nonlocal print_count
        if print_count >= 10:
            if pressed is True:
                local_print(dashes + button.name + pressed_str)
                print_count = 0
            else:
                local_print(dashes + button.name + released_str)
                print_count = 0
        else:
            if pressed is True:
                local_print(no_dashes + button.name + pressed_str)
                print_count = print_count + 1
            else:
                local_print(no_dashes + button.name + released_str)
                print_count = print_count + 1
    
    def on_scroll(x,
        y,
        dx,
        dy,
        local_print=print,
        dashes="--- ",
        no_dashes="    ",
        up_str="scroll up",
        down_str="scroll down"
        ):
        nonlocal print_count
        if print_count >= 10:
            if dy == 1:
                local_print(dashes + up_str)
                print_count = 0
            else:
                local_print(dashes + down_str)
                print_count = 0
        else:
            if dy == 1:
                local_print(no_dashes + up_str)
                print_count = print_count + 1
            else:
                local_print(no_dashes + down_str)
                print_count = print_count + 1
    
    try:
        listener = mouse.Listener(on_click=on_click, on_scroll=on_scroll)
        listener.start()
        listener.join()
    except KeyboardInterrupt:
        listener.stop()

main()

key_listener.py

from pynput import keyboard

def main():
    
    print_count = 0
    held = set()
    
    def on_press(key,
        local_print=print,
        local_hasattr=hasattr,
        held_local=held,
        hold=held.add,
        str_lower=str.lower,
        dashes="--- ",
        no_dashes="    ",
        end_text=" pressed",
        str_for_hasattr="name"
        ):
        nonlocal print_count
        if key not in held_local:
            if local_hasattr(key, str_for_hasattr):
                if print_count >= 10:
                    local_print(dashes + key.name + end_text)
                    print_count = 0
                else:
                    local_print(no_dashes + key.name + end_text)
                    print_count = print_count + 1
            else:
                if print_count >= 10:
                    local_print(dashes + str_lower(key.char) + end_text)
                    print_count = 0
                else:
                    local_print(no_dashes + str_lower(key.char) + end_text)
                    print_count = print_count + 1
            hold(key)
    
    def on_release(key,
        local_print=print,
        local_hasattr=hasattr,
        unhold=held.remove,
        str_lower=str.lower,
        dashes="--- ",
        no_dashes="    ",
        end_text=" released",
        str_for_hasattr="name"
        ):
        nonlocal print_count
        if local_hasattr(key, str_for_hasattr):
            if print_count >= 10:
                local_print(dashes + key.name + end_text)
                print_count = 0
            else:
                local_print(no_dashes + key.name + end_text)
                print_count = print_count + 1
        else:
            if print_count >= 10:
                local_print(dashes + str_lower(key.char) + end_text)
                print_count = 0
            else:
                local_print(no_dashes + str_lower(key.char) + end_text)
                print_count = print_count + 1
        try: # I don't trust this part
            unhold(key)
        except KeyError:
            pass
    
    try: # TypeError is possible because numpad 5's char attribute is None
        listener = keyboard.Listener(on_press=on_press, on_release=on_release)
        listener.start()
        listener.join()
    except (KeyboardInterrupt, TypeError):
        listener.stop()

main()

xterm_opener.sh

xterm -xrm 'XTerm.vt100.allowTitleOps: false' -T "keyboard" -geometry 28x16 -e python3 '/home/USERNAME/input_listener/key_listener.py' &
xterm -xrm 'XTerm.vt100.allowTitleOps: false' -T "mouse" -geometry 28x16 -e python3 '/home/USERNAME/input_listener/mouse_listener.py'

performance – under 100 line Python pynput keyboard + mouse input printer

I needed to have input shown for some things in a game I play on Linux, but Linux doesn’t seem to have any good input display programs. I decided it would be good enough to have python print to a pair of xterm windows (one for keyboard and one for mouse) using pynput. I do this using two different python programs because the only way I found to have one python programs deal with two terminals is to constantly write to a file and use tail -f, and I didn’t want to do that.

Because both programs ended up being so small and simple, I tried to write it so that the key/mouse listeners would run their functions as fast as possible. But I might have missed some things that could be done. I’m wondering if anyone knows of any other ways to optimize this for response time. I know it won’t make anything close to a noticeable difference, I’m just asking out of curiosity.

mouse_listener.py

from pynput import mouse

def main():
    
    print_count = 0
    
    def on_click(x, y, button, pressed, local_print=print):
        nonlocal print_count
        try:
            if print_count >= 10:
                local_print(f"--- {button.name} mouse {'pressed' if pressed else 'released'}")
                print_count = 0
            else:
                local_print(f"    {button.name} mouse {'pressed' if pressed else 'released'}")
                print_count += 1
        except AttributeError:
            pass
    
    def on_scroll(x, y, dx, dy, local_print=print):
        nonlocal print_count
        try:
            if print_count >= 10:
                local_print(f"--- {'scroll up' if dy == 1 else 'scroll down'}")
                print_count = 0
            else:
                local_print(f"    {'scroll up' if dy == 1 else 'scroll down'}")
                print_count += 1
        except AttributeError:
            pass
    
    try:
        listener = mouse.Listener(on_click=on_click, on_scroll=on_scroll)
        listener.start()
        listener.join()
    except KeyboardInterrupt:
        listener.stop()

main()

key_listener.py

from pynput import keyboard

def main():
    
    print_count = 0
    held = set() # this is needed because it keeps calling on_press when you hold a key
    
    def on_press(key, local_print=print, held_local=held, hold=held.add, str_lower=str.lower):
        nonlocal print_count
        if key not in held_local:
            try:
                if print_count >= 10:
                    local_print(f"--- {key.name} pressed")
                    print_count = 0
                else:
                    local_print(f"    {key.name} pressed")
                    print_count += 1
            except AttributeError:
                if print_count >= 10:
                    local_print(f"--- {str_lower(key.char) if key.char is not None else 5} pressed")
                    print_count = 0
                else:
                    local_print(f"    {str_lower(key.char) if key.char is not None else 5} pressed")
                    print_count += 1
            hold(key)
    
    def on_release(key, local_print=print, unhold=held.remove, str_lower=str.lower):
        nonlocal print_count
        try:
            if print_count >= 10:
                local_print(f"--- {key.name} released")
                print_count = 0
            else:
                local_print(f"    {key.name} released")
                print_count += 1
        except AttributeError:
            if print_count >= 10:
                local_print(f"--- {str_lower(key.char) if key.char is not None else 5} released")
                print_count = 0
            else:
                local_print(f"    {str_lower(key.char) if key.char is not None else 5} released")
                print_count += 1
        try:
            unhold(key)
        except KeyError:
            pass
    
    try:
        listener = keyboard.Listener(on_press=on_press, on_release=on_release)
        listener.start()
        listener.join()
    except KeyboardInterrupt:
        listener.stop()

main()

xterm_opener.sh

xterm -xrm 'XTerm.vt100.allowTitleOps: false' -T "keyboard" -geometry 28x16 -e python3 '/home/USERNAME/input_listener/key_listener.py' &
xterm -xrm 'XTerm.vt100.allowTitleOps: false' -T "mouse" -geometry 28x16 -e python3 '/home/USERNAME/input_listener/mouse_listener.py'

macos – automatically change keyboard shortcuts when keyboard layout changes

I have a MacBook Pro with American keyboard, but I also use a Bluetooth keyboard with Spanish layout.
To cycle through windows I use command+` in the built in keyboard, but when I’m using the Spanish keyboard this does not work and I have to change the shortcut to command+º.
Is there a way to quickly change this shortcut so I don’t have to open the settings window every time?

catalina – Keyboard Shortcut for Automator Service

I have a word count ‘services’ called with LMB and scrolling down to the services menu. I’d like to have a keyboard shortcut for it since I use it very often. All of the answers I see require that the services be in finder, but that doesn’t seem to work with word count needing to extract from the current application. Under ‘services’ in keyboard shortcuts, is there’s no way to select the ‘services’ that are in LMB? I’m in Catalina.

enter image description hereenter image description here

I’ve looked at the answers here Keyboard shortcut (almost) never works for Automator service and am still unable to figure it out. Thanks!

kde – does konsole have a keyboard only block selection mode or is it broken

I would like to select a group of words using the keyboard only.

https://docs.kde.org/stable5/en/applications/konsole/key-bindings.html

here they did have “Ctl-Shift-B” to enter block selection mode, it does not seem to work.
https://bugs.kde.org/show_bug.cgi?id=122831

termites contrl-shift-space does not work for konsole

alt + arrow keys will leap words, but with shift does not also select them

any help appreciated.

Why do France and Belgium use the AZERTY keyboard? What is the historical origin of this redundancy?

So, how did the keyboard layouts develop historically?

Did you have a look at https://en.wikipedia.org/wiki/AZERTY#History and https://en.wikipedia.org/wiki/QWERTY ?

In the beginning, there was not a keyboard layout. Each keyboard manufacturer. In fact, early Sholes typewriters had the keys arranged alphabetically. Trying to solve a jamming problem (and probably also based on letters frequency and users’s feedback) is how the initial QWERTY layout was born. The success of the Remington No. 2 of 1878 made this very popular.

AZERTY (just like QWERTZ or QZERTY) is basically a QWERTY variation adapted for a given language (based on the assumption that it would be better to type a given language if certain letters that are very frequent on them appear on the home row).

Why haven’t France and Belgium reformed this redundancy by using the QWERTY keyboard instead of the AZERTY keyboard?

Why should they use QWERTY? Do note that it isn’t an optimal keyboard layout, either. Why aren’t you -I assume- using QWERTY and not DVORAK?

There are lots and lots of users that learnt to type in AZERTY. There would be an high cost of changing to a different layout. Plus, there are lots and lots of physical keyboards in those places showing an AZERTY layout.

There is a cost of switching to something else. In fact, a BEPO layout would be preferable from a theorical point of view. However, it would be costly for users to retrain themselves into a different layout. And with most computers in the country using AZERTY, that would put them in a disadvantage when using a different computer. This makes them to continue using AZERTY. Just like other countries continue using QWERTY.

Note: there was recently a keyboard layout standardization by French AFNOR (NF Z71‐300), but it kept the position of AZERTY letters, see https://norme-azerty.fr/ (there was an accompanying BEPO layout, too)

keyboard – Is it possible to apply Karabiner’s keybindings to Xquartz

I am using XQuartz in macOS. Is it possible to apply Karabiner’s keybindings into XQuartz? Basically, I just want XQuartz to see the default keybindings that macOS using.


Please note that I am using Emacs key bindings using Karabiner.

Key Bindings (control+keys)

control+bfnp    arrow keys
control+d   forward delete
control+h   delete
control+i   tab
control+(   escape
control+m   return
control+v   page down
control+a   (Microsoft Office)  home
control+e   (Microsoft Office)  end

Please note that this question could be related to How to disable Microsoft Outlook‘s keybindings in macOS.

command line – Keyboard prevents mouse from selecting text in terminal [Kubuntu, Xubuntu]

since a few days I am having this really strange issue that when I have my mouse and keyboard plugged in, I cannot select text in a terminal using my mouse. The cursor becomes invisible as soon as I do not move it, and it flickers when I do. When I click and drag to select text, it continuously flickers, probably repeatedly “resetting” the text selection.

If I unplug my keyboard, it works fine.
If I plug the keyboard in again, it still works fine.
As soon as I press any key(s) on the keyboard, it reverts to the same problem.

Reproducible under Xubuntu and Kubuntu, both with installed systems and live systems.

Note: This only happens in the terminal. I can select text and icons fine in any other program. In Win10 (this is a dual boot), it also works without any issue.

I tested with a different mouse – same problem. Unfortunately, I don’t have a second keyboard to try, but I am not sure this will solve the issue. It’s strange that this only affects Linux terminals.

This is what it looks like: https://www.youtube.com/watch?v=8InE5CiR5jo

I’d appreciate any help! Thanks!

How does Android interpret physical keyboard inputs?

I thought I had a grasp of how they work in a general sense, but I’ve been trying out several keyboards lately and have run into some inexplicable behavior. For example, pressing the ESC key on one keyboard will functionally trigger the back function in Android, but on another keyboard it does not. Same with mouse inputs’ right clicks, seeing incongruemt behavior. I know some keyboards have proprietary technologies that render special keys non-interoperable, but I thought the basic standard keys all trigger the same scan codes? Why is this not the case?

keyboard – Switching layouts with Caps Lock doesn’t work if Caps Lock was pressed right after another key

I’m on macOS Big Sur 11.2.1 and I’m experiencing a weird behavior of Caps Lock as the layout switcher.

Caps Lock can be used for switching layouts by turning the Use Caps Lock key to switch layout setting in Settings > Keyboard.

It’s working fine, except when Caps Lock is pressed right after another key, e.g. Backspace.

Is the issue reproducible for someone else? Is it the macOS issue or the issue of my setup? If it’s the macOS issue, could it be fixed somehow?

Thanks!