Skip to content

Instantly share code, notes, and snippets.

@Cutuchiqueno
Last active December 14, 2015 12:52
Show Gist options
  • Save Cutuchiqueno/e9760ac2e922c5e5054f to your computer and use it in GitHub Desktop.
Save Cutuchiqueno/e9760ac2e922c5e5054f to your computer and use it in GitHub Desktop.
This small program was the first real program I wrote in Haskel. The only reason why I put it here is the possibility to receive feedback about the abundant inconsistencies, unsafeties and not very elegant decisions which the code provide to learn and leave them behind next time
-- This small program was the first real program I wrote in Haskel. The
-- only reason why I put it here is the possibility to receive feedback
-- about the abundant inconsistencies, unsafeties and not very elegant
-- decisions which the code provide to learn and leave them behind next
-- time
import Options.Applicative
import System.Environment
import System.Exit
import System.Process
import Data.List (isInfixOf)
import Text.Regex.PCRE
-- parser with optparse-applicative
data Options = Options
{ extDisplay :: Bool
, lapDisplay :: Bool }
options :: Parser Options
options = Options
<$> switch
( long "external-display"
<> short 'e'
<> help "turn on the external display connected to the laptop" )
<*> switch
( long "local-display"
<> short 'l'
<> help "turn on the local display of the laptop" )
greet :: Options -> IO ()
greet (Options True False) = getDisplays >>= setDisplays 'e'
greet (Options False True) = getDisplays >>= setDisplays 'l'
greet _ = getDisplays >>= setDisplays 'n'
main :: IO ()
main = execParser opts >>= greet
where
opts = info (helper <*> options)
( fullDesc
<> progDesc "Switch between local and external displays"
<> header "sctl - a small tool to switch between screen set-ups in a quick way" )
-- programm code
data Screen = Screen { display :: String
, connected :: Bool
, active :: Bool
} deriving (Show)
getDisplays :: IO [Screen]
getDisplays = do
output <- readProcess "xrandr" [] ""
let oLines = lines output
let displayStrs = fmap words ((filter (\line -> isInfixOf " connected " line) oLines))
let scrData = fmap (\display -> Screen (display !!0)
(display !!1 == "connected")
((concat display) =~ "axis\\)\\d{3}" :: Bool))
displayStrs -- parse active with regular expr
return scrData
setDisplays :: Char -> [Screen] -> IO()
setDisplays mode displays
| mode == 'l' = displayOn [(head displays)] >> displayOff (tail displays)
| mode == 'e' = displayOn (tail displays) >> displayOff [(head displays)]
| mode == 'n' = if (length displays) > 1 then displayOn notrunning >> displayOff running else return ()
where
displayOn on = mapM_ (\id -> callProcess "xrandr" ["--output", display id, "--auto"]) on
displayOff off = mapM_ (\id -> callProcess "xrandr" ["--output", display id, "--off"]) off
running = filter (\dis -> active dis == True) displays
notrunning = filter (\dis -> active dis == False) displays
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment