    -----------------------------------------------------------------------------
    -- |
    -- Module       : XMonad.Actions.TagWindows
    -- Description  : Functions for tagging windows and selecting them by tags.
    -- Copyright    : (c) Karsten Schoelzel <kuser@gmx.de>
    -- License      : BSD
    --
    -- Maintainer   : Karsten Schoelzel <kuser@gmx.de>
    -- Stability    : unstable
    -- Portability  : unportable
    --
    -- Functions for tagging windows and selecting them by tags.
    -----------------------------------------------------------------------------

    module XMonad.Actions.TagWindows (
                     -- * Usage
                     -- $usage
                     addTag, delTag, unTag,
                     setTags, getTags, hasTag,
                     withTaggedP,  withTaggedGlobalP, withFocusedP,
                     withTagged ,  withTaggedGlobal ,
                     focusUpTagged,   focusUpTaggedGlobal,
                     focusDownTagged, focusDownTaggedGlobal,
                     shiftHere, shiftToScreen,
                     tagPrompt,
                     tagDelPrompt,
                     TagPrompt,
                     ) where

    import Control.Exception as E

    import XMonad hiding (workspaces)
    import XMonad.Prelude
    import XMonad.Prompt
    import XMonad.StackSet hiding (filter)

    econst :: Monad m => a -> IOException -> m a
    econst :: forall (m :: * -> *) a. Monad m => a -> IOException -> m a
    econst = m a -> IOException -> m a
    forall a b. a -> b -> a
    const (m a -> IOException -> m a)
    -> (a -> m a) -> a -> IOException -> m a
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . a -> m a
    forall a. a -> m a
    forall (m :: * -> *) a. Monad m => a -> m a
    return

    -- $usage
    --
    -- To use window tags, import this module into your @xmonad.hs@:
    --
    -- > import XMonad.Actions.TagWindows
    -- > import XMonad.Prompt    -- to use tagPrompt
    --
    -- and add keybindings such as the following:
    --
    -- >   , ((modm,                 xK_f  ), withFocused (addTag "abc"))
    -- >   , ((modm .|. controlMask, xK_f  ), withFocused (delTag "abc"))
    -- >   , ((modm .|. shiftMask,   xK_f  ), withTaggedGlobalP "abc" W.sink)
    -- >   , ((modm,                 xK_d  ), withTaggedP "abc" (W.shiftWin "2"))
    -- >   , ((modm .|. shiftMask,   xK_d  ), withTaggedGlobalP "abc" shiftHere)
    -- >   , ((modm .|. controlMask, xK_d  ), focusUpTaggedGlobal "abc")
    -- >   , ((modm,                 xK_g  ), tagPrompt def (\s -> withFocused (addTag s)))
    -- >   , ((modm .|. controlMask, xK_g  ), tagDelPrompt def)
    -- >   , ((modm .|. shiftMask,   xK_g  ), tagPrompt def (\s -> withTaggedGlobal s float))
    -- >   , ((modWinMask,                xK_g  ), tagPrompt def (\s -> withTaggedP s (W.shiftWin "2")))
    -- >   , ((modWinMask .|. shiftMask,  xK_g  ), tagPrompt def (\s -> withTaggedGlobalP s shiftHere))
    -- >   , ((modWinMask .|. controlMask, xK_g ), tagPrompt def (\s -> focusUpTaggedGlobal s))
    --
    -- NOTE: Tags are saved as space separated strings and split with
    --       'unwords'. Thus if you add a tag \"a b\" the window will have
    --       the tags \"a\" and \"b\" but not \"a b\".
    --
    -- For detailed instructions on editing your key bindings, see
    -- <https://xmonad.org/TUTORIAL.html#customizing-xmonad the tutorial>.

    -- | set multiple tags for a window at once (overriding any previous tags)
    setTags :: [String] -> Window -> X ()
    setTags :: [String] -> Window -> X ()
    setTags = String -> Window -> X ()
    setTag (String -> Window -> X ())
    -> ([String] -> String) -> [String] -> Window -> X ()
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . [String] -> String
    unwords

    -- | set a tag for a window (overriding any previous tags)
    --   writes it to the \"_XMONAD_TAGS\" window property
    setTag :: String -> Window -> X ()
    setTag :: String -> Window -> X ()
    setTag String
    s Window
    w = (Display -> X ()) -> X ()
    forall a. (Display -> X a) -> X a
    withDisplay ((Display -> X ()) -> X ()) -> (Display -> X ()) -> X ()
    forall a b. (a -> b) -> a -> b
    $ \Display
    d ->
        IO () -> X ()
    forall (m :: * -> *) a. MonadIO m => IO a -> m a
    io (IO () -> X ()) -> IO () -> X ()
    forall a b. (a -> b) -> a -> b
    $ Display -> String -> Bool -> IO Window
    internAtom Display
    d String
    "_XMONAD_TAGS" Bool
    False IO Window -> (Window -> IO ()) -> IO ()
    forall a b. IO a -> (a -> IO b) -> IO b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= Display -> Window -> String -> Window -> IO ()
    setTextProperty Display
    d Window
    w String
    s

    -- | read all tags of a window
    --   reads from the \"_XMONAD_TAGS\" window property
    getTags :: Window -> X [String]
    getTags :: Window -> X [String]
    getTags Window
    w = (Display -> X [String]) -> X [String]
    forall a. (Display -> X a) -> X a
    withDisplay ((Display -> X [String]) -> X [String])
    -> (Display -> X [String]) -> X [String]
    forall a b. (a -> b) -> a -> b
    $ \Display
    d ->
        IO [String] -> X [String]
    forall (m :: * -> *) a. MonadIO m => IO a -> m a
    io (IO [String] -> X [String]) -> IO [String] -> X [String]
    forall a b. (a -> b) -> a -> b
    $ IO [String] -> (IOException -> IO [String]) -> IO [String]
    forall e a. Exception e => IO a -> (e -> IO a) -> IO a
    E.catch (Display -> String -> Bool -> IO Window
    internAtom Display
    d String
    "_XMONAD_TAGS" Bool
    False IO Window -> (Window -> IO TextProperty) -> IO TextProperty
    forall a b. IO a -> (a -> IO b) -> IO b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>=
                    Display -> Window -> Window -> IO TextProperty
    getTextProperty Display
    d Window
    w IO TextProperty -> (TextProperty -> IO [String]) -> IO [String]
    forall a b. IO a -> (a -> IO b) -> IO b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>=
                    Display -> TextProperty -> IO [String]
    wcTextPropertyToTextList Display
    d)
                   ([String] -> IOException -> IO [String]
    forall (m :: * -> *) a. Monad m => a -> IOException -> m a
    econst [[]]) IO [String] -> ([String] -> [String]) -> IO [String]
    forall (f :: * -> *) a b. Functor f => f a -> (a -> b) -> f b
    <&> (String -> [String]
    words (String -> [String])
    -> ([String] -> String) -> [String] -> [String]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . [String] -> String
    unwords)

    -- | check a window for the given tag
    hasTag :: String -> Window -> X Bool
    hasTag :: String -> Window -> X Bool
    hasTag String
    s Window
    w = (String
    s String -> [String] -> Bool
    forall a. Eq a => a -> [a] -> Bool
    forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
    `elem`) ([String] -> Bool) -> X [String] -> X Bool
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Window -> X [String]
    getTags Window
    w

    -- | add a tag to the existing ones
    addTag :: String -> Window -> X ()
    addTag :: String -> Window -> X ()
    addTag String
    s Window
    w = do
        [String]
    tags <- Window -> X [String]
    getTags Window
    w
        Bool -> X () -> X ()
    forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
    when (String
    s String -> [String] -> Bool
    forall (t :: * -> *) a. (Foldable t, Eq a) => a -> t a -> Bool
    `notElem` [String]
    tags) (X () -> X ()) -> X () -> X ()
    forall a b. (a -> b) -> a -> b
    $ [String] -> Window -> X ()
    setTags (String
    sString -> [String] -> [String]
    forall a. a -> [a] -> [a]
    :[String]
    tags) Window
    w

    -- | remove a tag from a window, if it exists
    delTag :: String -> Window -> X ()
    delTag :: String -> Window -> X ()
    delTag String
    s Window
    w = do
        [String]
    tags <- Window -> X [String]
    getTags Window
    w
        [String] -> Window -> X ()
    setTags ((String -> Bool) -> [String] -> [String]
    forall a. (a -> Bool) -> [a] -> [a]
    filter (String -> String -> Bool
    forall a. Eq a => a -> a -> Bool
    /= String
    s) [String]
    tags) Window
    w

    -- | remove all tags
    unTag :: Window -> X ()
    unTag :: Window -> X ()
    unTag = String -> Window -> X ()
    setTag String
    ""

    -- | Move the focus in a group of windows, which share the same given tag.
    --   The Global variants move through all workspaces, whereas the other
    --   ones operate only on the current workspace
    focusUpTagged, focusDownTagged, focusUpTaggedGlobal, focusDownTaggedGlobal :: String -> X ()
    focusUpTagged :: String -> X ()
    focusUpTagged         = (WindowSet -> [Window]) -> String -> X ()
    focusTagged' ([Window] -> [Window]
    forall a. [a] -> [a]
    reverse ([Window] -> [Window])
    -> (WindowSet -> [Window]) -> WindowSet -> [Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . WindowSet -> [Window]
    forall i l a s sd. Ord i => StackSet i l a s sd -> [a]
    wsToList)
    focusDownTagged :: String -> X ()
    focusDownTagged       = (WindowSet -> [Window]) -> String -> X ()
    focusTagged' WindowSet -> [Window]
    forall i l a s sd. Ord i => StackSet i l a s sd -> [a]
    wsToList
    focusUpTaggedGlobal :: String -> X ()
    focusUpTaggedGlobal   = (WindowSet -> [Window]) -> String -> X ()
    focusTagged' ([Window] -> [Window]
    forall a. [a] -> [a]
    reverse ([Window] -> [Window])
    -> (WindowSet -> [Window]) -> WindowSet -> [Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . WindowSet -> [Window]
    forall i l a s sd. Ord i => StackSet i l a s sd -> [a]
    wsToListGlobal)
    focusDownTaggedGlobal :: String -> X ()
    focusDownTaggedGlobal = (WindowSet -> [Window]) -> String -> X ()
    focusTagged' WindowSet -> [Window]
    forall i l a s sd. Ord i => StackSet i l a s sd -> [a]
    wsToListGlobal

    wsToList :: (Ord i) => StackSet i l a s sd -> [a]
    wsToList :: forall i l a s sd. Ord i => StackSet i l a s sd -> [a]
    wsToList StackSet i l a s sd
    ws = [a]
    crs [a] -> [a] -> [a]
    forall a. [a] -> [a] -> [a]
    ++ [a]
    cls
        where
            ([a]
    crs, [a]
    cls) = ((Stack a -> [a]) -> [a]
    forall {a}. (Stack a -> [a]) -> [a]
    cms Stack a -> [a]
    forall a. Stack a -> [a]
    down, (Stack a -> [a]) -> [a]
    forall {a}. (Stack a -> [a]) -> [a]
    cms ([a] -> [a]
    forall a. [a] -> [a]
    reverse ([a] -> [a]) -> (Stack a -> [a]) -> Stack a -> [a]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Stack a -> [a]
    forall a. Stack a -> [a]
    up))
            cms :: (Stack a -> [a]) -> [a]
    cms Stack a -> [a]
    f = [a] -> (Stack a -> [a]) -> Maybe (Stack a) -> [a]
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe [] Stack a -> [a]
    f (Workspace i l a -> Maybe (Stack a)
    forall i l a. Workspace i l a -> Maybe (Stack a)
    stack (Workspace i l a -> Maybe (Stack a))
    -> (StackSet i l a s sd -> Workspace i l a)
    -> StackSet i l a s sd
    -> Maybe (Stack a)
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Screen i l a s sd -> Workspace i l a
    forall i l a sid sd. Screen i l a sid sd -> Workspace i l a
    workspace (Screen i l a s sd -> Workspace i l a)
    -> (StackSet i l a s sd -> Screen i l a s sd)
    -> StackSet i l a s sd
    -> Workspace i l a
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . StackSet i l a s sd -> Screen i l a s sd
    forall i l a sid sd. StackSet i l a sid sd -> Screen i l a sid sd
    current (StackSet i l a s sd -> Maybe (Stack a))
    -> StackSet i l a s sd -> Maybe (Stack a)
    forall a b. (a -> b) -> a -> b
    $ StackSet i l a s sd
    ws)

    wsToListGlobal :: (Ord i) => StackSet i l a s sd -> [a]
    wsToListGlobal :: forall i l a s sd. Ord i => StackSet i l a s sd -> [a]
    wsToListGlobal StackSet i l a s sd
    ws = [[a]] -> [a]
    forall (t :: * -> *) a. Foldable t => t [a] -> [a]
    concat ([[a]
    crs] [[a]] -> [[a]] -> [[a]]
    forall a. [a] -> [a] -> [a]
    ++ [[a]]
    rws [[a]] -> [[a]] -> [[a]]
    forall a. [a] -> [a] -> [a]
    ++ [[a]]
    lws [[a]] -> [[a]] -> [[a]]
    forall a. [a] -> [a] -> [a]
    ++ [[a]
    cls])
        where
            curtag :: i
    curtag = StackSet i l a s sd -> i
    forall i l a s sd. StackSet i l a s sd -> i
    currentTag StackSet i l a s sd
    ws
            ([a]
    crs, [a]
    cls) = ((Stack a -> [a]) -> [a]
    forall {a}. (Stack a -> [a]) -> [a]
    cms Stack a -> [a]
    forall a. Stack a -> [a]
    down, (Stack a -> [a]) -> [a]
    forall {a}. (Stack a -> [a]) -> [a]
    cms ([a] -> [a]
    forall a. [a] -> [a]
    reverse ([a] -> [a]) -> (Stack a -> [a]) -> Stack a -> [a]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Stack a -> [a]
    forall a. Stack a -> [a]
    up))
            cms :: (Stack a -> [a]) -> [a]
    cms Stack a -> [a]
    f = [a] -> (Stack a -> [a]) -> Maybe (Stack a) -> [a]
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe [] Stack a -> [a]
    f (Workspace i l a -> Maybe (Stack a)
    forall i l a. Workspace i l a -> Maybe (Stack a)
    stack (Workspace i l a -> Maybe (Stack a))
    -> (StackSet i l a s sd -> Workspace i l a)
    -> StackSet i l a s sd
    -> Maybe (Stack a)
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Screen i l a s sd -> Workspace i l a
    forall i l a sid sd. Screen i l a sid sd -> Workspace i l a
    workspace (Screen i l a s sd -> Workspace i l a)
    -> (StackSet i l a s sd -> Screen i l a s sd)
    -> StackSet i l a s sd
    -> Workspace i l a
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . StackSet i l a s sd -> Screen i l a s sd
    forall i l a sid sd. StackSet i l a sid sd -> Screen i l a sid sd
    current (StackSet i l a s sd -> Maybe (Stack a))
    -> StackSet i l a s sd -> Maybe (Stack a)
    forall a b. (a -> b) -> a -> b
    $ StackSet i l a s sd
    ws)
            ([[a]]
    lws, [[a]]
    rws) = ((i -> i -> Bool) -> [[a]]
    mws i -> i -> Bool
    forall a. Ord a => a -> a -> Bool
    (<), (i -> i -> Bool) -> [[a]]
    mws i -> i -> Bool
    forall a. Ord a => a -> a -> Bool
    (>))
            mws :: (i -> i -> Bool) -> [[a]]
    mws i -> i -> Bool
    cmp = (Workspace i l a -> [a]) -> [Workspace i l a] -> [[a]]
    forall a b. (a -> b) -> [a] -> [b]
    map (Maybe (Stack a) -> [a]
    forall a. Maybe (Stack a) -> [a]
    integrate' (Maybe (Stack a) -> [a])
    -> (Workspace i l a -> Maybe (Stack a)) -> Workspace i l a -> [a]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Workspace i l a -> Maybe (Stack a)
    forall i l a. Workspace i l a -> Maybe (Stack a)
    stack) ([Workspace i l a] -> [[a]])
    -> (StackSet i l a s sd -> [Workspace i l a])
    -> StackSet i l a s sd
    -> [[a]]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . [Workspace i l a] -> [Workspace i l a]
    forall {l} {a}. [Workspace i l a] -> [Workspace i l a]
    sortByTag ([Workspace i l a] -> [Workspace i l a])
    -> (StackSet i l a s sd -> [Workspace i l a])
    -> StackSet i l a s sd
    -> [Workspace i l a]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . (Workspace i l a -> Bool) -> [Workspace i l a] -> [Workspace i l a]
    forall a. (a -> Bool) -> [a] -> [a]
    filter (\Workspace i l a
    w -> Workspace i l a -> i
    forall i l a. Workspace i l a -> i
    tag Workspace i l a
    w i -> i -> Bool
    `cmp` i
    curtag) ([Workspace i l a] -> [Workspace i l a])
    -> (StackSet i l a s sd -> [Workspace i l a])
    -> StackSet i l a s sd
    -> [Workspace i l a]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . StackSet i l a s sd -> [Workspace i l a]
    forall i l a s sd. StackSet i l a s sd -> [Workspace i l a]
    workspaces (StackSet i l a s sd -> [[a]]) -> StackSet i l a s sd -> [[a]]
    forall a b. (a -> b) -> a -> b
    $ StackSet i l a s sd
    ws
            sortByTag :: [Workspace i l a] -> [Workspace i l a]
    sortByTag = (Workspace i l a -> Workspace i l a -> Ordering)
    -> [Workspace i l a] -> [Workspace i l a]
    forall a. (a -> a -> Ordering) -> [a] -> [a]
    sortBy (\Workspace i l a
    x Workspace i l a
    y -> i -> i -> Ordering
    forall a. Ord a => a -> a -> Ordering
    compare (Workspace i l a -> i
    forall i l a. Workspace i l a -> i
    tag Workspace i l a
    x) (Workspace i l a -> i
    forall i l a. Workspace i l a -> i
    tag Workspace i l a
    y))

    focusTagged' :: (WindowSet -> [Window]) -> String -> X ()
    focusTagged' :: (WindowSet -> [Window]) -> String -> X ()
    focusTagged' WindowSet -> [Window]
    wl String
    t = (XState -> WindowSet) -> X WindowSet
    forall s (m :: * -> *) a. MonadState s m => (s -> a) -> m a
    gets XState -> WindowSet
    windowset X WindowSet -> (WindowSet -> X (Maybe Window)) -> X (Maybe Window)
    forall a b. X a -> (a -> X b) -> X b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= (Window -> X Bool) -> [Window] -> X (Maybe Window)
    forall (m :: * -> *) a.
    Monad m =>
    (a -> m Bool) -> [a] -> m (Maybe a)
    findM (String -> Window -> X Bool
    hasTag String
    t) ([Window] -> X (Maybe Window))
    -> (WindowSet -> [Window]) -> WindowSet -> X (Maybe Window)
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . WindowSet -> [Window]
    wl X (Maybe Window) -> (Maybe Window -> X ()) -> X ()
    forall a b. X a -> (a -> X b) -> X b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>=
        X () -> (Window -> X ()) -> Maybe Window -> X ()
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe (() -> X ()
    forall a. a -> X a
    forall (m :: * -> *) a. Monad m => a -> m a
    return ()) ((WindowSet -> WindowSet) -> X ()
    windows ((WindowSet -> WindowSet) -> X ())
    -> (Window -> WindowSet -> WindowSet) -> Window -> X ()
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Window -> WindowSet -> WindowSet
    forall s a i l sd.
    (Eq s, Eq a, Eq i) =>
    a -> StackSet i l a s sd -> StackSet i l a s sd
    focusWindow)

    -- | apply a pure function to windows with a tag
    withTaggedP, withTaggedGlobalP :: String -> (Window -> WindowSet -> WindowSet) -> X ()
    withTaggedP :: String -> (Window -> WindowSet -> WindowSet) -> X ()
    withTaggedP       String
    t Window -> WindowSet -> WindowSet
    f = String -> ([Window] -> X ()) -> X ()
    withTagged'       String
    t ((Window -> WindowSet -> WindowSet) -> [Window] -> X ()
    winMap Window -> WindowSet -> WindowSet
    f)
    withTaggedGlobalP :: String -> (Window -> WindowSet -> WindowSet) -> X ()
    withTaggedGlobalP String
    t Window -> WindowSet -> WindowSet
    f = String -> ([Window] -> X ()) -> X ()
    withTaggedGlobal' String
    t ((Window -> WindowSet -> WindowSet) -> [Window] -> X ()
    winMap Window -> WindowSet -> WindowSet
    f)

    winMap :: (Window -> WindowSet -> WindowSet) -> [Window] -> X ()
    winMap :: (Window -> WindowSet -> WindowSet) -> [Window] -> X ()
    winMap Window -> WindowSet -> WindowSet
    f [Window]
    tw = Bool -> X () -> X ()
    forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
    when ([Window]
    tw [Window] -> [Window] -> Bool
    forall a. Eq a => a -> a -> Bool
    /= []) ((WindowSet -> WindowSet) -> X ()
    windows ((WindowSet -> WindowSet) -> X ())
    -> (WindowSet -> WindowSet) -> X ()
    forall a b. (a -> b) -> a -> b
    $ ((WindowSet -> WindowSet)
     -> (WindowSet -> WindowSet) -> WindowSet -> WindowSet)
    -> [WindowSet -> WindowSet] -> WindowSet -> WindowSet
    forall a. (a -> a -> a) -> [a] -> a
    forall (t :: * -> *) a. Foldable t => (a -> a -> a) -> t a -> a
    foldl1 (WindowSet -> WindowSet)
    -> (WindowSet -> WindowSet) -> WindowSet -> WindowSet
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    (.) ((Window -> WindowSet -> WindowSet)
    -> [Window] -> [WindowSet -> WindowSet]
    forall a b. (a -> b) -> [a] -> [b]
    map Window -> WindowSet -> WindowSet
    f [Window]
    tw))

    withTagged, withTaggedGlobal :: String -> (Window -> X ()) -> X ()
    withTagged :: String -> (Window -> X ()) -> X ()
    withTagged       String
    t Window -> X ()
    f = String -> ([Window] -> X ()) -> X ()
    withTagged'       String
    t ((Window -> X ()) -> [Window] -> X ()
    forall (t :: * -> *) (m :: * -> *) a b.
    (Foldable t, Monad m) =>
    (a -> m b) -> t a -> m ()
    mapM_ Window -> X ()
    f)
    withTaggedGlobal :: String -> (Window -> X ()) -> X ()
    withTaggedGlobal String
    t Window -> X ()
    f = String -> ([Window] -> X ()) -> X ()
    withTaggedGlobal' String
    t ((Window -> X ()) -> [Window] -> X ()
    forall (t :: * -> *) (m :: * -> *) a b.
    (Foldable t, Monad m) =>
    (a -> m b) -> t a -> m ()
    mapM_ Window -> X ()
    f)

    withTagged' :: String -> ([Window] -> X ()) -> X ()
    withTagged' :: String -> ([Window] -> X ()) -> X ()
    withTagged' String
    t [Window] -> X ()
    m = (XState -> WindowSet) -> X WindowSet
    forall s (m :: * -> *) a. MonadState s m => (s -> a) -> m a
    gets XState -> WindowSet
    windowset X WindowSet -> (WindowSet -> X [Window]) -> X [Window]
    forall a b. X a -> (a -> X b) -> X b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= (Window -> X Bool) -> [Window] -> X [Window]
    forall (m :: * -> *) a.
    Applicative m =>
    (a -> m Bool) -> [a] -> m [a]
    filterM (String -> Window -> X Bool
    hasTag String
    t) ([Window] -> X [Window])
    -> (WindowSet -> [Window]) -> WindowSet -> X [Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . WindowSet -> [Window]
    forall i l a s sd. StackSet i l a s sd -> [a]
    index X [Window] -> ([Window] -> X ()) -> X ()
    forall a b. X a -> (a -> X b) -> X b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= [Window] -> X ()
    m

    withTaggedGlobal' :: String -> ([Window] -> X ()) -> X ()
    withTaggedGlobal' :: String -> ([Window] -> X ()) -> X ()
    withTaggedGlobal' String
    t [Window] -> X ()
    m = (XState -> WindowSet) -> X WindowSet
    forall s (m :: * -> *) a. MonadState s m => (s -> a) -> m a
    gets XState -> WindowSet
    windowset X WindowSet -> (WindowSet -> X [Window]) -> X [Window]
    forall a b. X a -> (a -> X b) -> X b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>=
        (Window -> X Bool) -> [Window] -> X [Window]
    forall (m :: * -> *) a.
    Applicative m =>
    (a -> m Bool) -> [a] -> m [a]
    filterM (String -> Window -> X Bool
    hasTag String
    t) ([Window] -> X [Window])
    -> (WindowSet -> [Window]) -> WindowSet -> X [Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . (Workspace String (Layout Window) Window -> [Window])
    -> [Workspace String (Layout Window) Window] -> [Window]
    forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
    concatMap (Maybe (Stack Window) -> [Window]
    forall a. Maybe (Stack a) -> [a]
    integrate' (Maybe (Stack Window) -> [Window])
    -> (Workspace String (Layout Window) Window
        -> Maybe (Stack Window))
    -> Workspace String (Layout Window) Window
    -> [Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Workspace String (Layout Window) Window -> Maybe (Stack Window)
    forall i l a. Workspace i l a -> Maybe (Stack a)
    stack) ([Workspace String (Layout Window) Window] -> [Window])
    -> (WindowSet -> [Workspace String (Layout Window) Window])
    -> WindowSet
    -> [Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . WindowSet -> [Workspace String (Layout Window) Window]
    forall i l a s sd. StackSet i l a s sd -> [Workspace i l a]
    workspaces X [Window] -> ([Window] -> X ()) -> X ()
    forall a b. X a -> (a -> X b) -> X b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= [Window] -> X ()
    m

    withFocusedP :: (Window -> WindowSet -> WindowSet) -> X ()
    withFocusedP :: (Window -> WindowSet -> WindowSet) -> X ()
    withFocusedP Window -> WindowSet -> WindowSet
    f = (Window -> X ()) -> X ()
    withFocused ((Window -> X ()) -> X ()) -> (Window -> X ()) -> X ()
    forall a b. (a -> b) -> a -> b
    $ (WindowSet -> WindowSet) -> X ()
    windows ((WindowSet -> WindowSet) -> X ())
    -> (Window -> WindowSet -> WindowSet) -> Window -> X ()
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Window -> WindowSet -> WindowSet
    f

    shiftHere :: (Ord a, Eq s, Eq i) => a -> StackSet i l a s sd -> StackSet i l a s sd
    shiftHere :: forall a s i l sd.
    (Ord a, Eq s, Eq i) =>
    a -> StackSet i l a s sd -> StackSet i l a s sd
    shiftHere a
    w StackSet i l a s sd
    s = i -> a -> StackSet i l a s sd -> StackSet i l a s sd
    forall a s i l sd.
    (Ord a, Eq s, Eq i) =>
    i -> a -> StackSet i l a s sd -> StackSet i l a s sd
    shiftWin (StackSet i l a s sd -> i
    forall i l a s sd. StackSet i l a s sd -> i
    currentTag StackSet i l a s sd
    s) a
    w StackSet i l a s sd
    s

    shiftToScreen :: (Ord a, Eq s, Eq i) => s -> a -> StackSet i l a s sd -> StackSet i l a s sd
    shiftToScreen :: forall a s i l sd.
    (Ord a, Eq s, Eq i) =>
    s -> a -> StackSet i l a s sd -> StackSet i l a s sd
    shiftToScreen s
    sid a
    w StackSet i l a s sd
    s = case (Screen i l a s sd -> Bool)
    -> [Screen i l a s sd] -> [Screen i l a s sd]
    forall a. (a -> Bool) -> [a] -> [a]
    filter (\Screen i l a s sd
    m -> s
    sid s -> s -> Bool
    forall a. Eq a => a -> a -> Bool
    /= Screen i l a s sd -> s
    forall i l a sid sd. Screen i l a sid sd -> sid
    screen Screen i l a s sd
    m) (StackSet i l a s sd -> Screen i l a s sd
    forall i l a sid sd. StackSet i l a sid sd -> Screen i l a sid sd
    current StackSet i l a s sd
    sScreen i l a s sd -> [Screen i l a s sd] -> [Screen i l a s sd]
    forall a. a -> [a] -> [a]
    :StackSet i l a s sd -> [Screen i l a s sd]
    forall i l a sid sd. StackSet i l a sid sd -> [Screen i l a sid sd]
    visible StackSet i l a s sd
    s) of
                                    []      -> StackSet i l a s sd
    s
                                    (Screen i l a s sd
    t:[Screen i l a s sd]
    _)   -> i -> a -> StackSet i l a s sd -> StackSet i l a s sd
    forall a s i l sd.
    (Ord a, Eq s, Eq i) =>
    i -> a -> StackSet i l a s sd -> StackSet i l a s sd
    shiftWin (Workspace i l a -> i
    forall i l a. Workspace i l a -> i
    tag (Workspace i l a -> i)
    -> (Screen i l a s sd -> Workspace i l a) -> Screen i l a s sd -> i
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Screen i l a s sd -> Workspace i l a
    forall i l a sid sd. Screen i l a sid sd -> Workspace i l a
    workspace (Screen i l a s sd -> i) -> Screen i l a s sd -> i
    forall a b. (a -> b) -> a -> b
    $ Screen i l a s sd
    t) a
    w StackSet i l a s sd
    s

    data TagPrompt = TagPrompt

    instance XPrompt TagPrompt where
        showXPrompt :: TagPrompt -> String
    showXPrompt TagPrompt
    TagPrompt = String
    "Select Tag:   "

    tagPrompt :: XPConfig -> (String -> X ()) -> X ()
    tagPrompt :: XPConfig -> (String -> X ()) -> X ()
    tagPrompt XPConfig
    c String -> X ()
    f = do
      [String]
    sc <- X [String]
    tagComplList
      TagPrompt -> XPConfig -> ComplFunction -> (String -> X ()) -> X ()
    forall p.
    XPrompt p =>
    p -> XPConfig -> ComplFunction -> (String -> X ()) -> X ()
    mkXPrompt TagPrompt
    TagPrompt XPConfig
    c (XPConfig -> [String] -> ComplFunction
    mkComplFunFromList' XPConfig
    c [String]
    sc) String -> X ()
    f

    tagComplList :: X [String]
    tagComplList :: X [String]
    tagComplList = (XState -> [Window]) -> X [Window]
    forall s (m :: * -> *) a. MonadState s m => (s -> a) -> m a
    gets ((Workspace String (Layout Window) Window -> [Window])
    -> [Workspace String (Layout Window) Window] -> [Window]
    forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
    concatMap (Maybe (Stack Window) -> [Window]
    forall a. Maybe (Stack a) -> [a]
    integrate' (Maybe (Stack Window) -> [Window])
    -> (Workspace String (Layout Window) Window
        -> Maybe (Stack Window))
    -> Workspace String (Layout Window) Window
    -> [Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Workspace String (Layout Window) Window -> Maybe (Stack Window)
    forall i l a. Workspace i l a -> Maybe (Stack a)
    stack) ([Workspace String (Layout Window) Window] -> [Window])
    -> (XState -> [Workspace String (Layout Window) Window])
    -> XState
    -> [Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . WindowSet -> [Workspace String (Layout Window) Window]
    forall i l a s sd. StackSet i l a s sd -> [Workspace i l a]
    workspaces (WindowSet -> [Workspace String (Layout Window) Window])
    -> (XState -> WindowSet)
    -> XState
    -> [Workspace String (Layout Window) Window]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . XState -> WindowSet
    windowset)
               X [Window] -> ([Window] -> X [[String]]) -> X [[String]]
    forall a b. X a -> (a -> X b) -> X b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= (Window -> X [String]) -> [Window] -> X [[String]]
    forall (t :: * -> *) (m :: * -> *) a b.
    (Traversable t, Monad m) =>
    (a -> m b) -> t a -> m (t b)
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> [a] -> m [b]
    mapM Window -> X [String]
    getTags
               X [[String]] -> ([[String]] -> [String]) -> X [String]
    forall (f :: * -> *) a b. Functor f => f a -> (a -> b) -> f b
    <&> [String] -> [String]
    forall a. Eq a => [a] -> [a]
    nub ([String] -> [String])
    -> ([[String]] -> [String]) -> [[String]] -> [String]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . [[String]] -> [String]
    forall (t :: * -> *) a. Foldable t => t [a] -> [a]
    concat

    tagDelPrompt :: XPConfig -> X ()
    tagDelPrompt :: XPConfig -> X ()
    tagDelPrompt XPConfig
    c = do
      [String]
    sc <- X [String]
    tagDelComplList
      Bool -> X () -> X ()
    forall (f :: * -> *). Applicative f => Bool -> f () -> f ()
    when ([String]
    sc [String] -> [String] -> Bool
    forall a. Eq a => a -> a -> Bool
    /= []) (X () -> X ()) -> X () -> X ()
    forall a b. (a -> b) -> a -> b
    $
        TagPrompt -> XPConfig -> ComplFunction -> (String -> X ()) -> X ()
    forall p.
    XPrompt p =>
    p -> XPConfig -> ComplFunction -> (String -> X ()) -> X ()
    mkXPrompt TagPrompt
    TagPrompt XPConfig
    c (XPConfig -> [String] -> ComplFunction
    mkComplFunFromList' XPConfig
    c [String]
    sc) ((Window -> X ()) -> X ()
    withFocused ((Window -> X ()) -> X ())
    -> (String -> Window -> X ()) -> String -> X ()
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . String -> Window -> X ()
    delTag)

    tagDelComplList :: X [String]
    tagDelComplList :: X [String]
    tagDelComplList = (XState -> WindowSet) -> X WindowSet
    forall s (m :: * -> *) a. MonadState s m => (s -> a) -> m a
    gets XState -> WindowSet
    windowset X WindowSet -> (WindowSet -> X [String]) -> X [String]
    forall a b. X a -> (a -> X b) -> X b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= X [String] -> (Window -> X [String]) -> Maybe Window -> X [String]
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe ([String] -> X [String]
    forall a. a -> X a
    forall (m :: * -> *) a. Monad m => a -> m a
    return []) Window -> X [String]
    getTags (Maybe Window -> X [String])
    -> (WindowSet -> Maybe Window) -> WindowSet -> X [String]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . WindowSet -> Maybe Window
    forall i l a s sd. StackSet i l a s sd -> Maybe a
    peek