Les grands IDE JetBrains (IDEA et al.) attribuent à peu près tous les raccourcis clavier imaginables à une fonction. Bien que parfois légèrement écrasant, cela permet également une utilisation efficace.
Mon problème est que Unity attribue également certains de ces raccourcis, et ils ont priorité. Un exemple particulièrement ennuyeux est CTRL + ALT + L . Le problème a déjà été exploré ici.
Cependant, aucune des approches n'est satisfaisante.
- Désactivation des raccourcis système globalement entrave ma productivité globale avec le système.
- Passer à un mappage de clavier différent dans IDEA me confondra énormément lorsque je développerai sur différentes plates-formes (et que je devrai choisir des mappages différents).
Existe-t-il un moyen de désactiver les raccourcis système uniquement lorsqu'une certaine application est active, c'est-à-dire en cours d'exécution et active ?
Je serais prêt à exécuter un script chaque fois que je lance l'application.
Réponse acceptée :
Comment désactiver automatiquement plusieurs raccourcis (spécifiques) si (et tant que) la fenêtre d'une application spécifique est active
Le script ci-dessous désactivera des raccourcis clavier spécifiques lorsqu'une fenêtre d'application arbitraire est active.
Bien que vous ayez mentionné""Je serais prêt à exécuter un script chaque fois que je lance l'application." , Il n'y a aucune raison de tuer le script par la suite, il manque extrêmement de jus.
Le scénario
#!/usr/bin/env python3
import subprocess
import time
import os
app = "gedit"
f = os.path.join(os.environ["HOME"], "keylist")
def run(cmd):
subprocess.Popen(cmd)
def get(cmd):
try:
return subprocess.check_output(cmd).decode("utf-8").strip()
except:
pass
def getactive():
return get(["xdotool", "getactivewindow"])
def setkeys(val):
# --- add the keys to be disabled below
keys = [
["org.gnome.settings-daemon.plugins.media-keys", "logout"],
["org.gnome.settings-daemon.plugins.media-keys", "screensaver"],
]
# ---
writelist = []
if not val:
try:
values = open(f).read().splitlines()
except FileNotFoundError:
values = []
for i, key in enumerate(keys):
try:
cmd = ["gsettings", "set"]+key+[values[i]]
except IndexError:
cmd = ["gsettings", "reset"]+key
run(cmd)
else:
for key in keys:
cmd = ["gsettings", "set"]+key+["['']"]
read = get(["gsettings", "get"]+key)
writelist.append(read)
run(cmd)
if writelist:
open(f, "wt").write("n".join(writelist))
front1 = None
while True:
time.sleep(1)
pid = get(["pgrep", app])
if pid:
try:
active = get(["xdotool", "getactivewindow"])
relevant = get(["xdotool", "search", "--all", "--pid", pid]).splitlines()
front2 = active in relevant
except AttributeError:
front2 = front1
else:
front2 = False
if front2 != front1:
if front2:
setkeys(True)
else:
setkeys(False)
front1 = front2
Comment utiliser
-
Le script a besoin de
xdotool
:sudo apt-get install xdotool
-
Copiez le script dans un fichier vide, enregistrez-le sous
disable_shortcuts.py
-
Dans l'en-tête du script, remplacez dans la ligne :
app = "gedit"
"gedit" par votre application, c'est-à-dire :le nom du processus propriétaire de la fenêtre.
-
Testez le script avec la commande :
python3 /path/to/disable_shortcuts.py
-
Si tout fonctionne correctement, ajoutez-le aux applications de démarrage :Dash> Startup Applications> Add. Ajoutez la commande :
/bin/bash -c "sleep 15 && python3 /path/to/disable_shortcuts.py"
Ajout de raccourcis supplémentaires à désactiver
À titre d'exemple, j'ai ajouté le raccourci que vous avez mentionné :CTRL + ALT + L . Les raccourcis sont définis dans le dconf
base de données, et peut être défini ou désactivé à l'aide de gsettings
.
Dans le script, ces gsettings
les entrées sont définies dans la fonction :setkeys()
def setkeys(val):
# --- add the keys to be disabled below
keys = [
["org.gnome.settings-daemon.plugins.media-keys", "screensaver"]
]
# ---
Un exemple pour ajouter (désactiver) le raccourci de déconnexion :
- Ouvrez une fenêtre de terminal, exécutez la commande
dconf watch /
- Ouvrez les paramètres système > "Clavier" > "Raccourcis" > "Système"
-
Réinitialisez le raccourci sur lui-même. Dans le terminal, vous pouvez voir les
gsettings
clé qui appartient au raccourci : -
Nous devons maintenant ajouter la clé trouvée (sous une apparence légèrement différente) :
["org.gnome.settings-daemon.plugins.media-keys", "logout"]
…à la liste des "clés" dans notre fonction :
def setkeys(val): # --- add the keys to be disabled below keys = [ ["org.gnome.settings-daemon.plugins.media-keys", "screensaver"], ["org.gnome.settings-daemon.plugins.media-keys", "logout"], ]
Maintenant, CTRL + ALT + L et CTRL + ALT + Supprimer sont désactivés si votre application est devant.
En relation:Relation entre la disposition du clavier et xmodmap ?Explication
Comme mentionné, les raccourcis, comme ceux que vous mentionnez, sont définis dans le dconf
base de données. Dans l'exemple CTRL + ALT + L , la clé pour définir ou modifier le raccourci est :
org.gnome.settings-daemon.plugins.media-keys screensaver
Pour désactiver la clé, la commande est :
gsettings set org.gnome.settings-daemon.plugins.media-keys screensaver ""
Pour réinitialiser la clé à sa valeur par défaut :
gsettings reset org.gnome.settings-daemon.plugins.media-keys screensaver
Le script regarde une fois par seconde si :
- votre application fonctionne du tout
- si c'est le cas, il regarde si l'une de ses fenêtres est active
-
encore une fois (seulement) si c'est le cas, il désactive les raccourcis, répertoriés dans
# --- add the keys to be disabled below keys = [ ["org.gnome.settings-daemon.plugins.media-keys", "screensaver"], ["org.gnome.settings-daemon.plugins.media-keys", "logout"], ]
… en attendant le prochain changement d'état.
Si la fenêtre active ne fait plus partie de votre application, les touches, mentionnées dans la liste, sont réinitialisées par défaut.
Remarque
Comme mentionné précédemment, la charge supplémentaire pour le processeur du script est nulle. Vous pouvez très bien l'exécuter au démarrage, comme expliqué dans "Comment utiliser".
Affecter plusieurs applications
Comme indiqué dans les commentaires, dans le cas spécifique d'OP, il est utile d'appliquer des raccourcis de désactivation sur un groupe d'applications, résidant toutes dans un seul répertoire.
Ci-dessous une version à appliquer sur toutes les applications dont la sortie de
pgrep -f
comprendra un répertoire spécifique. Dans mon exemple, j'ai défini le /opt
répertoire, donc si la fenêtre active est l'une des applications dans /opt
, les raccourcis définis seront désactivés.
amener une fenêtre de l'une des applications dans /opt au premier plan désactivera le raccourci de déconnexion
réactiver le raccourci si une autre fenêtre obtient le focus
Le scénario
#!/usr/bin/env python3
import subprocess
import time
import os
appdir = "/opt"
f = os.path.join(os.environ["HOME"], "keylist")
def run(cmd):
subprocess.call(cmd)
def get(cmd):
try:
return subprocess.check_output(cmd).decode("utf-8").strip()
except:
pass
def getactive():
return get(["xdotool", "getactivewindow"])
def setkeys(val):
# --- add the keys to be disabled below
keys = [
["org.gnome.settings-daemon.plugins.media-keys", "logout"],
["org.gnome.settings-daemon.plugins.media-keys", "screensaver"],
["org.gnome.desktop.wm.keybindings", "begin-move"],
]
# ---
writelist = []
if not val:
try:
values = open(f).read().splitlines()
except FileNotFoundError:
values = []
# for key in keys:
for i, key in enumerate(keys):
try:
cmd = ["gsettings", "set"]+key+[values[i]]
except IndexError:
cmd = ["gsettings", "reset"]+key
run(cmd)
else:
for key in keys:
cmd = ["gsettings", "set"]+key+["['']"]
read = get(["gsettings", "get"]+key)
writelist.append(read)
run(cmd)
if writelist:
open(f, "wt").write("n".join(writelist))
front1 = None
while True:
time.sleep(1)
# check if any of the apps runs at all
checkpids = get(["pgrep", "-f", appdir])
# if so:
if checkpids:
checkpids = checkpids.splitlines()
active = getactive()
# get pid frontmost (doesn't work on pid 0)
match = [l for l in get(["xprop", "-id", active]).splitlines()
if "_NET_WM_PID(CARDINAL)" in l]
if match:
# check if pid is of any of the relevant apps
pid = match[0].split("=")[1].strip()
front2 = True if pid in checkpids else False
else:
front2 = False
else:
front2 = False
if front2 != front1:
if front2:
setkeys(True)
else:
setkeys(False)
front1 = front2
Comment utiliser
-
Comme le premier script,
xdotool
doit être installé :sudo apt-get install xdotool
-
Copiez le script dans un fichier vide, enregistrez-le sous
disable_shortcuts.py
-
Dans l'en-tête du script, remplacez dans la ligne :
appdir = "/opt"
"/opt" par le répertoire où se trouvent vos applications.
-
Testez le script avec la commande :
python3 /path/to/disable_shortcuts.py
-
Si tout fonctionne correctement, ajoutez-le aux applications de démarrage :Dash> Startup Applications> Add. Ajoutez la commande :
/bin/bash -c "sleep 15 && python3 /path/to/disable_shortcuts.py"
L'ajout d'autres raccourcis à la liste fonctionne exactement de la même manière que la version 1 du script.
Connexes :Impossible de mettre à niveau le micrologiciel Logitech unify à l'aide de fwupd ?Cela fonctionne-t-il sur toutes les applications ?
Dans votre réponse, vous mentionnez :
xprop ne révèle pas les PID pour toutes les fenêtres. Exemple d'échec :chronomètre.
Les fenêtres avec pid 0 (comme les fenêtres tkinter, y compris Idle), n'ont pas d'id de fenêtre dans la sortie de xprop -id
. Idle
n'a pas de raccourcis conflictuels selon mon expérience. Si vous rencontrez une application avec le pid 0 qui nécessiterait la désactivation de raccourcis spécifiques, veuillez le mentionner.
Dans ce cas, une échappatoire possible serait de convertir la sortie de
xdotool getactivewindow
en hexadécimal, le format wmctrl
utilise, puis rechercher le pid
correspondant dans la sortie de
wmctrl -lp
Bien que cela semblait la chose la plus évidente à faire pour commencer, je ne l'ai pas utilisé dans le script pour garder le script aussi léger que possible.