Xmonad: Pega todos os atalhos de teclado

6

Estou usando o Xmonad e tenho uma lista bastante longa de atalhos de teclado personalizados definidos na minha configuração.

Eu gostaria de adicionar algo como uma captura na parte inferior da configuração que bloqueia a minha tela se alguém pressionar uma combinação de teclas que não esteja definida, então qualquer Ctrl + * ou Alt + * que não está definido para fazer outra coisa apenas deve bloquear a tela.

Existe alguma boa maneira de fazer isso sem ter que listar todos os combos atualmente indefinidos?

    
por replay 18.04.2016 / 20:57

1 resposta

1

Is there any good way to do that without having to list all of the currently undefined combos?

Você deve entender que não é simplesmente "bloquear qualquer combinação desconhecida". Você provavelmente não quer bloquear coisas como Controle - R que permite reverter o histórico do seu shell, ou Controlar - P que abre o diálogo de impressão na sua suíte de escritório favorita.

Com isso dito, a maneira mais limpa de atingir seu objetivo é redefinir como os atalhos de teclado são procurados no XMonad para que qualquer "não encontrado" se transforme em "bloquear a tela". Infelizmente, o XMonad não oferece essas facilidades ao usuário; você terá que hackear o próprio XMonad.

A próxima melhor coisa que você pode fazer é gerar um mapa de todos os combos de chave válidos, removê-los daqueles que você já definiu e vincular todos os restantes ao comando "bloquear a tela". Felizmente, tudo isso pode ser automatizado.

Suponho que você tenha seu comando de bloqueio de tela definido assim:

lockScreen = spawn "i3lock"

As combinações de chaves consistem em uma máscara e uma chave, todas listadas em Graphics.X11.Types .

Primeiro, vamos definir uma lista de possíveis máscaras:

masks = [controlMask, mod1Mask]

Aqui eu assumi que você só quer bloquear combos começando com Control e Alt . Existem 8 máscaras, e elas podem ser combinadas, então essa linha pode ser muito mais complicada. No entanto, quanto mais máscaras definirmos aqui, mais cuidadosos devemos ter ao gerar ligações - não queremos bloquear acidentalmente algo importante!

Ok, a próxima parada é a lista de chaves. Eles também estão listados em Graphics.X11.Types e começam com xK_ . Eles têm o tipo KeySym , mas o que eles realmente são é Word64 . No entanto, aconselho a não enlouquecer e evitar escrever algo como [0 .. maxBound :: KeySym] - isso resultará em um mapa enorme que consumirá muita memória.

Então, basta procurar o número de chaves que você deseja cobrir e agrupá-las em pequenas definições. Aqui, por exemplo, eu cubro as chaves mais comuns:

keys :: [KeySym]
keys = [xK_Home     .. xK_Num_Lock] ++  -- Cursor control & motion
       [xK_KP_Space .. xK_R15] ++       -- Keypad and Function keys
       [xK_space    .. xK_asciitilde]   -- ASCII and such

Agora estamos prontos para definir uma lista de atalhos de teclado:

fallbackKeys = [((mask, key), lockScreen)
               | mask <- masks
               , key  <- keys ]

Isso gerará uma definição de keybind para todas as combinações possíveis de máscaras e chaves fornecidas.

Agora temos que aplicar essas definições à sua configuração.

XMonad.Util.EZConfig tem um % co_de muito útil % combinator que, dada uma configuração e uma lista de definições de ligação de chaves, adicionará o último ao primeiro, sobrescrevendo definições existentes se houver algum conflito. O que queremos é exatamente o oposto: queremos aplicar additionalKeys de tal forma que eles preencham apenas lugares indefinidos, deixando keybinds já definidas como elas são. Para conseguir isso, vamos definir outra função:

import qualified Data.Map as M

backupKeys :: XConfig a -> [((ButtonMask, KeySym), X ())] -> XConfig a
backupKeys conf keyList =
    conf { keys = \cnf -> M.union (keys conf cnf) (M.fromList keyList) }

Este é um copiar-colar direto de fallbackKeys , mas os argumentos para additionalKeys são trocados, resultando no comportamento que queremos. (Veja a documentação Data.Map.union para entender como isso funciona.)

E agora podemos finalmente usar tudo isso. Algum lugar no seu union você tem uma linha como esta:

main = xmonad $ def {…} 'additionalKeys' myKeys

Altere da seguinte forma:

main = xmonad $ def {…} 'additionalKeys' myKeys 'backupKeys' fallbackKeys

Recompile e reinicie o XMonad e aproveite suas novas configurações!

    
por 27.04.2016 / 16:03