Ma vie rêvée

Aller au contenu | Aller au menu | Aller à la recherche

mardi 5 décembre 2017

Souris EssentielB ergo XL sous GNU/linux

Ma Logitech Performance MX commençait a fatiguer après seulement 3 ans de service (hors garantie bien sur), clics manquants, clics doubles intempestifs, etc. Je suis partie chercher une remplaçante.

[C'est a priori un problème de conception du pressoir qui fini par se tordre.  Ce qui a tendance a m'agacer sur un matériel de cette gamme de prix.]

Ne jouant plus beaucoup, j'ai laissé de côté les souris gamers et mon choix s'est porté sur la souris sans-fil EssentielB ergo XL vu qu'elle a plein de boutons, est de taille respectable (j'ai des grandes mains) et n'est pas trop chère (~30€).

Evidemment, aucune info sur le support sous GNU/linux mais bon c'est une souris usb, ça devrait aller, hein ?

 

Ben en fait oui, ça va. Branchement sans difficulté, reconnaissance sans problème par le système, clic droit, gauche, milieu, molette, précédent, suivant, tout ça fonctionne sans difficulté.

Reste les 3 derniers boutons : un à gauche du clic gauche, et 2 sous le pouce en dessous des précédent/suivant.

Pas de soucis, on sort xev pour récupérer la valeur du bouton et là, c'est le drame (en fait non mais c'est pour l'effet) :

keycode 180 (keysym 0x1008ffa9, XF86HomePage)

En fait, les 3 boutons ne sont pas détectés comme boutons de souris mais comme des touches de clavier. Ce qu'on confirme avec xinput :

[jules@tue-amour ~]$ xinput list
⎡ Virtual core pointer                        id=2    [master pointer  (3)]
⎜   ↳ Virtual core XTEST pointer                  id=4    [slave  pointer  (2)]
⎜   ↳ Compx 2.4G Receiver                         id=9    [slave  pointer  (2)]
⎣ Virtual core keyboard                       id=3    [master keyboard (2)]
    ↳ Virtual core XTEST keyboard                 id=5    [slave  keyboard (3)]
    ↳ Power Button                                id=6    [slave  keyboard (3)]
    ↳ Power Button                                id=7    [slave  keyboard (3)]
    ↳ AT Translated Set 2 keyboard                id=10    [slave  keyboard (3)]
    ↳ Compx 2.4G Receiver                         id=8    [slave  keyboard (3)]
    ↳ Compx 2.4G Receiver                         id=11    [slave  keyboard (3)]

Ici, Compx 2.4G Receiver est la souris, on voit bien qu'elle déclare une souris et 2 claviers (un seul est utilisé en fait).

Pour rappel (et en résumé), le matériel émet un signal pour chaque événement (ex : je clic un bouton), c'est le scancode, celui-ci est traduit par le noyau en un code numérique, le keycode (cf /usr/include/linux/input-event-codes.h ) qui contrairement au premier ne dépend plus du matériel. Le serveur X va ensuite traduire ce keycode en une instruction utilisable par les applications le keysym (cf par ex /usr/xhare/X11/xkb/symbols/inet). Enfin, chaque keysym sera consommé par les applications pour réaliser une action (afficher une lettre, valider une boite, lancer un menu, etc.)

Nos trois boutons ont donc pour keysyms XF86HomePage, XF86AudioRaiseVolume et XF86AudioLowerVolume, ce qui me pose un soucis étant donné que j'ai un clavier multimédia utilisant déjà ces touches là d'une part, et que j'aime bien paramétrer mes boutons de souris de façon précise d'autre part.

Après avoir cherché quelques heures sur le grand nain ternet mondial quelle était la meilleure solution, j'en suis arrivé à la conclusion qu'il me fallait modifier les keycodes émis par le noyau.

L'utilitaire setkeycodes que j'utilise pour mon clavier branché en PS/2 ne marche pas avec l'usb. Il faut directement aller expliquer à udev qu'il doit changer ça. La procédure n'est pas très compliquée :

  • trouver le scancode, ça se fait avec l'utilitaire evtest (paquet python-evdev sous mageia 6), on lance, on clique et on regarde ce qui s'affiche. Il s'agit de la valeur MSC_SCAN. Chez moi, il s'agissait de 786979, 786665 et 786666 respectivement.
  • Créer un fichier .hwdb dans /etc/udev/hwdb.d/ avec les instructions qui vont bien :
    $less /etc/udev/hwdb.d/99-keyboard.hwdb
    evdev:input:b0003v25A7pFA61*
     KEYBOARD_KEY_C00E9=f23
     KEYBOARD_KEY_C00EA=f22
     KEYBOARD_KEY_C0223=f21
    
    La première ligne désigne la souris, b0003 c'est l'usb, v25A7pFA61 le vendor id et product id qu'on obtient via lsusb. Les trois lignes suivantes correspondent aux réattributions des touches, KEYBOARD_KEY_XXXXX est la touche actuelle avec la valeur précédente convertie en hexadécimal et la partie de droite après le signe égal est le nouveau keycode que l'on veut, ici les touches F21 à F23 dont je n'ai pas l'usage.
  • Une fois le fichier correctement fait, on lance systemd-hwdb update pour mettre à jour la base de donnée suivit de udevadm trigger pour la prendre en compte. Plus qu'à vérifier avec xev. Si ça ne marche pas, augmentez le niveau de log de udevadm (man udevadm option control) et regarder dans le journal (journactl -f).

 

Quand on regarde maintenant, les keycodes sont donc différents et de nouveaux keysyms ont été attribués, dans mon cas XF86TouchpadToggle, XF86TouchpadOn, XF86TouchpadOff. Je suis satisfait, n'ayant pas de touchpad sur cette machine.

Maintenant, plus qu'à modifier mon fichier .xbindkeysrc pour prendre en compte ces nouvelles touches et leur attribuer l'action que je veux. Par exemple, pour la touche en bas du pouce, j'aime bien l'utiliser pour recharger un onglet (ctrl+R) :

"xvkbd -xsendevent -text "\Cr""
 m:0x10 + c:200
#Mod2 + XF86TouchpadOn

xbindkeys peut utiliser directement le keycode (ligne 2) ou le keysym (ligne 3), pour avoir la syntaxe, xbindkeys --key est bien pratique. La première ligne est la commande éxécutée lorsque le bouton/touche est pressé, ici, xvkbd qui envoie le signal ctrl+R.

Il est possible de faire plein d'autres choses (cf xdotool ou xte), y compris générer le clic d'un bouton de souris depuis une touche de clavier qui est en fait un bouton de souris reconnue comme un clavier. :D