xmonad

出自 Arch Linux 中文维基

xmonad 是 X 下的一個平鋪 窗口管理器。窗口會自動排列、無間隙或重疊地平鋪在屏幕上,從而最大限度地利用屏幕。窗口管理器功能可通過鍵盤訪問:鼠標操作是可選的。

Xmonad 使用 Haskell 語言 編寫、配置並擴展功能的。用户可以將自定義佈局算法、按鍵綁定和其他擴展功能寫在配置文件中。

佈局是動態應用的,並且在每個工作空間上可以使用不同的佈局。 Xmonad 完全支持 Xinerama,後者可允許將窗口平鋪在多個物理屏幕上。

安裝[編輯 | 編輯原始碼]

安裝 xmonad 軟件包,其提供了最基本的配置,最好還安裝上 xmonad-contrib,可獲得更有用的桌面配置以及其他平鋪算法、配置和腳本等。

此外,可安裝開發版本的 xmonad-gitAUR, 其還附帶了些額外的依賴;以及同時安裝 xmonad-contrib-gitAUR

注意: 記得在升級 xmonad 後運行 xmonad --recompile 命令,否則下次啟動尋找共享庫時可能會遇到問題。

如何啟動[編輯 | 編輯原始碼]

xinit 運行 xmonad.

或者,你也可以在 display manager(SDDM) 的會話菜單中選擇 XMonad

請確保在啟動 XMonad 之前你已經安裝了至少一個默認終端模擬器 Xterm,當然你也可以在這之前修改 XMonad 的配置文件 ~/.xmonad/xmonad.hs 來指定一個默認的終端,這很重要,否則你將無法在新的窗口管理器下進行任何工作。

注意: 默認情況下,XMonad 之顯示一個十字光標, 可以根據這個文章內容來更改默認顯示, see Cursor themes#Change X shaped default cursor.

配置文件[編輯 | 編輯原始碼]

創建一個配置目錄 ~/.xmonad 和 配置文件 .xmonad/xmonad.hs ,然後根據下面的指導編寫基礎的配置項。

在更改配置文件 ~/.xmonad/xmonad.hs 後,使用 Mod+q 快捷鍵來重新啟動 XMonad,使更改生效。

提示:默認的XMonad 的配置在沒有 xmonad.hs 配置文件的情況下也是十分友好的

因為 xmonad 的配置文件使用的是 Haskell 語言編寫,一般人需要自定義定製一個自己的配置文件可能是困難且耗費時間的,以下網站資源是一些關於 xmonad 的詳細配置示例參考:

把更改和自定義內容寫入 ~/.xmonad/xmonad.hs ,XMonad 將會從你的 def函數中讀取相關參數的設定,

一個編寫的 xmonad.hs 示例如下:

import XMonad

main = xmonad def
    { terminal    = "urxvt"  --默认终端
    , modMask     = mod4Mask --快捷前置键, 4是win键,1是alt也是默认的
    , borderWidth = 3        --边框宽度
    }

這裏只更改了默認終端,快捷前置鍵和窗口邊框的寬度,其他的設置還是 XMonad 的默認值 (默認值從 Xconfig繼承)。

當配置越來越複雜的時候,可以把參數以賦值的形式傳遞給 def 函數中的變量,用更容易識別的變量名可以優化配置文件的格式佈局,方便自己和其他人查看與維護。 下面是一個簡單的例子:

import XMonad

myTerminal    = "urxvt"
myModMask     = mod4Mask -- Win key or Super_L
myBorderWidth = 3

main = do
  xmonad $ def
    { terminal    = myTerminal
    , modMask     = myModMask
    , borderWidth = myBorderWidth
    }


Also, order at top level (main, myTerminal, myModMask etc.), or within the {} does not matter in Haskell, as long as imports come first.


{
  terminal           = myTerminal,
  focusFollowsMouse  = myFocusFollowsMouse,
  borderWidth        = myBorderWidth,
  modMask            = myModMask,
  -- numlockMask deprecated in 0.9.1
  -- numlockMask        = myNumlockMask,
  workspaces         = myWorkspaces,
  normalBorderColor  = myNormalBorderColor,
  focusedBorderColor = myFocusedBorderColor,

  -- key bindings
  keys               = myKeys,
  mouseBindings      = myMouseBindings,

  -- hooks, layouts
  layoutHook         = myLayout,
  manageHook         = myManageHook,
  handleEventHook    = myEventHook,
  logHook            = myLogHook,
  startupHook        = myStartupHook
}

The package itself also includes a xmonad.hs, which is the latest official example xmonad.hs that comes with the xmonad Haskell module as an example of how to override everything. This should not be used as a template configuration, but as examples of parts you can pick to use in your own configuration. It is located in an architecture and version dependant directory in /usr/share/ (e.g. find /usr/share -name xmonad.hs).

A base desktop configuration[編輯 | 編輯原始碼]

In xmonad-contrib is a better default configuration for average desktop uses. It also helps with problems in some modern programs like Chromium.

It can be added like so:

import XMonad
import XMonad.Config.Desktop

main = xmonad desktopConfig
    { terminal    = "urxvt"
    , modMask     = mod4Mask
    }

Exiting xmonad[編輯 | 編輯原始碼]

To end the current xmonad session, press Mod+Shift+Q. By default, Mod is the Alt key.

Tips and tricks[編輯 | 編輯原始碼]

X-Selection-Paste[編輯 | 編輯原始碼]

The keyboard-centered operation in xmonad can be further supported with a keyboard shortcut for X-Selection-Paste.

Also, there exists a function "pasteSelection" in XMonad.Util.Paste that can be bound to a key using a line like:

xmonad.hs
  import XMonad.Util.Paste -- Remember to include this line
  
  -- X-selection-paste buffer
  , ((0, xK_Insert), pasteSelection)

Pressing the "Insert" key will now paste the mouse buffer in the active window.

Keyboard shortcuts[編輯 | 編輯原始碼]

Default keyboard shortcuts are listed in the man page of xmonad.

Targeting unbound keys[編輯 | 編輯原始碼]

If you use xmonad as a stand alone window manager, you can edit the xmonad.hs to add unbound keyboard keys. You just need to find the Xf86 name of the key (such as XF86PowerDown) and look it up in /usr/include/X11/XF86keysym.h. It will give you a keycode (like 0x1008FF2A) which you can use to add a line like the following in the keybindings section of your xmonad.hs:

((0,               0x1008FF2A), spawn "sudo pm-suspend")

Increase the number of workspaces[編輯 | 編輯原始碼]

By default, xmonad uses a set of 9 workspaces. You can change this by changing the workspaces parameter:

xmonad.hs
import XMonad
import XMonad.Util.EZConfig (additionalKeys)

main=do
  xmonad $ def
    { ...
    , workspaces = myWorkspaces
    , ...
    } `additionalKeys` myAdditionalKeys

myWorkspaces = ["1","2","3","4","5","6","7","8","9"] ++ (map snd myExtraWorkspaces) -- you can customize the names of the default workspaces by changing the list

myExtraWorkspaces = [(xK_0, "0")] -- list of (key, name)

myAdditionalKeys =
    [ -- ... your other hotkeys ...
    ] ++ [
        ((myModMask, key), (windows $ W.greedyView ws))
        | (key, ws) <- myExtraWorkspaces
    ] ++ [
        ((myModMask .|. shiftMask, key), (windows $ W.shift ws))
        | (key, ws) <- myExtraWorkspaces
    ]

Making room for docks/panels/trays (Xmobar, Tint2, Conky, etc)[編輯 | 編輯原始碼]

Wrap your layouts with avoidStruts from XMonad.Hooks.ManageDocks for automatic dock/panel/trayer spacing:

import XMonad
import XMonad.Hooks.ManageDocks

main=do
  xmonad $ docks def
    { ...
    , layoutHook=avoidStruts $ layoutHook def
    , manageHook=manageHook def <+> manageDocks
    , ...
    }

If you ever want to toggle the gaps, this action can be added to your key bindings:

,((modMask x, xK_b     ), sendMessage ToggleStruts)

Equally sized gaps between windows[編輯 | 編輯原始碼]

If your goal is to have equally sized gaps between individual windows and the screen, the following code will not work as expected:

layoutHook = spacing 10 $ Tall (1 (3/100) (1/2)) ||| Full

This makes each window have its own spacing in each direction. If you have two windows side-by-side, the spacing in the middle will be combined, creating a gap that is twice as large as needed.

A workaround is to specify both a screen and a window spacing, but only use the top and left margins for the screen and bottom and right margins for the windows. To do this, change the above code into:

 layoutHook = spacingRaw False (Border 10 0 10 0) True (Border 0 10 0 10) True $ Tall (1 (3/100) (1/2)) ||| Full

Using xmobar with xmonad[編輯 | 編輯原始碼]

本文或本章節可能需要合併到xmobar

附註: Make use of the separate article available(在 Talk:Xmonad 中討論)

xmobar is a light and minimalistic text-based bar, designed to work with xmonad. To use xmobar with xmonad, you will need two packages in addition to the xmonad package. These packages are xmonad-contrib and xmobar from the official repositories, or you can use xmobar-gitAUR from the AUR instead of the official xmobar package.

Here we will start xmobar from within xmonad, which reloads xmobar whenever you reload xmonad.

Open ~/.xmonad/xmonad.hs in your favorite editor, and choose one of the two following options:

Quick, less flexible[編輯 | 編輯原始碼]

注意: There is also dzen2 which you can substitute for xmobar in either case.

Common imports:

import XMonad
import XMonad.Hooks.DynamicLog

The xmobar action starts xmobar and returns a modified configuration that includes all of the options described in #More configurable.

main = xmonad =<< xmobar def { modMask = mod4Mask {- or any other configurations here ... -}}

More configurable[編輯 | 編輯原始碼]

As of xmonad(-contrib) 0.9, there is a new statusBar function in XMonad.Hooks.DynamicLog. It allows you to use your own configuration for:

  • The command used to execute the bar
  • The PP that determines what is being written to the bar
  • The key binding to toggle the gap for the bar

The following is an example of how to use it:

~/.xmonad/xmonad.hs
-- Imports.
import XMonad
import XMonad.Hooks.DynamicLog

-- The main function.
main = xmonad =<< statusBar myBar myPP toggleStrutsKey myConfig

-- Command to launch the bar.
myBar = "xmobar"

-- Custom PP, configure it as you like. It determines what is being written to the bar.
myPP = xmobarPP { ppCurrent = xmobarColor "#429942" "" . wrap "<" ">" }

-- Key binding to toggle the gap for the bar.
toggleStrutsKey XConfig {XMonad.modMask = modMask} = (modMask, xK_b)

-- Main configuration, override the defaults to your liking.
myConfig = def { modMask = mod4Mask }

Verify XMobar config[編輯 | 編輯原始碼]

The template and default xmobarrc contains this.

At last, open up ~/.xmobarrc and make sure you have StdinReader in the template and run the plugin. E.g.

~/.xmobarrc
Config { ...
       , commands = [ Run StdinReader .... ]
         ...
       , template = " %StdinReader% ... "
       }

Now, all you should have to do is either to start, or restart, xmonad.

Controlling xmonad with external scripts[編輯 | 編輯原始碼]

Here are a few ways to do it,

  • simulate keypress events using xdotool or similar programs. See this Ubuntu forums thread. The following command would simulate the keypress Super+n:
xdotool key Super+n
  • wmctrl -If you have desktopConfig or EwmhDesktops configured, this is a very easy to use and standard utility.

Launching another window manager within xmonad[編輯 | 編輯原始碼]

If you are using xmonad-gitAUR, as of January of 2011, you can restart to another window manager from within xmonad. You just need to write a small script, and add stuff to your ~/.xmonad/xmonad.hs. Here is the script.

~/bin/obtoxmd
#!/bin/sh
openbox
xmonad

And here are the modifications you need to add to your ~/.xmonad/xmonad.hs:

~/.xmonad/xmonad.hs
import XMonad
--You need to add this import
import XMonad.Util.Replace

main do
    -- And this "replace"
    replace
    xmonad $ def
    {
    --Add the usual here
    }

You also need to add the following key binding:

~/xmonad/xmonad.hs
--Add a keybinding as follows:
((modm .|. shiftMask, xK_o     ), restart "/home/abijr/bin/obtoxmd" True)

Just remember to add a comma before or after and change the path to your actual script path. Now just Mod+q (restart xmonad to refresh the configuration), and then hit Mod+Shift+o and you should have Openbox running with the same windows open as in xmonad. To return to xmonad you should just exit Openbox. Here is a link to adamvo's ~/.xmonad/xmonad.hs which uses this setup Adamvo's xmonad.hs

KDE and xmonad[編輯 | 編輯原始碼]

The xmonad wiki has instructions on how to run xmonad inside KDE

It also might be a good idea to set a global keyboard shortcut in KDE to start xmonad in case it is accidentally killed or closed.

Disable plasmashell[編輯 | 編輯原始碼]

You might want to disable plasmashell (the KDE5 thing responsible for desktop background, taskbar, tray, etc.).

  cp /etc/xdg/autostart/plasmashell.desktop ~/.config/autostart/

Then edit ~/.config/autostart/plasmashell.desktop and replace Exec=plasmashell with Exec=. The result will look like this:

~/.config/autostart/plasmashell.desktop
[Desktop Entry]
Exec=
Name=Plasma Desktop Workspace
... # more stuff

IM Layout for Skype[編輯 | 編輯原始碼]

In orded to create an IM layout for the newer versions of skype, the following code can be used:

xmonad.hs
myIMLayout = withIM (1%7) skype Grid
    where
      skype = And (ClassName "Skype") (Role "")

Example configurations[編輯 | 編輯原始碼]

Below are some example configurations from fellow xmonad users. Feel free to add links to your own.

  • brisbin33 :: simple, useful, readable :: config screenshot
  • jelly :: Configuration with prompt, different layouts, twinview with xmobar :: xmonad.hs
  • MrElendig :: Simple configuration, with xmobar :: xmonad.hs, .xmobarrc, screenshot.
  • thayer :: A minimal mouse-friendly config ideal for netbooks :: configs screenshot
  • vicfryzel :: Beautiful and usable xmonad configuration, along with xmobar configuration, xinitrc, dmenu, and other scripts that make xmonad more usable. :: git repository, screenshot.
  • vogt :: Check out adamvo's config and many others in the official Xmonad/Config archive
  • wulax :: Example of using xmonad inside Xfce. Contains two layouts for GIMP. :: xmonad.hs, screenshot.
  • alex-courtis :: Clean xmonad, xmobar, media keys, screenshot, j4/dmenu; fonts rendered at the DPI reported by the monitor :: xmonad.hs, screenshot.

Troubleshooting[編輯 | 編輯原始碼]

GNOME 3 and xmonad[編輯 | 編輯原始碼]

本文或本章節的事實準確性存在爭議。

原因: This no longer works with GNOME. It might still work with GNOME Flashback.(在 Talk:Xmonad 中討論)


With the release of GNOME 3 custom GNOME sessions require additional steps to make GNOME play nicely with xmonad.

Add an xmonad session file for use by gnome-session (/usr/share/gnome-session/sessions/xmonad.session):

[GNOME Session]
Name=Xmonad session
RequiredComponents=gnome-panel;gnome-settings-daemon;
RequiredProviders=windowmanager;notifications;
DefaultProvider-windowmanager=xmonad
DefaultProvider-notifications=notification-daemon

Create a desktop file for GDM (/usr/share/xsessions/xmonad-gnome-session.desktop):

[Desktop Entry]
Name=Xmonad GNOME
Comment=Tiling window manager
TryExec=/usr/bin/gnome-session
Exec=gnome-session --session=xmonad
Type=XSession

Create or edit this file (/usr/share/applications/xmonad.desktop):

[Desktop Entry]
Type=Application
Encoding=UTF-8
Name=Xmonad
Exec=xmonad
NoDisplay=true
X-GNOME-WMName=Xmonad
X-GNOME-Autostart-Phase=WindowManager
X-GNOME-Provides=windowmanager
X-GNOME-Autostart-Notify=false

Finally, install xmonad-contrib and create or edit ~/.xmonad/xmonad.hs to have the following

import XMonad
import XMonad.Config.Gnome

main = xmonad gnomeConfig

xmonad should now appear in the list of GDM sessions and also play nicely with gnome-session itself.

Compositing in GNOME and xmonad[編輯 | 編輯原始碼]

Some applications look better (e.g. GNOME Do) when composition is enabled. This, however, is not the case in the default xmonad window manager. To enable it add an additional .desktop file /usr/share/xsessions/xmonad-gnome-session-composite.desktop:

[Desktop Entry]
Name=Xmonad GNOME (Composite)
Comment=Tiling window manager
TryExec=/usr/bin/gnome-session
Exec=/usr/sbin/gnome-xmonad-composite
Type=XSession

And create /usr/sbin/gnome-xmonad-composite and chmod +x /usr/sbin/gnome-xmonad-composite:

xcompmgr &
gnome-session --session=xmonad

Now choose "Xmonad GNOME (Composite)" in the list of sessions during login. Reference xcompmgr(1) for additional "eye candy".

Xfce 4 and xmonad[編輯 | 編輯原始碼]

Use xfceConfig instead of def after importing XMonad.Config.Xfce in ~/.xmonad/xmonad.hs, e.g. adapting the minimal configuration above:

import XMonad
import XMonad.Config.Xfce

main = xmonad xfceConfig
    { terminal    = "urxvt"
    , modMask     = mod4Mask
    }

Also add an entry to Settings > Session and Startup > Application Autostart that runs xmonad --replace.

Missing xmonad-i386-linux or xmonad-x86_64-linux[編輯 | 編輯原始碼]

xmonad should automatically create the xmonad-i386-linux file (in ~/.xmonad/). If this it not the case, grab a configuration file from the xmonad wiki or create your own. Put the .hs and all others files in ~/.xmonad/ and run this command from the folder:

xmonad --recompile

Now you should see the file.

注意: A reason you may get an error message saying that xmonad-x86_64-linux is missing is that xmonad-contrib is not installed.

Problems with Java applications[編輯 | 編輯原始碼]

If you have problems, like Java application Windows not resizing, or menus immediately closing after you click, see Java#Gray window, applications not resizing with WM, menus immediately closing.

Empty space at the bottom of gvim or terminals[編輯 | 編輯原始碼]

See Vim#Empty space at the bottom of gVim windows for a solution which makes the area match the background color.

For rxvt-unicode, you can use rxvt-unicode-patchedAUR.

You can also configure xmonad to respect size hints, but this will leave a gap instead. See on Xmonad.Layout.LayoutHints.

Chromium/Chrome will not go fullscreen[編輯 | 編輯原始碼]

If Chrome fails to go fullscreen when F11 is pressed, you can use the XMonad.Hooks.EwmhDesktops extension found in the xmonad-contrib package. Simply add the import statement to your ~/.xmonad/xmonad.hs:

import XMonad.Hooks.EwmhDesktops

and then add handleEventHook = fullscreenEventHook to the appropriate place; for example:

...
        xmonad $ def
            { modMask            = mod4Mask
            , handleEventHook    = fullscreenEventHook
            }
...

After a recompile/restart of xmonad, Chromium should now respond to F11 (fullscreen) as expected.

Multitouch / touchegg[編輯 | 編輯原始碼]

Touchégg polls the window manager for the _NET_CLIENT_LIST (in order to fetch a list of windows it should listen for mouse events on.) By default, xmonad does not supply this property. To enable this, use the XMonad.Hooks.EwmhDesktops extension found in the xmonad-contrib package.

Keybinding issues with an azerty keyboard layout[編輯 | 編輯原始碼]

Users with a keyboard with azerty layout can run into issues with certain keybindings. Using the XMonad.Config.Azerty module will solve this.

GNOME 3 mod4+p changes display configuration instead of launching dmenu[編輯 | 編輯原始碼]

If you do not need the capability to switch the display-setup in the gnome-control-center, just execute

dconf write /org/gnome/settings-daemon/plugins/xrandr/active false

as your user, to disable the xrandr plugin which grabs Super+p.

Problems with focused border in VirtualBox[編輯 | 編輯原始碼]

A known issue with Virtualbox (Ticket #6479) can cause problems with the focused window border. A solution can be found by installing a compositing manager like xcompmgr which overrides the incorrect behavior of vboxvideo.

Steam games (Half-Life, Left 4 Dead, …) and xmonad[編輯 | 編輯原始碼]

There seems to be some trouble with xmonad and Source engine based games like Half-Life. If they do not start or get stuck with a black screen, a workaround is to start them in windowed mode. To do so, right click on the game in your Steam library and choose properties, click on launch options and enter [1]:

-windowed

Another solution is to float the window of the game using the manage hook. For example, the following line can be used for Half-Life:

 className =? "hl_linux" --> doFloat

This can also be worked around by making xmonad pay attention to EWMH hints and including its fullscreen hook [2]:

  main = xmonad $ ewmh def{ handleEventHook =
           handleEventHook def <+> fullscreenEventHook }

This has a few other effects and makes it behave more akin to fullscreen apps in other WMs.

LibreOffice - focus flicking between main window and dialog[編輯 | 編輯原始碼]

The LibreOffice UI defaults to the gtk engine outside a desktop environment. This may cause problems with some xmonad configurations resulting in focus rapidly flicking between the LibreOffice main window and any open LibreOffice dialog window. Effectively locking the application. In this case the environment variable SAL_USE_VCLPLUGIN can be set to explicitly force LibreOffice to use another UI theme as outlined in LibreOffice#Theme For instance

  export SAL_USE_VCLPLUGIN=gen lowriter

to use the general (QT) UI.

Problems with finding shared libraries after update[編輯 | 編輯原始碼]

The xmonad executable is located in ~/.xmonad/. After upgrading xmonad, an old executable might persist and need in that case be removed for xmonad to compile a new executable. Alternatively use xmonad --recompile.

In the case that xmonad --recompile cannot find any modules at all (including XMonad itself), try regenerating the package database cache

sudo ghc-pkg recache

Broken/missing XMonad.Prompt and window decorations[編輯 | 編輯原始碼]

XMonad by default uses the font -misc-fixed-*-*-*-*-10-*-*-*-*-*-*-* [3]. If this font is missing those windows simply fail to render at all. Easiest fix is to install (xorg-fonts-misc.

See also[編輯 | 編輯原始碼]