moses-palmer / pynput

Sends virtual input commands
GNU Lesser General Public License v3.0
1.79k stars 248 forks source link

Unable to use media keys on Kubuntu 20.04 #313

Open varishtsg opened 4 years ago

varishtsg commented 4 years ago

While trying to simulate media keys like, volume up / down or play / pause, it simply crashes and gives me this error.

keyboard.press(Key.media_play_pause) Traceback (most recent call last): File "", line 1, in File "/home/senpai/.virtualenvs/SunteHo/lib/python3.8/site-packages/pynput/keyboard/_base.py", line 392, in press self._handle(resolved, True) File "/home/senpai/.virtualenvs/SunteHo/lib/python3.8/site-packages/pynput/keyboard/_xorg.py", line 243, in _handle Xlib.ext.xtest.fake_input( File "/usr/lib/python3.8/contextlib.py", line 120, in exit next(self.gen) File "/home/senpai/.virtualenvs/SunteHo/lib/python3.8/site-packages/pynput/_util/xorg.py", line 78, in display_manager raise X11Error(errors) pynput._util.xorg.X11Error: [(BadValue(<Xlib.display._BaseDisplay object at 0x7fd21822c550>, b'\x00\x02#\x00\x00\x00\x00\x00\x02\x00\x84\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'), None)]

I am running Kubuntu 20.04. I am using a laptop with Nvidia GPU if that helps.

SuperMechaDeathChrist commented 4 years ago

I'm experiencing the same error. I'm trying to run a server controlling the mouse and keyboard of a Raspberry Pi 4. The OS is Raspberry OS 10 (buster). I also have a keyboard with multimedia buttons. It doesn't detect play/next/previous in that keyboard, but it does detect volume up/down/mute, so at least it should be possible to emulate volume control keys.

MatthiasLohr commented 3 years ago

Any solution for this so far? Struggling with the same issue... None if the media keys are working, I'm getting the same error as described above.

SuperMechaDeathChrist commented 3 years ago

I found a workaround. At least for the volume control keys, anyways. Media play_pause/previous/next still don't work. But that's probably because they also don't wok for my physical keyboard. If there's anyone with linux and multimedia keys working in a physical keyboard, please try this method and report if you can get them to work using pynput.

First, I ran this key logger:

from pynput.keyboard import Listener

def log_keystroke(key):
    key = str(key).replace("'", "")

    if key == 'Key.space':
        key = ' '
    if key == 'Key.shift_r':
        key = ''
    if key == "Key.enter":
        key = '\n'
    print(key,[key])

with Listener(on_press=log_keystroke) as l: l.join()

and saw what was being printed for the keys that did work for the physical keyboard I had. This is what I got for the media and volume keys as a dict:

myKey = {
    'media_play_pause':269025044,
    'media_volume_mute':269025042,
    'media_volume_down':269025041,
    'media_volume_up':269025043,
    'media_previous':269025046,
    'media_next':269025047,
    }

So, when I want to increase the volume on my Raspberry Pi 4, I just do this:

from pynput.keyboard import Key, KeyCode, Controller as KeyboardController
keyboard = KeyboardController()

myKey = {
    'media_volume_mute':269025042,
    'media_volume_down':269025041,
    'media_volume_up':269025043
}

# Do this.
nk=KeyCode(myKey['media_volume_up'])
keyboard.press(nk)
keyboard.release(nk)

# Instead of this, which causes the BadValue error already mentioned.
# keyboard.press(Key.media_volume_up)
# keyboard.release(Key.media_volume_up)

I'm not sure if those numeric key codes depend on the operating system or something else. Try this method and report your key codes. It might help somebody.

moses-palmer commented 3 years ago

Thank you for your investigation!

It appears that the keycodes for media keys may need revisiting.

Saruspete commented 3 years ago

Hello,

i'm having the same issue on my Gentoo. In my case, the Media buttons are defined in Xlib/keysymdef/xf86.py, but as XF86_Audio (there' an underscore).

So I'm loading the xf86 before loading Pynput (Xlib.XK.load_keysym_group('xf86') ), then load the modified version of KeyCode._from_media (with XF86_Audio instead of XF86Audio).

In [1]: import Xlib.XK                                                                                                                      

In [2]: Xlib.XK.load_keysym_group('xf86')                                                                                                   

In [3]: from pynput.keyboard import Controller, Key, KeyCode                                                                                
Xlib.xauth: warning, no xauthority details available

In [4]: Key.media_play_pause                                                                                                                
Out[4]: <Key.media_play_pause: <269025044>>
Saruspete commented 3 years ago

Hello,

Can anyone check if this simple fix (adding an underscore) is working for you too, so we can implement it ? @moses-palmer @MatthiasLohr @SuperMechaDeathChrist

(edit: fixed previous comment, missing the load_keysym_group() call )

thanks

moses-palmer commented 3 years ago

I have pushed the suggested changes to fixup-xorg-media-keys.

This updated version does not crash for me, but then again, neither did the previous one. I would appreciate feedback on whether it fixes the problem for you, @varishtsg , @SuperMechaDeathChrist, @MatthiasLohr and @Saruspete.

Saruspete commented 3 years ago

Works for me.

Had to struggle to work against the version on the system, but once fixed, that was good.

You can test this on/off with a sed like

# Comment load line, volume keys shouldn't work:
sed -Ee "/^#?Xlib.XK.load_keysym_group/s/^#?/#/" -i lib/python3*/site-packages/pynput/keyboard/_xorg.py
# Uncomment, should work again
sed -Ee "/^#?Xlib.XK.load_keysym_group/s/^#?//" -i lib/python3*/site-packages/pynput/keyboard/_xorg.py
Saruspete commented 3 years ago

Hello OP & commenters @varishtsg @SuperMechaDeathChrist @MatthiasLohr

Can you please test the branch with fixes done by @moses-palmer so they can merge it ?

Thanks

MatthiasLohr commented 3 years ago

Sorry for my late reply. I'l try as soon as I can. What I can confirm for now: Just using the keycode numbers presented by @SuperMechaDeathChrist, it works for me. But I didn't take a look at the exact other changes, so I can't give a statement for that right now.

Saruspete commented 3 years ago

Hello & Happy new year,

No news from anybody else here, despite the work done by @moses-palmer ... Let's get this fork merged

Cheers,

BETLOG commented 1 year ago

Kubuntu 22.04 and this seems to have resurfaced somewhere prior to about 2023-05-01(+10UTC) 108 keyboard (only has volume buttons), and the following have stopped working: mute, volume up, volume down

System sounds (and probably everything else) are suddenly 100% volume despite whatever i try to set in pavucontrol-qt

xev

KeyRelease event, serial 40, synthetic NO, window 0x6e00001, root 0x1e3, subw 0x0, time 3429709, (271,227), root:(1142,725), state 0x10, keycode 121 (keysym 0x1008ff12, XF86AudioMute), same_screen YES, XLookupString gives 0 bytes: XFilterEvent returns: False

KeyRelease event, serial 40, synthetic NO, window 0x6e00001, root 0x1e3, subw 0x0, time 3430175, (271,227), root:(1142,725), state 0x10, keycode 122 (keysym 0x1008ff11, XF86AudioLowerVolume), same_screen YES, XLookupString gives 0 bytes: XFilterEvent returns: False

KeyRelease event, serial 40, synthetic NO, window 0x6e00001, root 0x1e3, subw 0x0, time 3430639, (271,227), root:(1142,725), state 0x10, keycode 123 (keysym 0x1008ff13, XF86AudioRaiseVolume), same_screen YES, XLookupString gives 0 bytes: XFilterEvent returns: False

sudo showkey -k

keycode 28 release keycode 113 press keycode 113 release keycode 114 press keycode 114 release keycode 115 press keycode 115 release