x11-xinput-0.1.0.0: Graphics/X11/XInput/Devices.hs
module Graphics.X11.XInput.Devices
(Device (..),
DevicesMap (..),
buildDevicesMap,
showDevicesMap,
isMasterDevice,
deviceById, masterDeviceById,
deviceByName
) where
import qualified Data.Map as M
import Text.Printf
import Graphics.X11.XInput.Types
data Device = Device {
masterDevice :: DeviceInfo,
slaveDevices :: [DeviceInfo] }
deriving (Eq, Show)
data DevicesMap = DevicesMap {
masterDevices :: M.Map DeviceID Device
, allDevices :: M.Map DeviceID DeviceInfo
, byName :: M.Map String DeviceInfo }
deriving (Eq, Show)
buildDevicesMap :: [DeviceInfo] -> DevicesMap
buildDevicesMap list = DevicesMap {
masterDevices = M.fromList $ build [] list
, allDevices = M.fromList [(diID di, di) | di <- list]
, byName = M.fromList [(diName di, di) | di <- list]
}
where
build :: [(DeviceID, Device)] -> [DeviceInfo] -> [(DeviceID, Device)]
build done [] = done
build done (d:ds) =
case diUse d of
XIMasterPointer -> build (simply d: done) ds
XIMasterKeyboard -> build (simply d: done) ds
XISlavePointer -> build (up d done) ds
XISlaveKeyboard -> build (up d done) ds
XIFloatingSlave -> build (up d done) ds
simply d = (diID d, Device d [])
up :: DeviceInfo -> [(DeviceID, Device)] -> [(DeviceID, Device)]
up d ds = map (update d) ds
update :: DeviceInfo -> (DeviceID, Device) -> (DeviceID, Device)
update slave pair@(masterID, master)
| diAttachment slave == masterID = (masterID, add master slave)
| otherwise = pair
add master slave =
master {slaveDevices = slave: slaveDevices master}
showDevicesMap :: DevicesMap -> String
showDevicesMap m = unlines $ map go $ M.assocs $ masterDevices m
where
go (devID, dev) =
(printf "#%s: %s\n" (show devID) (show $ masterDevice dev))
++ (unlines $ map one $ slaveDevices dev)
one dev = printf " +-- #%s: %s"
(show $ diID dev)
(show dev)
isMasterDevice :: DeviceID -> DevicesMap -> Bool
isMasterDevice i dmap = i `M.member` masterDevices dmap
deviceById :: DeviceID -> DevicesMap -> Maybe DeviceInfo
deviceById i dmap = M.lookup i (allDevices dmap)
masterDeviceById :: DeviceID -> DevicesMap -> Maybe Device
masterDeviceById i dmap = M.lookup i (masterDevices dmap)
deviceByName :: String -> DevicesMap -> Maybe DeviceInfo
deviceByName name dmap = M.lookup name (byName dmap)