|
|
-----------------------------------------------------------------------------
-- |
-- Module : XMonad.Hooks.DebugStack
-- Copyright : (c) Brandon S Allbery KF8NH, 2014
-- License : BSD3-style (see LICENSE)
--
-- Maintainer : allbery.b@gmail.com
-- Stability : unstable
-- Portability : not portable
--
-- Dump the state of the 'StackSet'. A @logHook@ and @handleEventHook@ are
-- also provided.
--
-----------------------------------------------------------------------------
module XMonad.Hooks.DebugStack (debugStack
,debugStackFull
,debugStackString
,debugStackFullString
,debugStackLogHook
,debugStackFullLogHook
,debugStackEventHook
,debugStackFullEventHook
) where
import XMonad.Core
import qualified XMonad.StackSet as W
import XMonad.Util.DebugWindow
import Graphics.X11.Types (Window)
import Graphics.X11.Xlib.Extras (Event)
import Control.Monad (foldM)
import Data.Map (member)
import Data.Monoid (All(..))
import Data.List (intercalate)
-- | Print the state of the current window stack for the current workspace to
-- @stderr@, which for most installations goes to @~/.xsession-errors@.
-- "XMonad.Util.DebugWindow" is used to display the individual windows.
debugStack :: X ()
debugStack = debugStackString >>= trace
-- | Print the state of the current window stack for all workspaces to
-- @stderr@, which for most installations goes to @~/.xsession-errors@.
-- "XMonad.Util.DebugWindow" is used to display the individual windows.
debugStackFull :: X ()
debugStackFull = debugStackFullString >>= trace
-- | 'debugStack' packaged as a 'logHook'. (Currently this is identical.)
debugStackLogHook :: X ()
debugStackLogHook = debugStack
-- | 'debugStackFull packaged as a 'logHook'. (Currently this is identical.)
debugStackFullLogHook :: X ()
debugStackFullLogHook = debugStackFull
-- | 'debugStack' packaged as a 'handleEventHook'. You almost certainly do not
-- want to use this unconditionally, as it will cause massive amounts of
-- output and possibly slow @xmonad@ down severely.
debugStackEventHook :: Event -> X All
debugStackEventHook _ = debugStack >> return (All True)
-- | 'debugStackFull' packaged as a 'handleEventHook'. You almost certainly do
-- not want to use this unconditionally, as it will cause massive amounts of
-- output and possibly slow @xmonad@ down severely.
debugStackFullEventHook :: Event -> X All
debugStackFullEventHook _ = debugStackFull >> return (All True)
-- | Dump the state of the current workspace in the 'StackSet' as a multiline 'String'.
debugStackString :: X String
debugStackString = withWindowSet $ debugStackWs . W.workspace . W.current
-- | Dump the state of all workspaces in the 'StackSet' as a multiline 'String'.
-- @@@ this is in stackset order, which is roughly lru-ish
debugStackFullString :: X String
debugStackFullString = withWindowSet $ fmap (intercalate "\n") . mapM debugStackWs . W.workspaces
-- | Dump the state of a workspace in the current 'StackSet' as a multiline 'String'.
-- @
-- Workspace "foo::
-- mm
-- * ww
-- ^ww
-- @
-- * indicates the focused window, ^ indicates a floating window
debugStackWs :: W.Workspace String (Layout Window) Window -> X String
debugStackWs w = withWindowSet $ \ws -> do
let cur = if wt == W.currentTag ws then " (current)" else ""
wt = W.tag w
s <- emit ws $ W.integrate' . W.stack $ w
return $ intercalate "\n" $ ("Workspace " ++ show wt ++ cur):s
where
emit :: WindowSet -> [Window] -> X [String]
emit _ [] = return [" -empty workspace-"]
emit ww ws = do
(_,ss) <- foldM emit' (ww,[]) ws
return ss
emit' :: (WindowSet,[String])
-> Window
-> X (WindowSet,[String])
emit' (ws,a) w' = do
let focus = if Just w' == W.peek ws then '*' else ' '
float = if w' `member` W.floating ws then '^' else ' '
s <- debugWindow w'
return (ws,(focus:float:s):a)
|