如果尚未在特定工作区启动应用程序,则在该工作区启动应用程序

Start applications on specific workspace if not yet started there

简而言之:当我切换到工作区 X 时,我希望某些程序自动启动,但前提是它们尚未启动。

这与 XMonad startup on different workspaces 不同,因为我不想将 windows 移动到特定的工作区(比如总是将 xterm 移动到工作区 2)。
这对我也不起作用:xmonad spawn on startup in different workspace。我不希望所有应用程序在我登录时立即启动,这也不会自动启动,例如xterm 如果我关闭它并再次切换到工作区 2。


关于行不通的事情已经说完了,下面是行的是:
(差不多)

在我的工作区列表中,我保存了带有工作区名称的元组和切换到那里时要启动的列表程序:

myWorkspaces = [ ("VIM", ["gvim"]), ("TERM",[myTerminal ++ " -e tmux"]) ]

-- In my keybindings:
[ ((mod4Mask, key), loadWorkspace workspace cmd)
  | (key, (workspace, cmd)) <- zip [xK_1..] myWorkspaces
]

我定义了一个函数来切换到工作区并生成给定的程序:

loadWorkspace :: String -> [String] -> X()
loadWorkspace workspace commands =
    do windows $ W.greedyView workspace
       mapM_ spawn filtered_commands
           where filtered_commands :: X [String]
                 filtered_commands = filterM isNotOpen commands

                 isNotOpen :: String -> X Bool
                 isNotOpen command = return True

(由于某些原因 mapM_ 要求第二个参数是 String 而不是 [String]。我想要将 spawn 映射到 filtered_commands 中的字符串,知道为什么这不起作用吗?)

最后缺少的一块是isNotOpen函数,它应该在当前工作空间中搜索windows的className和return是否command 已经存在了。


我发现(与其他语言和技术相比)寻找 XMonad 做事的方式非常困难。对于这种情况,我只能找到如何在当前 WS - https://superuser.com/a/852152/481701 中获取 windows。好的,我想,这给了我一个 Window 对象,我可以查询它的一些属性。

但是没有。 Window 实际上是... Word64 的别名!!!好吧,我想。 Google xmonad 获取 window 属性。没有什么。 xmonad 从 window id 获取类名。没有什么。 xmonad window 信息。还有十几种其他表达类似内容的方式 - 没有有用的结果。我得到的只是 xmonad 主页、常见问题解答或 "Xmonad configuration tips".
我也在 hayoo! 中尝试了这些,我能得到的最接近的是 "fromClassName - Colorize a window depending on it's className."。哈哈

那么,如何在 ManageHook 之外获取 window 的类名(或任何其他属性)?

您可能喜欢 dynamic projects or topic spaces 作为预烘焙的替代品。它们并没有完全您建议的那样,但也许其中之一足够接近仍然有用,并且需要较少的配置工作。

I want to map spawn over the strings in filtered_commands, any idea why this doesn't work?

是的,您需要提升 mapM_ 来处理单子参数(与单子函数或 return 值相反)。因此:

filtered_commands >>= mapM_ spawn

或者,因为您已经在 do 区块中:

result_of_filtered_commands <- filtered_commands
mapM_ spawn result_of_filtered_commands

So, how can I get a window's className (or any other attributes) outside of ManageHook?

看看the source of className:

className = ask >>= (\w -> liftX $ withDisplay $ \d -> fmap resClass $ io $ getClassHint d w)

您可以只将 liftX 的参数作为 X 操作而不是 Query 操作。关键函数是 X11 包中的 getClassHint,它还提供对 windows.

的其他属性的访问

安装 wmctrl

sudo apt install wmctrl

并创建一个脚本(在本例中为第二个工作区 (-t 1) 上的雷鸟):

#!/bin/sh

 (thunderbird &)  & sleep 5 && 
sh -c "wmctrl -i -r `wmctrl -l | grep Thunderbird` -t 1"

要知道您在 wmctrl 上的应用程序名称,您可以通过在终端上轻按来查看它:

wmctrl -l

并将其替换为脚本中的正确名称。

注意大写字母("Thunderbird"不是"thunderbird")!!

3d 工作区上使用 firefox 的其他示例 (-t 2):

#!/bin/sh
(firefox &)  & sleep 5 && 
sh -c "wmctrl -i -r `wmctrl -l | grep Firefox` -t 2"

奖金:

这是启动时要执行的命令:

sh -c "thunderbird  & sleep 5 && wmctrl -i -r `wmctrl -l | grep Thunderbird` -t 1"

使用 Cinnamon 在 Debain 10 上工作。但应该适用于所有人