XMonad.Actions.TreeSelect

xmonad-contrib-0.13: Third party extensions for xmonad

Copyright | (c) Tom Smeets <tom.tsmeets@gmail.com>
License | BSD3-style (see LICENSE)
Maintainer | Tom Smeets <tom.tsmeets@gmail.com>
Stability | unstable
Portability | unportable
Safe Haskell | None
Language | Haskell98

XMonad.Actions.TreeSelect

Contents

- Usage
- Configuring
- Navigation
- Advanced usage

Description

TreeSelect displays your workspaces or actions in a Tree-like format. You can select the desired workspace/action with the cursor or hjkl keys.

This module is fully configurable and very useful if you like to have a lot of workspaces.

Only the nodes up to the currently selected are displayed. This will be configurable in the near future by changing `ts_hidechildren` to `False`, this is not yet implemented.

Synopsis

- treeselectWorkspace :: TSConfig WorkspaceId -> Forest String -> (WorkspaceId -> WindowSet -> WindowSet) -> X ()
- toWorkspaces :: Forest String -> [WorkspaceId]
- treeselectAction :: TSConfig (X a) -> Forest (TSNode (X a)) -> X ()
- type Pixel = Word64
- data TSConfig a = TSConfig {
  - ts_hidechildren :: Bool
  - ts_background :: Pixel
  - ts_font :: String
  - ts_node :: (Pixel, Pixel)
  - ts_nodealt :: (Pixel, Pixel)
  - ts_highlight :: (Pixel, Pixel)
  - ts_extra :: Pixel
  - ts_node_width :: Int
  - ts_node_height :: Int
  - ts_originX :: Int
  - ts_originY :: Int
  - ts_indent :: Int
  - ts_navigate :: Map (KeyMask, KeySym) (TreeSelect a (Maybe a))
  }
- tsDefaultConfig :: TSConfig a
- defaultNavigation :: Map (KeyMask, KeySym) (TreeSelect a (Maybe a))
- select :: TreeSelect a (Maybe a)
- cancel :: TreeSelect a (Maybe a)
- moveParent :: TreeSelect a (Maybe a)
- moveChild :: TreeSelect a (Maybe a)
- moveNext :: TreeSelect a (Maybe a)
- movePrev :: TreeSelect a (Maybe a)
- moveHistBack :: TreeSelect a (Maybe a)
- moveHistForward :: TreeSelect a (Maybe a)
- moveTo :: [String] -> TreeSelect a (Maybe a)
- data TSNode a = TSNode {
  - tsn_name :: String
  - tsn_extra :: String
  - tsn_value :: a
  }
- treeselect :: TSConfig a -> Forest (TSNode a) -> X (Maybe a)
- treeselectAt :: TSConfig a -> TreeZipper (TSNode a) -> [[String]] -> X (Maybe a)

# Usage

These imports are used in the following example

    import Data.Tree
    import XMonad.Actions.TreeSelect
    import XMonad.Hooks.WorkspaceHistory
    import qualified XMonad.StackSet as W

For selecting Workspaces, you need to define them in a tree structure using `Node` instead of just a standard list

Here is an example workspace-tree

    myWorkspaces :: Forest String
    myWorkspaces = [ Node "Browser" [] -- a workspace for your browser
                   , Node "Home"       -- for everyday activity's
                       [ Node "1" []   --  with 4 extra sub-workspaces, for even more activity's
                       , Node "2" []
                       , Node "3" []
                       , Node "4" []
                       ]
                   , Node "Programming" -- for all your programming needs
                       [ Node "Haskell" []
                       , Node "Docs"    [] -- documentation
                       ]
                   ]

Then add it to your `workspaces` using the `toWorkspaces` function.

Optionally, if you add `workspaceHistoryHook` to your `logHook` you can use the 'o' and 'i' keys to select from previously-visited workspaces

    xmonad $ defaultConfig { ...
                           , workspaces = toWorkspaces myWorkspaces
                           , logHook = workspaceHistoryHook
                           }

After that you still need to bind buttons to `treeselectWorkspace` to start selecting a workspaces and moving windows

you could bind `Mod-f` to switch workspace

     , ((modMask, xK_f), treeselectWorkspace myTreeConf myWorkspaces W.greedyView)

and bind `Mod-Shift-f` to moving the focused windows to a workspace

     , ((modMask .|. shiftMask, xK_f), treeselectWorkspace myTreeConf myWorkspaces W.shift)

treeselectWorkspace #

Arguments

:: TSConfig WorkspaceId |
-> Forest String | your tree of workspace-names
-> (WorkspaceId -> WindowSet -> WindowSet) | the "view" function. Instances can be `greedyView` for switching to a workspace and/or `shift` for moving the focused window to a selected workspace. These actions can also be combined by doing
    \i -> W.greedyView i . W.shift i
-> X () |

Select a workspace and execute a "view" function from XMonad.StackSet on it.

toWorkspaces :: Forest String -> [WorkspaceId] #

Convert the workspace-tree to a flat list of paths such that XMonad can use them

The Nodes will be separated by a dot ('.') character

treeselectAction :: TSConfig (X a) -> Forest (TSNode (X a)) -> X () #

Select from a Tree of `X` actions

Each of these actions have to be specified inside a `TSNode`

Example

    treeselectAction myTreeConf
       [ Node (TSNode "Hello"    "displays hello"      (spawn "xmessage hello!")) []
       , Node (TSNode "Shutdown" "Poweroff the system" (spawn "shutdown")) []
       , Node (TSNode "Brightness" "Sets screen brightness using xbacklight" (return ()))
           [ Node (TSNode "Bright" "FULL POWER!!"            (spawn "xbacklight -set 100")) []
           , Node (TSNode "Normal" "Normal Brightness (50%)" (spawn "xbacklight -set 50"))  []
           , Node (TSNode "Dim"    "Quite dark"              (spawn "xbacklight -set 10"))  []
           ]
       ]

# Configuring

The selection menu is very configurable, you can change the font, all colors and the sizes of the boxes.

The default config defined as `tsDefaultConfig`

    tsDefaultConfig = TSConfig { ts_hidechildren = True
                               , ts_background   = 0xc0c0c0c0
                               , ts_font         = "xft:Sans-16"
                               , ts_node         = (0xff000000, 0xff50d0db)
                               , ts_nodealt      = (0xff000000, 0xff10b8d6)
                               , ts_highlight    = (0xffffffff, 0xffff0000)
                               , ts_extra        = 0xff000000
                               , ts_node_width   = 200
                               , ts_node_height  = 30
                               , ts_originX      = 0
                               , ts_originY      = 0
                               , ts_indent       = 80
                               , ts_navigate     = defaultNavigation
                               }

type Pixel = Word64 #

The `Pixel` Color format is in the form of `0xaarrggbb`

Note that transparency is only supported if you have a window compositor running like compton

Some Examples:

    white       = 0xffffffff
    black       = 0xff000000
    red         = 0xffff0000
    blue        = 0xff00ff00
    green       = 0xff0000ff
    transparent = 0x00000000

data TSConfig a #

Extensive configuration for displaying the tree.

This class also has a `Default` instance

Constructors

TSConfig |
Fields ts_hidechildren :: Bool when enabled, only the parents (and their first children) of the current node will be shown (This feature is not yet implemented!) ts_background :: Pixel background color filling the entire screen. ts_font :: String XMF font for drawing the node name extra text ts_node :: (Pixel, Pixel) node foreground (text) and background color when not selected ts_nodealt :: (Pixel, Pixel) every other node will use this color instead of `ts_node` ts_highlight :: (Pixel, Pixel) node foreground (text) and background color when selected ts_extra :: Pixel extra text color ts_node_width :: Int node width in pixels ts_node_height :: Int node height in pixels ts_originX :: Int tree X position on the screen in pixels ts_originY :: Int tree Y position on the screen in pixels ts_indent :: Int indentation amount for each level in pixels ts_navigate :: Map (KeyMask, KeySym) (TreeSelect a (Maybe a)) key bindings for navigating the tree

Instances

Default (TSConfig a) # |
Methods def :: TSConfig a #

tsDefaultConfig :: TSConfig a #

Default configuration.

Using nice alternating blue nodes

# Navigation

Keybindings for navigations can also be modified

This is the definition of `defaultNavigation`

    defaultNavigation :: M.Map (KeyMask, KeySym) (TreeSelect a (Maybe a))
    defaultNavigation = M.fromList
        [ ((0, xK_Escape), cancel)
        , ((0, xK_Return), select)
        , ((0, xK_space),  select)
        , ((0, xK_Up),     movePrev)
        , ((0, xK_Down),   moveNext)
        , ((0, xK_Left),   moveParent)
        , ((0, xK_Right),  moveChild)
        , ((0, xK_k),      movePrev)
        , ((0, xK_j),      moveNext)
        , ((0, xK_h),      moveParent)
        , ((0, xK_l),      moveChild)
        , ((0, xK_o),      moveHistBack)
        , ((0, xK_i),      moveHistForward)
        ]

defaultNavigation :: Map (KeyMask, KeySym) (TreeSelect a (Maybe a)) #

Default navigation

- navigation using either arrow key or vi style hjkl
- Return or Space to confirm
- Escape or Backspace to cancel to

select :: TreeSelect a (Maybe a) #

Quit returning the currently selected node

cancel :: TreeSelect a (Maybe a) #

Quit without returning anything

moveParent :: TreeSelect a (Maybe a) #

Move the cursor to its parent node

moveChild :: TreeSelect a (Maybe a) #

Move the cursor one level down, highlighting its first child-node

moveNext :: TreeSelect a (Maybe a) #

Move the cursor to the next child-node

movePrev :: TreeSelect a (Maybe a) #

Move the cursor to the previous child-node

moveHistBack :: TreeSelect a (Maybe a) #

Move backwards in history

moveHistForward :: TreeSelect a (Maybe a) #

Move forward in history

moveTo #

Arguments

:: [String] | path, always starting from the top
-> TreeSelect a (Maybe a) |

Move to a specific node

# Advanced usage

This module can also be used to select any other action

data TSNode a #

Tree Node With a name and extra text

Constructors

TSNode |
Fields tsn_name :: String tsn_extra :: String extra text, displayed next to the node name tsn_value :: a value to return when this node is selected

treeselect #

Arguments

:: TSConfig a | config file
-> Forest (TSNode a) | a list of `Tree`s to select from.
-> X (Maybe a) |

Run Treeselect with a given config and tree. This can be used for selectiong anything

- for switching workspaces and moving windows use `treeselectWorkspace`
- for selecting actions use `treeselectAction`

treeselectAt #

Arguments

:: TSConfig a | config file
-> TreeZipper (TSNode a) | tree structure with a cursor position (starting node)
-> [[String]] | list of paths that can be navigated with `moveHistBack` and `moveHistForward` (bound to the `o` and `i` keys)
-> X (Maybe a) |

Same as `treeselect` but ad a specific starting position