From 426c931d5b0ebc6d53396c34ec38eb342be501c3 Mon Sep 17 00:00:00 2001 From: jao Date: Sun, 25 Nov 2018 07:35:54 +0000 Subject: Refactoring: Xmobar.Run --- src/lib/Xmobar.hs | 4 +- src/lib/Xmobar/Commands.hs | 72 ---------------------------- src/lib/Xmobar/Config.hs | 52 ++------------------ src/lib/Xmobar/Plugins/BufferedPipeReader.hs | 2 +- src/lib/Xmobar/Plugins/CommandReader.hs | 2 +- src/lib/Xmobar/Plugins/Date.hs | 2 +- src/lib/Xmobar/Plugins/DateZone.hs | 2 +- src/lib/Xmobar/Plugins/EWMH.hs | 2 +- src/lib/Xmobar/Plugins/Kbd.hs | 2 +- src/lib/Xmobar/Plugins/Locks.hs | 2 +- src/lib/Xmobar/Plugins/MBox.hs | 2 +- src/lib/Xmobar/Plugins/Mail.hs | 2 +- src/lib/Xmobar/Plugins/MarqueePipeReader.hs | 2 +- src/lib/Xmobar/Plugins/Monitors.hs | 2 +- src/lib/Xmobar/Plugins/PipeReader.hs | 2 +- src/lib/Xmobar/Plugins/StdinReader.hs | 2 +- src/lib/Xmobar/Plugins/XMonadLog.hs | 2 +- src/lib/Xmobar/Run/Commands.hs | 72 ++++++++++++++++++++++++++++ src/lib/Xmobar/Run/Runnable.hs | 60 +++++++++++++++++++++++ src/lib/Xmobar/Run/Runnable.hs-boot | 8 ++++ src/lib/Xmobar/Run/Template.hs | 65 +++++++++++++++++++++++++ src/lib/Xmobar/Run/Types.hs | 65 +++++++++++++++++++++++++ src/lib/Xmobar/Runnable.hs | 60 ----------------------- src/lib/Xmobar/Runnable.hs-boot | 8 ---- src/lib/Xmobar/Template.hs | 65 ------------------------- src/lib/Xmobar/X11/EventLoop.hs | 4 +- xmobar.cabal | 11 +++-- 27 files changed, 298 insertions(+), 276 deletions(-) delete mode 100644 src/lib/Xmobar/Commands.hs create mode 100644 src/lib/Xmobar/Run/Commands.hs create mode 100644 src/lib/Xmobar/Run/Runnable.hs create mode 100644 src/lib/Xmobar/Run/Runnable.hs-boot create mode 100644 src/lib/Xmobar/Run/Template.hs create mode 100644 src/lib/Xmobar/Run/Types.hs delete mode 100644 src/lib/Xmobar/Runnable.hs delete mode 100644 src/lib/Xmobar/Runnable.hs-boot delete mode 100644 src/lib/Xmobar/Template.hs diff --git a/src/lib/Xmobar.hs b/src/lib/Xmobar.hs index 897d671..f125a72 100644 --- a/src/lib/Xmobar.hs +++ b/src/lib/Xmobar.hs @@ -45,8 +45,8 @@ import Control.Concurrent.Async (Async, cancel) import Control.Exception (bracket) import Xmobar.Config -import Xmobar.Runnable -import Xmobar.Template +import Xmobar.Run.Runnable +import Xmobar.Run.Template import Xmobar.System.Signal (setupSignalHandler, withDeferSignals) import Xmobar.X11.Types import Xmobar.X11.EventLoop (startLoop, startCommand) diff --git a/src/lib/Xmobar/Commands.hs b/src/lib/Xmobar/Commands.hs deleted file mode 100644 index 5917bb8..0000000 --- a/src/lib/Xmobar/Commands.hs +++ /dev/null @@ -1,72 +0,0 @@ ------------------------------------------------------------------------------ --- | --- Module : Xmobar.Commands --- Copyright : (c) Andrea Rossato --- License : BSD-style (see LICENSE) --- --- Maintainer : Jose A. Ortega Ruiz --- Stability : unstable --- Portability : unportable --- --- The 'Exec' class and the 'Command' data type. --- --- The 'Exec' class rappresents the executable types, whose constructors may --- appear in the 'Config.commands' field of the 'Config.Config' data type. --- --- The 'Command' data type is for OS commands to be run by xmobar --- ------------------------------------------------------------------------------ - -module Xmobar.Commands (Command (..), Exec (..)) where - -import Prelude -import Control.Exception (handle, SomeException(..)) -import Data.Char -import System.Process -import System.Exit -import System.IO (hClose) - -import Xmobar.System.Signal -import Xmobar.Utils (hGetLineSafe, tenthSeconds) - -class Show e => Exec e where - alias :: e -> String - alias e = takeWhile (not . isSpace) $ show e - rate :: e -> Int - rate _ = 10 - run :: e -> IO String - run _ = return "" - start :: e -> (String -> IO ()) -> IO () - start e cb = go - where go = run e >>= cb >> tenthSeconds (rate e) >> go - trigger :: e -> (Maybe SignalType -> IO ()) -> IO () - trigger _ sh = sh Nothing - -data Command = Com Program Args Alias Rate - | ComX Program Args String Alias Rate - deriving (Show,Read,Eq) - -type Args = [String] -type Program = String -type Alias = String -type Rate = Int - -instance Exec Command where - alias (ComX p _ _ a _) = - if p /= "" then (if a == "" then p else a) else "" - alias (Com p a al r) = alias (ComX p a "" al r) - start (Com p as al r) cb = - start (ComX p as ("Could not execute command " ++ p) al r) cb - start (ComX prog args msg _ r) cb = if r > 0 then go else exec - where go = exec >> tenthSeconds r >> go - exec = do - (i,o,e,p) <- runInteractiveProcess prog args Nothing Nothing - exit <- waitForProcess p - let closeHandles = hClose o >> hClose i >> hClose e - getL = handle (\(SomeException _) -> return "") - (hGetLineSafe o) - case exit of - ExitSuccess -> do str <- getL - closeHandles - cb str - _ -> closeHandles >> cb msg diff --git a/src/lib/Xmobar/Config.hs b/src/lib/Xmobar/Config.hs index 364ce17..c38bd6f 100644 --- a/src/lib/Xmobar/Config.hs +++ b/src/lib/Xmobar/Config.hs @@ -1,5 +1,3 @@ -{-# LANGUAGE TypeOperators, CPP #-} - ----------------------------------------------------------------------------- -- | -- Module : Xmobar.Config @@ -20,36 +18,17 @@ module Xmobar.Config Config (..) , XPosition (..), Align (..), Border(..) , defaultConfig - , runnableTypes , getXdgConfigFile ) where -import System.Environment -import System.Directory (getHomeDirectory) -import System.FilePath (()) - -import Xmobar.Commands -import {-# SOURCE #-} Xmobar.Runnable -import Xmobar.Plugins.Monitors import Xmobar.Plugins.Date -import Xmobar.Plugins.PipeReader -import Xmobar.Plugins.BufferedPipeReader -import Xmobar.Plugins.MarqueePipeReader -import Xmobar.Plugins.CommandReader import Xmobar.Plugins.StdinReader -import Xmobar.Plugins.XMonadLog -import Xmobar.Plugins.EWMH -import Xmobar.Plugins.Kbd -import Xmobar.Plugins.Locks -#ifdef INOTIFY -import Xmobar.Plugins.Mail -import Xmobar.Plugins.MBox -#endif +import System.Environment +import System.Directory (getHomeDirectory) +import System.FilePath (()) -#ifdef DATEZONE -import Xmobar.Plugins.DateZone -#endif +import Xmobar.Run.Runnable (Runnable(..)) -- $config -- Configuration data type and default configuration @@ -150,29 +129,6 @@ defaultConfig = "%uname% * %theDate%" } - --- | An alias for tuple types that is more convenient for long lists. -type a :*: b = (a, b) -infixr :*: - --- | This is the list of types that can be hidden inside --- 'Runnable.Runnable', the existential type that stores all commands --- to be executed by Xmobar. It is used by 'Runnable.readRunnable' in --- the 'Runnable.Runnable' Read instance. To install a plugin just add --- the plugin's type to the list of types (separated by ':*:') appearing in --- this function's type signature. -runnableTypes :: Command :*: Monitors :*: Date :*: PipeReader :*: - BufferedPipeReader :*: CommandReader :*: StdinReader :*: - XMonadLog :*: EWMH :*: Kbd :*: Locks :*: -#ifdef INOTIFY - Mail :*: MBox :*: -#endif -#ifdef DATEZONE - DateZone :*: -#endif - MarqueePipeReader :*: () -runnableTypes = undefined - xdgConfigDir :: IO String xdgConfigDir = do env <- getEnvironment case lookup "XDG_CONFIG_HOME" env of diff --git a/src/lib/Xmobar/Plugins/BufferedPipeReader.hs b/src/lib/Xmobar/Plugins/BufferedPipeReader.hs index 0b55cf7..65ecea2 100644 --- a/src/lib/Xmobar/Plugins/BufferedPipeReader.hs +++ b/src/lib/Xmobar/Plugins/BufferedPipeReader.hs @@ -20,8 +20,8 @@ import Control.Concurrent.STM import System.IO import System.IO.Unsafe(unsafePerformIO) -import Xmobar.Commands import Xmobar.Utils(hGetLineSafe) +import Xmobar.Run.Commands import Xmobar.System.Signal import Xmobar.System.Environment diff --git a/src/lib/Xmobar/Plugins/CommandReader.hs b/src/lib/Xmobar/Plugins/CommandReader.hs index 4c71c96..69c8e0c 100644 --- a/src/lib/Xmobar/Plugins/CommandReader.hs +++ b/src/lib/Xmobar/Plugins/CommandReader.hs @@ -16,7 +16,7 @@ module Xmobar.Plugins.CommandReader(CommandReader(..)) where import System.IO -import Xmobar.Commands +import Xmobar.Run.Commands import Xmobar.Utils (hGetLineSafe) import System.Process(runInteractiveCommand, getProcessExitCode) diff --git a/src/lib/Xmobar/Plugins/Date.hs b/src/lib/Xmobar/Plugins/Date.hs index fd7acae..62a4ee7 100644 --- a/src/lib/Xmobar/Plugins/Date.hs +++ b/src/lib/Xmobar/Plugins/Date.hs @@ -19,7 +19,7 @@ module Xmobar.Plugins.Date (Date(..)) where -import Xmobar.Commands +import Xmobar.Run.Commands #if ! MIN_VERSION_time(1,5,0) import System.Locale diff --git a/src/lib/Xmobar/Plugins/DateZone.hs b/src/lib/Xmobar/Plugins/DateZone.hs index f3207c8..7215713 100644 --- a/src/lib/Xmobar/Plugins/DateZone.hs +++ b/src/lib/Xmobar/Plugins/DateZone.hs @@ -22,7 +22,7 @@ module Xmobar.Plugins.DateZone (DateZone(..)) where -import Xmobar.Commands +import Xmobar.Run.Commands import Xmobar.Utils(tenthSeconds) #ifdef DATEZONE diff --git a/src/lib/Xmobar/Plugins/EWMH.hs b/src/lib/Xmobar/Plugins/EWMH.hs index ab5dc32..4a443d6 100644 --- a/src/lib/Xmobar/Plugins/EWMH.hs +++ b/src/lib/Xmobar/Plugins/EWMH.hs @@ -22,7 +22,7 @@ import Control.Monad.State import Control.Monad.Reader import Graphics.X11 hiding (Modifier, Color) import Graphics.X11.Xlib.Extras -import Xmobar.Commands +import Xmobar.Run.Commands #ifdef UTF8 #undef UTF8 import Codec.Binary.UTF8.String as UTF8 diff --git a/src/lib/Xmobar/Plugins/Kbd.hs b/src/lib/Xmobar/Plugins/Kbd.hs index f8ad971..f4dad36 100644 --- a/src/lib/Xmobar/Plugins/Kbd.hs +++ b/src/lib/Xmobar/Plugins/Kbd.hs @@ -20,7 +20,7 @@ import Control.Monad (forever) import Graphics.X11.Xlib import Graphics.X11.Xlib.Extras -import Xmobar.Commands +import Xmobar.Run.Commands import Xmobar.Utils (nextEvent') import Xmobar.System.Kbd diff --git a/src/lib/Xmobar/Plugins/Locks.hs b/src/lib/Xmobar/Plugins/Locks.hs index 1f73f1f..19bce20 100644 --- a/src/lib/Xmobar/Plugins/Locks.hs +++ b/src/lib/Xmobar/Plugins/Locks.hs @@ -19,7 +19,7 @@ import Data.List import Data.Bits import Control.Monad import Graphics.X11.Xlib.Extras -import Xmobar.Commands +import Xmobar.Run.Commands import Xmobar.System.Kbd import Xmobar.Utils (nextEvent') diff --git a/src/lib/Xmobar/Plugins/MBox.hs b/src/lib/Xmobar/Plugins/MBox.hs index ba50207..4bd0ebd 100644 --- a/src/lib/Xmobar/Plugins/MBox.hs +++ b/src/lib/Xmobar/Plugins/MBox.hs @@ -16,7 +16,7 @@ module Xmobar.Plugins.MBox (MBox(..)) where import Prelude -import Xmobar.Commands +import Xmobar.Run.Commands #ifdef INOTIFY import Xmobar.Utils (changeLoop, expandHome) diff --git a/src/lib/Xmobar/Plugins/Mail.hs b/src/lib/Xmobar/Plugins/Mail.hs index aa28b98..d59e70d 100644 --- a/src/lib/Xmobar/Plugins/Mail.hs +++ b/src/lib/Xmobar/Plugins/Mail.hs @@ -15,7 +15,7 @@ module Xmobar.Plugins.Mail(Mail(..)) where -import Xmobar.Commands +import Xmobar.Run.Commands #ifdef INOTIFY import Xmobar.Utils (expandHome, changeLoop) diff --git a/src/lib/Xmobar/Plugins/MarqueePipeReader.hs b/src/lib/Xmobar/Plugins/MarqueePipeReader.hs index 3cce008..a48e81c 100644 --- a/src/lib/Xmobar/Plugins/MarqueePipeReader.hs +++ b/src/lib/Xmobar/Plugins/MarqueePipeReader.hs @@ -17,7 +17,7 @@ module Xmobar.Plugins.MarqueePipeReader where import System.IO (openFile, IOMode(ReadWriteMode), Handle) import Xmobar.System.Environment import Xmobar.Utils(tenthSeconds, hGetLineSafe) -import Xmobar.Commands(Exec(alias, start)) +import Xmobar.Run.Commands(Exec(alias, start)) import System.Posix.Files (getFileStatus, isNamedPipe) import Control.Concurrent(forkIO, threadDelay) import Control.Concurrent.STM (TChan, atomically, writeTChan, tryReadTChan, newTChan) diff --git a/src/lib/Xmobar/Plugins/Monitors.hs b/src/lib/Xmobar/Plugins/Monitors.hs index b263bd8..fe909d8 100644 --- a/src/lib/Xmobar/Plugins/Monitors.hs +++ b/src/lib/Xmobar/Plugins/Monitors.hs @@ -17,7 +17,7 @@ module Xmobar.Plugins.Monitors where -import Xmobar.Commands +import Xmobar.Run.Commands import Xmobar.Plugins.Monitors.Common (runM, runMD) #ifdef WEATHER diff --git a/src/lib/Xmobar/Plugins/PipeReader.hs b/src/lib/Xmobar/Plugins/PipeReader.hs index d04f747..f18b9cb 100644 --- a/src/lib/Xmobar/Plugins/PipeReader.hs +++ b/src/lib/Xmobar/Plugins/PipeReader.hs @@ -15,8 +15,8 @@ module Xmobar.Plugins.PipeReader(PipeReader(..)) where import System.IO -import Xmobar.Commands(Exec(..)) import Xmobar.Utils(hGetLineSafe) +import Xmobar.Run.Commands(Exec(..)) import Xmobar.System.Environment(expandEnv) import System.Posix.Files import Control.Concurrent(threadDelay) diff --git a/src/lib/Xmobar/Plugins/StdinReader.hs b/src/lib/Xmobar/Plugins/StdinReader.hs index ff96b2b..bed7f5c 100644 --- a/src/lib/Xmobar/Plugins/StdinReader.hs +++ b/src/lib/Xmobar/Plugins/StdinReader.hs @@ -23,9 +23,9 @@ import System.Posix.Process import System.Exit import System.IO import Control.Exception (SomeException(..), handle) -import Xmobar.Commands import Xmobar.Actions (stripActions) import Xmobar.Utils (hGetLineSafe) +import Xmobar.Run.Commands data StdinReader = StdinReader | UnsafeStdinReader deriving (Read, Show) diff --git a/src/lib/Xmobar/Plugins/XMonadLog.hs b/src/lib/Xmobar/Plugins/XMonadLog.hs index 908d2a4..a4f17bb 100644 --- a/src/lib/Xmobar/Plugins/XMonadLog.hs +++ b/src/lib/Xmobar/Plugins/XMonadLog.hs @@ -20,7 +20,7 @@ module Xmobar.Plugins.XMonadLog (XMonadLog(..)) where import Control.Monad import Graphics.X11 import Graphics.X11.Xlib.Extras -import Xmobar.Commands +import Xmobar.Run.Commands #ifdef UTF8 #undef UTF8 import Codec.Binary.UTF8.String as UTF8 diff --git a/src/lib/Xmobar/Run/Commands.hs b/src/lib/Xmobar/Run/Commands.hs new file mode 100644 index 0000000..198edee --- /dev/null +++ b/src/lib/Xmobar/Run/Commands.hs @@ -0,0 +1,72 @@ +----------------------------------------------------------------------------- +-- | +-- Module : Xmobar.Commands +-- Copyright : (c) Andrea Rossato +-- License : BSD-style (see LICENSE) +-- +-- Maintainer : Jose A. Ortega Ruiz +-- Stability : unstable +-- Portability : unportable +-- +-- The 'Exec' class and the 'Command' data type. +-- +-- The 'Exec' class rappresents the executable types, whose constructors may +-- appear in the 'Config.commands' field of the 'Config.Config' data type. +-- +-- The 'Command' data type is for OS commands to be run by xmobar +-- +----------------------------------------------------------------------------- + +module Xmobar.Run.Commands (Command (..), Exec (..)) where + +import Prelude +import Control.Exception (handle, SomeException(..)) +import Data.Char +import System.Process +import System.Exit +import System.IO (hClose) + +import Xmobar.System.Signal +import Xmobar.Utils (hGetLineSafe, tenthSeconds) + +class Show e => Exec e where + alias :: e -> String + alias e = takeWhile (not . isSpace) $ show e + rate :: e -> Int + rate _ = 10 + run :: e -> IO String + run _ = return "" + start :: e -> (String -> IO ()) -> IO () + start e cb = go + where go = run e >>= cb >> tenthSeconds (rate e) >> go + trigger :: e -> (Maybe SignalType -> IO ()) -> IO () + trigger _ sh = sh Nothing + +data Command = Com Program Args Alias Rate + | ComX Program Args String Alias Rate + deriving (Show,Read,Eq) + +type Args = [String] +type Program = String +type Alias = String +type Rate = Int + +instance Exec Command where + alias (ComX p _ _ a _) = + if p /= "" then (if a == "" then p else a) else "" + alias (Com p a al r) = alias (ComX p a "" al r) + start (Com p as al r) cb = + start (ComX p as ("Could not execute command " ++ p) al r) cb + start (ComX prog args msg _ r) cb = if r > 0 then go else exec + where go = exec >> tenthSeconds r >> go + exec = do + (i,o,e,p) <- runInteractiveProcess prog args Nothing Nothing + exit <- waitForProcess p + let closeHandles = hClose o >> hClose i >> hClose e + getL = handle (\(SomeException _) -> return "") + (hGetLineSafe o) + case exit of + ExitSuccess -> do str <- getL + closeHandles + cb str + _ -> closeHandles >> cb msg diff --git a/src/lib/Xmobar/Run/Runnable.hs b/src/lib/Xmobar/Run/Runnable.hs new file mode 100644 index 0000000..962166e --- /dev/null +++ b/src/lib/Xmobar/Run/Runnable.hs @@ -0,0 +1,60 @@ +{-# LANGUAGE ExistentialQuantification, MultiParamTypeClasses, FlexibleContexts, FlexibleInstances #-} +----------------------------------------------------------------------------- +-- | +-- Module : Xmobar.Runnable +-- Copyright : (c) Andrea Rossato +-- License : BSD-style (see LICENSE) +-- +-- Maintainer : Jose A. Ortega Ruiz +-- Stability : unstable +-- Portability : unportable +-- +-- The existential type to store the list of commands to be executed. +-- I must thank Claus Reinke for the help in understanding the mysteries of +-- reading existential types. The Read instance of Runnable must be credited to +-- him. +-- +-- See here: +-- http:\/\/www.haskell.org\/pipermail\/haskell-cafe\/2007-July\/028227.html +-- +----------------------------------------------------------------------------- + +module Xmobar.Run.Runnable where + +import Control.Monad +import Text.Read +import Xmobar.Run.Types (runnableTypes) +import Xmobar.Run.Commands + +data Runnable = forall r . (Exec r, Read r, Show r) => Run r + +instance Exec Runnable where + start (Run a) = start a + alias (Run a) = alias a + trigger (Run a) = trigger a + +instance Show Runnable where + show (Run x) = show x + +instance Read Runnable where + readPrec = readRunnable + +class ReadAsAnyOf ts ex where + -- | Reads an existential type as any of hidden types ts + readAsAnyOf :: ts -> ReadPrec ex + +instance ReadAsAnyOf () ex where + readAsAnyOf ~() = mzero + +instance (Read t, Exec t, ReadAsAnyOf ts Runnable) => ReadAsAnyOf (t,ts) Runnable where + readAsAnyOf ~(t,ts) = r t `mplus` readAsAnyOf ts + where r ty = do { m <- readPrec; return (Run (m `asTypeOf` ty)) } + +-- | The 'Prelude.Read' parser for the 'Runnable' existential type. It +-- needs an 'Prelude.undefined' with a type signature containing the +-- list of all possible types hidden within 'Runnable'. See 'Config.runnableTypes'. +-- Each hidden type must have a 'Prelude.Read' instance. +readRunnable :: ReadPrec Runnable +readRunnable = prec 10 $ do + Ident "Run" <- lexP + parens $ readAsAnyOf runnableTypes diff --git a/src/lib/Xmobar/Run/Runnable.hs-boot b/src/lib/Xmobar/Run/Runnable.hs-boot new file mode 100644 index 0000000..f272d81 --- /dev/null +++ b/src/lib/Xmobar/Run/Runnable.hs-boot @@ -0,0 +1,8 @@ +{-# LANGUAGE ExistentialQuantification #-} +module Xmobar.Run.Runnable where +import Xmobar.Run.Commands + +data Runnable = forall r . (Exec r,Read r,Show r) => Run r + +instance Read Runnable +instance Exec Runnable diff --git a/src/lib/Xmobar/Run/Template.hs b/src/lib/Xmobar/Run/Template.hs new file mode 100644 index 0000000..5bada89 --- /dev/null +++ b/src/lib/Xmobar/Run/Template.hs @@ -0,0 +1,65 @@ +------------------------------------------------------------------------------ +-- | +-- Module: Xmobar.Template +-- Copyright: (c) 2018 Jose Antonio Ortega Ruiz +-- License: BSD3-style (see LICENSE) +-- +-- Maintainer: jao@gnu.org +-- Stability: unstable +-- Portability: portable +-- Created: Sun Nov 25, 2018 05:49 +-- +-- +-- Handling the top-level output template +-- +------------------------------------------------------------------------------ + + +module Xmobar.Run.Template(parseCommands) where + +import qualified Data.Map as Map +import Text.ParserCombinators.Parsec + +import Xmobar.Run.Commands +import Xmobar.Run.Runnable +import Xmobar.Config + +-- | Parses the output template string +templateStringParser :: Config -> Parser (String,String,String) +templateStringParser c = do + s <- allTillSep c + com <- templateCommandParser c + ss <- allTillSep c + return (com, s, ss) + +-- | Parses the command part of the template string +templateCommandParser :: Config -> Parser String +templateCommandParser c = + let chr = char . head . sepChar + in between (chr c) (chr c) (allTillSep c) + +-- | Combines the template parsers +templateParser :: Config -> Parser [(String,String,String)] +templateParser = many . templateStringParser + +-- | Actually runs the template parsers +parseCommands :: Config -> String -> IO [(Runnable,String,String)] +parseCommands c s = + do str <- case parse (templateParser c) "" s of + Left _ -> return [("", s, "")] + Right x -> return x + let cl = map alias (commands c) + m = Map.fromList $ zip cl (commands c) + return $ combine c m str + +-- | Given a finite "Map" and a parsed template produce the resulting +-- output string. +combine :: Config -> Map.Map String Runnable + -> [(String, String, String)] -> [(Runnable,String,String)] +combine _ _ [] = [] +combine c m ((ts,s,ss):xs) = (com, s, ss) : combine c m xs + where com = Map.findWithDefault dflt ts m + dflt = Run $ Com ts [] [] 10 + +allTillSep :: Config -> Parser String +allTillSep = many . noneOf . sepChar diff --git a/src/lib/Xmobar/Run/Types.hs b/src/lib/Xmobar/Run/Types.hs new file mode 100644 index 0000000..4fb526a --- /dev/null +++ b/src/lib/Xmobar/Run/Types.hs @@ -0,0 +1,65 @@ +{-# LANGUAGE TypeOperators, CPP #-} +------------------------------------------------------------------------------ +-- | +-- Module: Xmobar.Run.Types +-- Copyright: (c) 2018 Jose Antonio Ortega Ruiz +-- License: BSD3-style (see LICENSE) +-- +-- Maintainer: jao@gnu.org +-- Stability: unstable +-- Portability: portable +-- Created: Sun Nov 25, 2018 07:17 +-- +-- +-- An enumeration of all runnable types +-- +------------------------------------------------------------------------------ + + +module Xmobar.Run.Types(runnableTypes) where + +import Xmobar.Run.Commands + +import {-# SOURCE #-} Xmobar.Run.Runnable() +import Xmobar.Plugins.Monitors +import Xmobar.Plugins.Date +import Xmobar.Plugins.PipeReader +import Xmobar.Plugins.BufferedPipeReader +import Xmobar.Plugins.MarqueePipeReader +import Xmobar.Plugins.CommandReader +import Xmobar.Plugins.StdinReader +import Xmobar.Plugins.XMonadLog +import Xmobar.Plugins.EWMH +import Xmobar.Plugins.Kbd +import Xmobar.Plugins.Locks + +#ifdef INOTIFY +import Xmobar.Plugins.Mail +import Xmobar.Plugins.MBox +#endif + +#ifdef DATEZONE +import Xmobar.Plugins.DateZone +#endif + +-- | An alias for tuple types that is more convenient for long lists. +type a :*: b = (a, b) +infixr :*: + +-- | This is the list of types that can be hidden inside +-- 'Runnable.Runnable', the existential type that stores all commands +-- to be executed by Xmobar. It is used by 'Runnable.readRunnable' in +-- the 'Runnable.Runnable' Read instance. To install a plugin just add +-- the plugin's type to the list of types (separated by ':*:') appearing in +-- this function's type signature. +runnableTypes :: Command :*: Monitors :*: Date :*: PipeReader :*: + BufferedPipeReader :*: CommandReader :*: StdinReader :*: + XMonadLog :*: EWMH :*: Kbd :*: Locks :*: +#ifdef INOTIFY + Mail :*: MBox :*: +#endif +#ifdef DATEZONE + DateZone :*: +#endif + MarqueePipeReader :*: () +runnableTypes = undefined diff --git a/src/lib/Xmobar/Runnable.hs b/src/lib/Xmobar/Runnable.hs deleted file mode 100644 index 164f661..0000000 --- a/src/lib/Xmobar/Runnable.hs +++ /dev/null @@ -1,60 +0,0 @@ -{-# LANGUAGE ExistentialQuantification, MultiParamTypeClasses, FlexibleContexts, FlexibleInstances #-} ------------------------------------------------------------------------------ --- | --- Module : Xmobar.Runnable --- Copyright : (c) Andrea Rossato --- License : BSD-style (see LICENSE) --- --- Maintainer : Jose A. Ortega Ruiz --- Stability : unstable --- Portability : unportable --- --- The existential type to store the list of commands to be executed. --- I must thank Claus Reinke for the help in understanding the mysteries of --- reading existential types. The Read instance of Runnable must be credited to --- him. --- --- See here: --- http:\/\/www.haskell.org\/pipermail\/haskell-cafe\/2007-July\/028227.html --- ------------------------------------------------------------------------------ - -module Xmobar.Runnable where - -import Control.Monad -import Text.Read -import Xmobar.Config (runnableTypes) -import Xmobar.Commands - -data Runnable = forall r . (Exec r, Read r, Show r) => Run r - -instance Exec Runnable where - start (Run a) = start a - alias (Run a) = alias a - trigger (Run a) = trigger a - -instance Show Runnable where - show (Run x) = show x - -instance Read Runnable where - readPrec = readRunnable - -class ReadAsAnyOf ts ex where - -- | Reads an existential type as any of hidden types ts - readAsAnyOf :: ts -> ReadPrec ex - -instance ReadAsAnyOf () ex where - readAsAnyOf ~() = mzero - -instance (Read t, Exec t, ReadAsAnyOf ts Runnable) => ReadAsAnyOf (t,ts) Runnable where - readAsAnyOf ~(t,ts) = r t `mplus` readAsAnyOf ts - where r ty = do { m <- readPrec; return (Run (m `asTypeOf` ty)) } - --- | The 'Prelude.Read' parser for the 'Runnable' existential type. It --- needs an 'Prelude.undefined' with a type signature containing the --- list of all possible types hidden within 'Runnable'. See 'Config.runnableTypes'. --- Each hidden type must have a 'Prelude.Read' instance. -readRunnable :: ReadPrec Runnable -readRunnable = prec 10 $ do - Ident "Run" <- lexP - parens $ readAsAnyOf runnableTypes diff --git a/src/lib/Xmobar/Runnable.hs-boot b/src/lib/Xmobar/Runnable.hs-boot deleted file mode 100644 index 0f67322..0000000 --- a/src/lib/Xmobar/Runnable.hs-boot +++ /dev/null @@ -1,8 +0,0 @@ -{-# LANGUAGE ExistentialQuantification #-} -module Xmobar.Runnable where -import Xmobar.Commands - -data Runnable = forall r . (Exec r,Read r,Show r) => Run r - -instance Read Runnable -instance Exec Runnable diff --git a/src/lib/Xmobar/Template.hs b/src/lib/Xmobar/Template.hs deleted file mode 100644 index bd4852a..0000000 --- a/src/lib/Xmobar/Template.hs +++ /dev/null @@ -1,65 +0,0 @@ ------------------------------------------------------------------------------- --- | --- Module: Xmobar.Template --- Copyright: (c) 2018 Jose Antonio Ortega Ruiz --- License: BSD3-style (see LICENSE) --- --- Maintainer: jao@gnu.org --- Stability: unstable --- Portability: portable --- Created: Sun Nov 25, 2018 05:49 --- --- --- Handling the top-level output template --- ------------------------------------------------------------------------------- - - -module Xmobar.Template(parseCommands) where - -import qualified Data.Map as Map -import Text.ParserCombinators.Parsec - -import Xmobar.Commands -import Xmobar.Config -import Xmobar.Runnable - --- | Parses the output template string -templateStringParser :: Config -> Parser (String,String,String) -templateStringParser c = do - s <- allTillSep c - com <- templateCommandParser c - ss <- allTillSep c - return (com, s, ss) - --- | Parses the command part of the template string -templateCommandParser :: Config -> Parser String -templateCommandParser c = - let chr = char . head . sepChar - in between (chr c) (chr c) (allTillSep c) - --- | Combines the template parsers -templateParser :: Config -> Parser [(String,String,String)] -templateParser = many . templateStringParser - --- | Actually runs the template parsers -parseCommands :: Config -> String -> IO [(Runnable,String,String)] -parseCommands c s = - do str <- case parse (templateParser c) "" s of - Left _ -> return [("", s, "")] - Right x -> return x - let cl = map alias (commands c) - m = Map.fromList $ zip cl (commands c) - return $ combine c m str - --- | Given a finite "Map" and a parsed template produce the resulting --- output string. -combine :: Config -> Map.Map String Runnable - -> [(String, String, String)] -> [(Runnable,String,String)] -combine _ _ [] = [] -combine c m ((ts,s,ss):xs) = (com, s, ss) : combine c m xs - where com = Map.findWithDefault dflt ts m - dflt = Run $ Com ts [] [] 10 - -allTillSep :: Config -> Parser String -allTillSep = many . noneOf . sepChar diff --git a/src/lib/Xmobar/X11/EventLoop.hs b/src/lib/Xmobar/X11/EventLoop.hs index cc08acd..f97c56b 100644 --- a/src/lib/Xmobar/X11/EventLoop.hs +++ b/src/lib/Xmobar/X11/EventLoop.hs @@ -37,11 +37,11 @@ import Data.Map hiding (foldr, map, filter) import Data.Maybe (fromJust, isJust) import Xmobar.Config -import Xmobar.Commands import Xmobar.Actions -import Xmobar.Runnable import Xmobar.Utils import Xmobar.System.Signal +import Xmobar.Run.Commands +import Xmobar.Run.Runnable import Xmobar.X11.Parsers import Xmobar.X11.Window import Xmobar.X11.XUtil diff --git a/xmobar.cabal b/xmobar.cabal index 76182dc..ff167e4 100644 --- a/xmobar.cabal +++ b/xmobar.cabal @@ -97,11 +97,12 @@ library exposed-modules: Xmobar, Xmobar.Config, Xmobar.Actions, - Xmobar.Commands, - Xmobar.Runnable + Xmobar.Run.Commands, + Xmobar.Run.Runnable - other-modules: Xmobar.Template, - Xmobar.Utils, + other-modules: Xmobar.Utils, + Xmobar.Run.Types, + Xmobar.Run.Template, Xmobar.System.StatFS, Xmobar.System.Environment, Xmobar.System.Localize, @@ -308,7 +309,7 @@ test-suite XmobarTest other-modules: Xmobar.Plugins.Monitors.Volume Xmobar.Plugins.Monitors.Alsa Plugins.Monitors.AlsaSpec - Xmobar.Commands + Xmobar.Run.Commands Xmobar.Plugins.Monitors.Common Xmobar.System.Signal Xmobar.Utils -- cgit v1.2.3