Como posso alterar o comportamento das teclas de atalho no xmonad se o programa está sendo executado?

12

Estou usando alguns mapeamentos principais no meu xmonad.hsarquivo de configuração:

...
    , modMask = mod4Mask     -- Rebind Mod to the Windows key
...
 [ ((controlMask, xK_Print), spawn "sleep 0.2; scrot -s")
 , ((0, xK_Print), spawn "scrot")
 , ((controlMask, xK_f), spawn "firefox")
 ]

O terceiro mapeamento é executado firefoxao pressionar ctrl+f. Eu gostaria de fazer algo mais complexo:

if (firefox is running):
  focus and maximize firefox window:
else:
  run firefox

E eu gostaria de mudar ctrl+fpara win+f. Como eu posso fazer isso?

xralf
fonte
A colocação cruzada como esta (aqui e no stackoverflow) é realmente um negócio comum?
ДМИТРИЙ МАЛИКОВ 11/11
Não: é desencorajado ativamente ...
jasonwryan
Está fora de tópico no SO, por isso pedi que se livrassem da cópia deles.
Michael Mrozek
@ dmitry.malikov Este parece ser o melhor lugar para a pergunta.
xralf
Melhor ainda; xralf excluiu a cópia do SO. Muito obrigado
Michael Mrozek

Respostas:

8

Olhando para os pacotes contrib do XMonad , você encontrará XMonad.Actions.WindowGo, que exporta a seguinte função :

runOrRaiseMaster :: String -> Query Bool -> X ()

que utiliza um argumento de string do programa para executar , por exemplo, "firefox"; e uma consulta booleana que é usada para descobrir se já está sendo executada , através das propriedades do X11, por exemplo (className =? "Firefox")(consulte o topo da XMonad.Actions.WindowGopágina para variantes).

Portanto, tudo que você precisa é vincular runOrRaiseMaster "firefox" (className =? "Firefox")à chave desejada, conforme explicado emXMonad.Doc.Extending , via

((modMask, xK_f ), runOrRaiseMaster "firefox" (className =? "Firefox"))

como parte das combinações Data.Mapde teclas da sua configuração (os detalhes diferem com a maneira como você define as configurações, ou seja, com toda a sua configuração xmonad.hs, consulte Adicionando combinações de teclas ).

Observe que não há sentido real em maximizar uma janela no XMonad. Ao configurar as coisas conforme explicado, você terá Mod4+ a fseguinte ação:

  • se houver uma janela com um nome de classe correspondente ao "Firefox", ela será focada e definida como master , ou seja, dependendo do layout recente , será a grande janela
  • se nenhuma janela corresponder, o Firefox será gerado e definido como master .

A maximização pode ser emulada escolhendo o Fulllayout após a chamada runOrRaiseMaster, conforme descrito aqui :

("M-<F1>", sendMessage $ JumpToLayout "Full")

(observe que este exemplo também demonstra XMonad.Util.EZConfigpermitir definições mais fáceis de vinculação de teclas)

Combinar essas duas coisas também é possível. Ambos são do tipo X (), ou seja, estão na X Mônada . Usando >>, que é do tipo (verifique com :t (>>)em ghci)

(>>) :: Monad m => m a -> m b -> m b

também temos (runOrRaiseMaster "firefox" (className =? "Firefox")) >> (sendMessage $ JumpToLayout "Full")uma combinação de dois X ()tipos de tipos X ()e, portanto, pode ser vinculado a uma chave.

EDIT ausente )na linha de código com>>

Editar2 modm -> modMask.

Edit3 Esta xmonad.hsespero funciona.

( Por que não aprender um Haskell para o bem? )

sr_
fonte
Obrigado por trabalhar a resposta e outras informações e o tutorial Haskell. Eu gosto da sintaxe Haskell e do paradigma funcional. A única coisa que não funciona é a parte em que >> (sendMessage $ JumptoLayout "Full")há algum erro com o construtor. Talvez seja algo fácil, que eu resolva depois de aprender Haskell.
xralf
Esqueci: ainda modmassim não funciona, ainda estou usando controlMask.
xralf
@xralf, (1) faltava um suporte - funciona agora? (2) eu precisaria do seu todo xmonad.hspara consertar isso; melhor, basta dar uma olhada por aqui, no arquivo de configuração e ver como os outros o fazem ou usam o mencionado EZConfig.
sr_
O suporte não ajudou. Aqui está o arquivo xmonad.hs que estou usando.
xralf
(1) Os colchetes ainda estão incorretos, a ação do tipo X ()para vincular à chave deve ser (runOrRaiseMaster ...) >> (sendMessage ...), resultando em ,((...,...), (runOrR...) >> (send...) ) (a (antes run...)
sr_