rendered paste body-- -*- haskell -*-
import Monad (liftM)
import XMonad
import XMonad.Core
import System.Exit
import qualified XMonad.StackSet as W
import qualified Data.Map as M
import XMonad.Layout.Tabbed
import XMonad.Layout.ResizableTile
import XMonad.Layout.Grid
import XMonad.Layout.Magnifier
import XMonad.Layout.TabBarDecoration
import XMonad.Hooks.DynamicLog ( PP(..), dynamicLogWithPP, dzenColor, wrap, defaultPP )
import XMonad.Actions.CycleWS
import XMonad.Hooks.ManageDocks
import XMonad.Hooks.EwmhDesktops
import XMonad.Actions.DwmPromote
import XMonad.Actions.UpdatePointer
import XMonad.Hooks.UrgencyHook
import XMonad.Util.Run (spawnPipe)
import System.IO
import XMonad.Prompt
import XMonad.Prompt.Shell
more generic search prompts than those in XMonad.Prompt.Search
import XMonad.Util.WorkspaceCompare
import XMonad.Util.EZConfig
import Graphics.X11.ExtraTypes.XF86(xF86XK_AudioLowerVolume,
xF86XK_AudioMute, xF86XK_AudioNext, xF86XK_AudioPlay,
xF86XK_AudioPrev, xF86XK_AudioRaiseVolume, xF86XK_AudioStop, xF86XK_Forward, xF86XK_Back)
import XMonad.Actions.Warp
import Data.Ratio
myStatusbarCmd = "run-dzen2"
myTerminal = "urxvtc"
myScreenLock = "xlock +nolock"
myBorderWidth = 0
myModMask = mod4Mask
myNumlockMask = mod2Mask
myWorkspaces = ["1:web", "2:bk" ,"3:ssh", "4:dev", "5:sh", "6:maths", "7:games", "8:multimedia", "9:tmp", "10:logs"]
myNormalBorderColor = "#111"
myFocusedBorderColor = "cadetblue3"
myKeys = \conf -> mkKeymap conf $
[ ("C-S-<Esc>", spawn $ myScreenLock)
, ("M-C-<Esc>", spawn $ "xkill")
, ("M-<Space>", sendMessage NextLayout)
, ("M-S-<Space>", setLayout $ XMonad.layoutHook conf)
, ("M-n", refresh)
, ("M-S-c", kill)
, ("M-<Tab>", windows W.focusDown)
, ("M-j", windows W.focusDown)
, ("M-S-<Tab>", windows W.focusUp)
, ("M-k", windows W.focusUp)
, ("M-m", windows W.focusMaster)
, ("M-S-k", windows W.swapDown)
, ("M-S-j", windows W.swapUp)
, ("M-b", sendMessage ToggleStruts)
, ("M-h", sendMessage Shrink)
, ("M-l", sendMessage Expand)
, ("M-t", withFocused $ windows . W.sink)
, ("M-,", sendMessage (IncMasterN 1))
, ("M-.", sendMessage (IncMasterN (-1)))
, ("M-S-q", io (exitWith ExitSuccess))
, ("M-q", restart "xmonad" True)
, ("M-p", shellPrompt oxyXPConfig)
, ("M-o", shellPrompt oxyXPConfig)
, ("M-S-<Right>", shiftToNext >> nextWS)
, ("M-S-<Left>", shiftToPrev >> prevWS)
, ("M-<Down>", nextScreen)
, ("M-S-<Down>", shiftNextScreen >> nextScreen)
, ("M-<Left>", prevNonEmptyWS)
, ("M-C-k", prevNonEmptyWS)
, ("M-<Right>", nextNonEmptyWS)
, ("M-C-j", nextNonEmptyWS)
, ("M-s", swapNextScreen)
, ("M-<Up>", swapNextScreen)
, ("M-a", sendMessage MirrorShrink)
, ("M-y", sendMessage MirrorExpand)
, ("M-<Return>", dwmpromote)
, ("M-x c", kill)
, ("M-u M-x M-x", swapNextScreen)
, ("M-x a", spawn "cgoban")
, ("M-x b", spawn "urxvtc -g 80x24+172+149 -pe tabbed")
, ("M-x d", spawn "urxvtc -e sh -c 'screen -x'")
, ("M-x e", spawn "urxvtc -name Emacs -g 272x83+0-0 -e sh -c 'TERM=xterm-color emacsclient -nw'")
sh -c 'TERM=xterm-color nimred-emacsclient'")
, ("M-x f", spawn "urxvtc -name firefox -g 96x11+626+494 -e firefox3")
, ("M-x g", spawn "gcalculator")
, ("M-x h", spawn "xboard -boardSize Middling -fcp crafty -clockMode False")
, ("M-x l", spawn "urxvtc -name slrn -g 252x78+64+48 -e sh -c 'slrn'")
-e sh -c 'TERM=xterm-color emacs -daemon -g 272x83+0-0'")
, ("M-x m", spawn "urxvtc -name Mutt -g 252x78+64+48 -e sh -c 'env TERM=xterm-color mutt -y'")
, ("M-x n", spawn "urxvtc -name ncmpc -g 150x35-56-40 -e sh -c 'TERM=xterm-color ncmpc'")
-e opera -nomail -noraise -geometry 1244x670+326+128")
, ("M-x o", spawn "urxvtc -name opera -g 96x11+644+320 -e opera -nomail -noraise -geometry 1109x574+386+116")
, ("M-x p", spawn "opera -newpage `xclip -o | xargs echo`")
, ("M-x r", spawn "urxvtc -name radiobrowser -g 99x80+39-26 -e sh -c 'screen -xRD -c ~/.screenrc4tvradio'")
, ("M-x s", spawn "fltk-sudoku -g 480x505+928+107")
-e sh -c 'screen -xRD -c ~/.screenrc4tv'")
, ("M-x v", spawn "urxvtc -name vim -g 252x78+64+48 -e sh -c 'TERM=xterm-color vim'")
, ("M-x w", spawn "urxvtc -g 245x72-91-88 -C")
, ("M-x x", spawn $ XMonad.terminal conf)
, ("M-x M-o", spawn "urxvtc -g 80x24+780+448 -e soffice -nologo")
, ("M-x M-f", spawn "urxvtc -g 226x30+331+116 -e finch")
, ("M1-x p", spawn "emacsclient --eval '(emms-play-playlist (expand-file-name \"~/.emacs.d/emms/All.m3u\"))'")
, ("M1-x r", spawn "emacsclient --eval '(emms-random)'")
, ("C-<F20>", spawn "emacsclient --eval '(emms-seek-forward)'")
, ("C-<F19>", spawn "emacsclient --eval '(emms-seek-backward)'")
, ("S-<Tab>", spawn "xclip -o | xargs echo | wgetpaste -X > /dev/console")
, ("S-<Esc>", spawn "xclip -o | xargs echo | xargs -o wgetpaste -X -c > /dev/console")
, ("C-M1-r", spawn "sudo /sbin/fastboot")
, ("C-M1-p", spawn "sudo /sbin/fasthalt -p")
, ("C-M1-M-e", spawn "eject /dev/rcd0d")
, ("C-M1-M-p", spawn "sudo /sbin/shutdown -p now")
, ("C-M1-M-r", spawn "sudo /sbin/shutdown -r now")
, ("C-M1-M-w", spawn "random-wallpaper")
, ("M-<", spawn $ myScreenLock)
, ("M1-<Return>", spawn $ XMonad.terminal conf)
, ("M-w", sendMessage MagnifyMore)
, ("M-e", sendMessage MagnifyLess)
, ("C-<", warpToWindow (1%10) (1%10)) -- Move pointer to currently focused window
]
++
[ (m ++ i, windows $ f j)
| (i, j) <- zip (map show [1..9]) (XMonad.workspaces conf)
, (m, f) <- [("M-", W.view), ("M-S-", W.shift)]
]
where
nextNonEmptyWS = moveTo Next (WSIs (liftM (not .) isVisible))
prevNonEmptyWS = moveTo Prev (WSIs (liftM (not .) isVisible))
isVisible :: X (WindowSpace -> Bool)
isVisible = do
vs <- gets (map (W.tag . W.workspace) . W.visible . windowset)
return (\w -> (W.tag w) `elem` vs)
multimediaKeys =
[
((0 , xF86XK_AudioMute), spawn "aumute")
, ((0 , xF86XK_AudioLowerVolume), spawn "aumix -v-5")
, ((0 , xF86XK_AudioRaiseVolume), spawn "aumix -v+5 ")
, ((0 , xF86XK_AudioPlay), spawn "emacsclient --eval '(emms-pause)'")
, ((0 , xF86XK_AudioStop), spawn "emacsclient --eval '(emms-stop)'")
, ((0 , xF86XK_AudioPrev), spawn "emacsclient --eval '(emms-previous)'")
, ((0 , xF86XK_AudioNext), spawn "emacsclient --eval '(emms-next)'")
]
-- Config for Prompt
oxyXPConfig :: XPConfig
oxyXPConfig = defaultXPConfig { font = "xft:Consolas-12"
, bgColor = "Aquamarine3"
, fgColor = "black"
, fgHLight = "black"
, bgHLight = "darkslategray4"
, borderColor = "black"
, promptBorderWidth = 1
, position = Top
, height = 24
, defaultText = []
}
myMouseBindings (XConfig {XMonad.modMask = modMask}) = M.fromList $
[ ((modMask, button1), (\w -> focus w >> mouseMoveWindow w))
, ((modMask, button2), (\w -> focus w >> windows W.swapMaster))
, ((modMask, button3), (\w -> focus w >> mouseResizeWindow w))
, ((modMask, button4), (\_ -> windows W.focusUp))
, ((modMask, button5), (\_ -> windows W.focusDown))
, ((controlMask .|. modMask, button5), nextNonEmptyWS)
, ((controlMask .|. modMask, button4), prevNonEmptyWS)
]
where
nextNonEmptyWS = \_ -> moveTo Next (WSIs (liftM (not .) isVisible))
prevNonEmptyWS = \_ -> moveTo Prev (WSIs (liftM (not .) isVisible))
myLayout = avoidStrutsOn[U] $ tabs
||| tiled
||| Mirror tiled
||| magnify Grid
where
tiled = ResizableTall nmaster delta ratio []
nmaster = 1
ratio = 8 % 13
delta = 3 % 100
tabs = tabbed shrinkText oxyDarkTheme
magnify = magnifiercz (13%10)
-- Configuration for Tabbed
oxyTheme :: Theme
oxyTheme = defaultTheme { inactiveBorderColor = "#000"
, activeBorderColor = myFocusedBorderColor
, activeColor = "aquamarine3"
, inactiveColor = "DarkSlateGray4"
, inactiveTextColor = "#222"
, activeTextColor = "#222"
, fontName = "xft:Consolas-10:bold"
, decoHeight = 18
, urgentColor = "#000"
, urgentTextColor = "#63b8ff"
}
oxyDarkTheme :: Theme
oxyDarkTheme = defaultTheme { inactiveBorderColor = "#777"
, activeBorderColor = myFocusedBorderColor
, activeColor = "#000"
, inactiveColor = "#444"
, inactiveTextColor = "aquamarine4"
, activeTextColor = "aquamarine1"
, fontName = "xft:Dejavu Sans Mono-8"
, decoHeight = 15
, urgentColor = "#000"
, urgentTextColor = "#63b8ff"
}
-- A manageHook to float everything by default and unfloat a few windows
myManageHook :: ManageHook
myManageHook = composeAll [ appName =? "urxvt" --> unfloat
, appName =? "Console" --> unfloat
, appName =? "Emacs" --> unfloat
, appName =? "slrn" --> unfloat
, appName =? "Mutt" --> unfloat
, appName =? "sshinfo" --> unfloat
, appName =? "sshfr" --> unfloat
, appName =? "sshnet" --> unfloat
, className =? "Minefield" --> doF (W.shift "1:web")
, appName =? "firefox" --> doF (W.shift "1:web")
, className =? "Firefox" --> doF (W.shift "1:web")
, className =? "Opera" --> doF (W.shift "1:web")
, className =? "opera" --> doF (W.shift "1:web")
, appName =? "opera" --> doF (W.shift "1:web")
, appName =? "sshinfo" --> doF (W.shift "3:ssh")
, appName =? "sshfr" --> doF (W.shift "3:ssh")
, appName =? "sshnet" --> doF (W.shift "3:ssh")
, appName =? "scilex" --> doF (W.shift "6:maths")
, appName =? "Xscilab" --> doF (W.shift "6:maths")
, className =? "CGoban Control" --> doF (W.shift "7:games")
, className =? "Basicwin" --> doF (W.shift "7:games")
, className =? "xboard" --> doF (W.shift "7:games")
, className =? "XBoard" --> doF (W.shift "7:games")
, className =? "Sudoku" --> doF (W.shift "7:games")
, className =? "Fltk" --> doF (W.shift "7:games")
, appName =? "tvbrowser" --> doF (W.shift "8:multimedia")
, appName =? "radiobrowser" --> doF (W.shift "8:multimedia")
, appName =? "ncmpc" --> doF (W.shift "8:multimedia")
, className =? "MPlayer" --> doF (W.shift "8:multimedia")
, className =? "VLC" --> doF (W.shift "8:multimedia")
, className =? "vlc" --> doF (W.shift "8:multimedia")
, appName =? "VLC" --> doF (W.shift "8:multimedia")
, appName =? "vlc" --> doF (W.shift "8:multimedia")
, appName =? "Mutt" --> doF (W.shift "9:tmp")
, appName =? "slrn" --> doF (W.shift "9:tmp")
, appName =? "Xpdf" --> doF (W.shift "9:tmp")
, appName =? "Console" --> doF (W.shift "10:logs") ]
<+> doFloat <+> manageDocks
where unfloat = ask >>= doF . W.sink
-- Status bars and logging
myLogHook h = do
ewmhDesktopsLogHook
dynamicLogWithPP $ oxyPP h
updatePointer (Relative (1/20) (1/20))
-- dynamiclog pretty printer for dzen
--
oxyPP :: Handle -> PP
oxyPP h = defaultPP { ppCurrent = wrap "^fg(#000000)^bg(#a6c292)^p(2)^i(/home/nimred/.icons/has_win.xbm)" "^p(2)^fg()^bg()"
, ppSep = " ^fg(grey60)^r(3x3)^fg() "
, ppWsSep = ""
, ppVisible = wrap "^bg(grey30)^fg(grey75)^p(2)" "^p(2)^fg()^bg()"
, ppLayout = dzenColor "#80AA83" "" .
(\x -> case x of
"Mirror ResizableTall" -> "MTiled"
"ResizableTall" -> "Tiled"
"Tabbed Bottom Simplest" -> "Tabbed"
"Tabbed Simplest" -> "Tabbed"
_ -> x
)
, ppTitle = dzenColor "white" "" . wrap "< " " >"
, ppOutput = hPutStrLn h
}
myFocusFollowsMouse :: Bool
myFocusFollowsMouse = True
------------------------------------------------------------------------
-- Now run xmonad with all the defaults we set up.
main = do
pipe <- spawnPipe myStatusbarCmd
xmonad $ withUrgencyHook NoUrgencyHook $ defaults pipe
defaults pipe = defaultConfig {
-- simple stuff
terminal = myTerminal,
focusFollowsMouse = myFocusFollowsMouse,
borderWidth = myBorderWidth,
modMask = myModMask,
numlockMask = myNumlockMask,
workspaces = myWorkspaces,
normalBorderColor = myNormalBorderColor,
focusedBorderColor = myFocusedBorderColor,
-- key bindings
keys = myKeys,
mouseBindings = myMouseBindings,
-- hooks, layouts
layoutHook = myLayout,
manageHook = myManageHook,
logHook = myLogHook pipe
} `additionalKeys` multimediaKeys