You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何让XMonad正确使用基于Haskell的Xmobar?

配置XMonad启动Haskell编写的xmobar

简短总结

如何修改以下xmonad.hs配置:

import XMonad
main :: IO ()
main = xmonad def { terminal = "urxvt" , modMask = mod4Mask }

让XMonad能够正确启动xmobar(仅启动一次,重启XMonad时自动终止并重新启动),且不使用xmobarrc配置文件,而是使用包含以下内容的Haskell文件xmobar.hs:

import Xmobar
main :: IO ()
main = xmobar defaultConfig { commands = [Run XMonadLog], template = "%XMonadLog%" }

详细说明

从XMonad教程中了解到:

也可以像配置XMonad一样,完全用Haskell配置xmobar。如需了解更多信息,可查看官方文档中的xmobar.hs示例。更复杂的示例可查看jao的xmobar.hs(他是xmobar的现任维护者)。

官方示例文件说明如下:

-- An example of a Haskell-based xmobar. Compile it with
--   ghc --make -- xmobar.hs
-- with the xmobar library installed or simply call:
--   xmobar /path/to/xmobar.hs
-- and xmobar will compile and launch it for you and

验证发现,执行ghc --make xmobar.hs(GHC 9.4.8)会生成一个xmobar可执行文件,运行该文件即可启动状态栏;而xmobar /path/to/xmobar.hs则不会返回。

但不清楚如何正确配置XMonad以启动xmobar。官方文档提到:

或者将你的xmobar.hs程序放在~/.config/xmobar/xmobar.hs,运行系统级xmobar时,它会检测到你的自定义实现,并按需重新编译和运行。

但仍不清楚如何让XMobar执行"运行系统级xmobar"这一步骤。

更多发现

已得到一个最小可运行示例,但仍有不少细节不理解。

给定~/.config/xmonad/xmonad.hs:

import XMonad
import XMonad.Hooks.EwmhDesktops
import XMonad.Hooks.StatusBar.PP
import XMonad.Util.Run

main :: IO ()
main = do
     xmproc <- spawnPipe "xmobar ~/.config/xmonad/xmobar.hs"
     xmonad . ewmhFullscreen
            . ewmh
            $ myConfig xmproc

myConfig h = def
    { terminal = "urxvt"
    , modMask = mod4Mask
    , logHook = dynamicLogWithPP xmobarPP
    { ppOutput = hPutStrLn h
    }
    }

以及~/.config/xmonad/xmobar.hs:

import Xmobar

config :: Config
config = defaultConfig
    {
      commands =
        [ Run StdinReader,
          Run $ Date "%a %_d %b %Y <fc=#ee9a00>%H:%M:%S</fc>" "date" 10
        ],
      template = "%StdinReader% }{ %date%",
      alignSep = "}{"
    }

main :: IO ()
main = xmobar config

两者配合运行正常,但仍有以下疑问:

  • 教程中提到:

    因此,最好切换到基于属性的日志记录方式,将内容写入X11属性,再由xmobar读取;这样就不会出现内容未被读取的问题!
    最重要的是,教程得出结论:
    因此,我们必须在xmobar中使用XMonadLog而非StdinReader。
    但当前示例的xmobar.hs用的是StdinReader;若直接替换为XMonadLog(未做其他修改),会出现两个问题:

    • 当前工作区无法正确显示;
    • 按Super+q重启XMonad时,会新生成一个xmobar进程,旧进程未被终止(每按一次,pidof xmobar就会多一个进程ID)。
  • 原本对xmonad.hs中的代码有疑问:
    xmproc <- spawnPipe "xmobar ~/.config/xmonad/xmobar.hs"
    
    既然将XMobar作为库使用,为何要运行xmobar可执行文件并传入xmobar.hs路径,而非直接启动编译好的可执行文件?
    回顾官方示例后认为这一做法合理:
    -- An example of a Haskell-based xmobar. Compile it with
    --   ghc --make -- xmobar.hs
    -- with the xmobar library installed or simply call:
    --   xmobar /path/to/xmobar.hs
    -- and xmobar will compile and launch it for you and
    
  • 状态栏未为窗口设置偏移,导致窗口部分覆盖状态栏:
    窗口覆盖状态栏截图
    一直未能找到解决方法,而使用xmobarrc配置时不会出现此问题。

内容的提问来源于stack exchange,提问作者Enlico

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.02 10:35:01