{-# LANGUAGE DeriveAnyClass #-}
{-# LANGUAGE DeriveGeneric #-}
module Brick.AttrMap
( AttrMap
, AttrName
, attrMap
, forceAttrMap
, forceAttrMapAllowStyle
, attrName
, attrNameComponents
, attrMapLookup
, setDefaultAttr
, getDefaultAttr
, applyAttrMappings
, mergeWithDefault
, mapAttrName
, mapAttrNames
)
where
import qualified Data.Semigroup as Sem
import Control.DeepSeq
import Data.Bits ((.|.))
import qualified Data.Map as M
import Data.Maybe (mapMaybe)
import Data.List (inits)
import GHC.Generics (Generic)
import Graphics.Vty (Attr(..), MaybeDefault(..), Style)
data AttrName = AttrName [String]
deriving (Int -> AttrName -> ShowS
[AttrName] -> ShowS
AttrName -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [AttrName] -> ShowS
$cshowList :: [AttrName] -> ShowS
show :: AttrName -> String
$cshow :: AttrName -> String
showsPrec :: Int -> AttrName -> ShowS
$cshowsPrec :: Int -> AttrName -> ShowS
Show, ReadPrec [AttrName]
ReadPrec AttrName
Int -> ReadS AttrName
ReadS [AttrName]
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
readListPrec :: ReadPrec [AttrName]
$creadListPrec :: ReadPrec [AttrName]
readPrec :: ReadPrec AttrName
$creadPrec :: ReadPrec AttrName
readList :: ReadS [AttrName]
$creadList :: ReadS [AttrName]
readsPrec :: Int -> ReadS AttrName
$creadsPrec :: Int -> ReadS AttrName
Read, AttrName -> AttrName -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: AttrName -> AttrName -> Bool
$c/= :: AttrName -> AttrName -> Bool
== :: AttrName -> AttrName -> Bool
$c== :: AttrName -> AttrName -> Bool
Eq, Eq AttrName
AttrName -> AttrName -> Bool
AttrName -> AttrName -> Ordering
AttrName -> AttrName -> AttrName
forall a.
Eq a
-> (a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
min :: AttrName -> AttrName -> AttrName
$cmin :: AttrName -> AttrName -> AttrName
max :: AttrName -> AttrName -> AttrName
$cmax :: AttrName -> AttrName -> AttrName
>= :: AttrName -> AttrName -> Bool
$c>= :: AttrName -> AttrName -> Bool
> :: AttrName -> AttrName -> Bool
$c> :: AttrName -> AttrName -> Bool
<= :: AttrName -> AttrName -> Bool
$c<= :: AttrName -> AttrName -> Bool
< :: AttrName -> AttrName -> Bool
$c< :: AttrName -> AttrName -> Bool
compare :: AttrName -> AttrName -> Ordering
$ccompare :: AttrName -> AttrName -> Ordering
Ord, forall x. Rep AttrName x -> AttrName
forall x. AttrName -> Rep AttrName x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cto :: forall x. Rep AttrName x -> AttrName
$cfrom :: forall x. AttrName -> Rep AttrName x
Generic, AttrName -> ()
forall a. (a -> ()) -> NFData a
rnf :: AttrName -> ()
$crnf :: AttrName -> ()
NFData)
instance Sem.Semigroup AttrName where
(AttrName [String]
as) <> :: AttrName -> AttrName -> AttrName
<> (AttrName [String]
bs) = [String] -> AttrName
AttrName forall a b. (a -> b) -> a -> b
$ [String]
as forall a. Monoid a => a -> a -> a
`mappend` [String]
bs
instance Monoid AttrName where
mempty :: AttrName
mempty = [String] -> AttrName
AttrName []
mappend :: AttrName -> AttrName -> AttrName
mappend = forall a. Semigroup a => a -> a -> a
(Sem.<>)
data AttrMap = AttrMap Attr (M.Map AttrName Attr)
| ForceAttr Attr
| ForceAttrAllowStyle Attr AttrMap
deriving (Int -> AttrMap -> ShowS
[AttrMap] -> ShowS
AttrMap -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [AttrMap] -> ShowS
$cshowList :: [AttrMap] -> ShowS
show :: AttrMap -> String
$cshow :: AttrMap -> String
showsPrec :: Int -> AttrMap -> ShowS
$cshowsPrec :: Int -> AttrMap -> ShowS
Show, forall x. Rep AttrMap x -> AttrMap
forall x. AttrMap -> Rep AttrMap x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cto :: forall x. Rep AttrMap x -> AttrMap
$cfrom :: forall x. AttrMap -> Rep AttrMap x
Generic, AttrMap -> ()
forall a. (a -> ()) -> NFData a
rnf :: AttrMap -> ()
$crnf :: AttrMap -> ()
NFData)
attrName :: String -> AttrName
attrName :: String -> AttrName
attrName = [String] -> AttrName
AttrName forall b c a. (b -> c) -> (a -> b) -> a -> c
. (forall a. a -> [a] -> [a]
:[])
attrNameComponents :: AttrName -> [String]
attrNameComponents :: AttrName -> [String]
attrNameComponents (AttrName [String]
cs) = [String]
cs
attrMap :: Attr
-> [(AttrName, Attr)]
-> AttrMap
attrMap :: Attr -> [(AttrName, Attr)] -> AttrMap
attrMap Attr
theDefault [(AttrName, Attr)]
pairs = Attr -> Map AttrName Attr -> AttrMap
AttrMap Attr
theDefault (forall k a. Ord k => [(k, a)] -> Map k a
M.fromList [(AttrName, Attr)]
pairs)
forceAttrMap :: Attr -> AttrMap
forceAttrMap :: Attr -> AttrMap
forceAttrMap = Attr -> AttrMap
ForceAttr
forceAttrMapAllowStyle :: Attr -> AttrMap -> AttrMap
forceAttrMapAllowStyle :: Attr -> AttrMap -> AttrMap
forceAttrMapAllowStyle = Attr -> AttrMap -> AttrMap
ForceAttrAllowStyle
mergeWithDefault :: Attr -> AttrMap -> Attr
mergeWithDefault :: Attr -> AttrMap -> Attr
mergeWithDefault Attr
_ (ForceAttr Attr
a) = Attr
a
mergeWithDefault Attr
_ (ForceAttrAllowStyle Attr
f AttrMap
_) = Attr
f
mergeWithDefault Attr
a (AttrMap Attr
d Map AttrName Attr
_) = Attr -> Attr -> Attr
combineAttrs Attr
d Attr
a
attrMapLookup :: AttrName -> AttrMap -> Attr
attrMapLookup :: AttrName -> AttrMap -> Attr
attrMapLookup AttrName
_ (ForceAttr Attr
a) = Attr
a
attrMapLookup AttrName
a (ForceAttrAllowStyle Attr
forced AttrMap
m) =
let result :: Attr
result = AttrName -> AttrMap -> Attr
attrMapLookup AttrName
a AttrMap
m
in Attr
forced { attrStyle :: MaybeDefault Style
attrStyle = Attr -> MaybeDefault Style
attrStyle Attr
forced MaybeDefault Style -> MaybeDefault Style -> MaybeDefault Style
`combineStyles` Attr -> MaybeDefault Style
attrStyle Attr
result
}
attrMapLookup (AttrName []) (AttrMap Attr
theDefault Map AttrName Attr
_) = Attr
theDefault
attrMapLookup (AttrName [String]
ns) (AttrMap Attr
theDefault Map AttrName Attr
m) =
let results :: [Attr]
results = forall a b. (a -> Maybe b) -> [a] -> [b]
mapMaybe (\[String]
n -> forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup ([String] -> AttrName
AttrName [String]
n) Map AttrName Attr
m) (forall a. [a] -> [[a]]
inits [String]
ns)
in forall (t :: * -> *) b a.
Foldable t =>
(b -> a -> b) -> b -> t a -> b
foldl Attr -> Attr -> Attr
combineAttrs Attr
theDefault [Attr]
results
setDefaultAttr :: Attr -> AttrMap -> AttrMap
setDefaultAttr :: Attr -> AttrMap -> AttrMap
setDefaultAttr Attr
_ (ForceAttr Attr
a) = Attr -> AttrMap
ForceAttr Attr
a
setDefaultAttr Attr
newDefault (ForceAttrAllowStyle Attr
a AttrMap
m) =
Attr -> AttrMap -> AttrMap
ForceAttrAllowStyle Attr
a (Attr -> AttrMap -> AttrMap
setDefaultAttr Attr
newDefault AttrMap
m)
setDefaultAttr Attr
newDefault (AttrMap Attr
_ Map AttrName Attr
m) = Attr -> Map AttrName Attr -> AttrMap
AttrMap Attr
newDefault Map AttrName Attr
m
getDefaultAttr :: AttrMap -> Attr
getDefaultAttr :: AttrMap -> Attr
getDefaultAttr (ForceAttr Attr
a) = Attr
a
getDefaultAttr (ForceAttrAllowStyle Attr
_ AttrMap
m) = AttrMap -> Attr
getDefaultAttr AttrMap
m
getDefaultAttr (AttrMap Attr
d Map AttrName Attr
_) = Attr
d
combineAttrs :: Attr -> Attr -> Attr
combineAttrs :: Attr -> Attr -> Attr
combineAttrs (Attr MaybeDefault Style
s1 MaybeDefault Color
f1 MaybeDefault Color
b1 MaybeDefault Text
u1) (Attr MaybeDefault Style
s2 MaybeDefault Color
f2 MaybeDefault Color
b2 MaybeDefault Text
u2) =
MaybeDefault Style
-> MaybeDefault Color
-> MaybeDefault Color
-> MaybeDefault Text
-> Attr
Attr (MaybeDefault Style
s1 MaybeDefault Style -> MaybeDefault Style -> MaybeDefault Style
`combineStyles` MaybeDefault Style
s2)
(MaybeDefault Color
f1 forall a. MaybeDefault a -> MaybeDefault a -> MaybeDefault a
`combineMDs` MaybeDefault Color
f2)
(MaybeDefault Color
b1 forall a. MaybeDefault a -> MaybeDefault a -> MaybeDefault a
`combineMDs` MaybeDefault Color
b2)
(MaybeDefault Text
u1 forall a. MaybeDefault a -> MaybeDefault a -> MaybeDefault a
`combineMDs` MaybeDefault Text
u2)
combineMDs :: MaybeDefault a -> MaybeDefault a -> MaybeDefault a
combineMDs :: forall a. MaybeDefault a -> MaybeDefault a -> MaybeDefault a
combineMDs MaybeDefault a
_ (SetTo a
v) = forall v. v -> MaybeDefault v
SetTo a
v
combineMDs (SetTo a
v) MaybeDefault a
_ = forall v. v -> MaybeDefault v
SetTo a
v
combineMDs MaybeDefault a
_ MaybeDefault a
v = MaybeDefault a
v
combineStyles :: MaybeDefault Style -> MaybeDefault Style -> MaybeDefault Style
combineStyles :: MaybeDefault Style -> MaybeDefault Style -> MaybeDefault Style
combineStyles (SetTo Style
a) (SetTo Style
b) = forall v. v -> MaybeDefault v
SetTo forall a b. (a -> b) -> a -> b
$ Style
a forall a. Bits a => a -> a -> a
.|. Style
b
combineStyles MaybeDefault Style
_ (SetTo Style
v) = forall v. v -> MaybeDefault v
SetTo Style
v
combineStyles (SetTo Style
v) MaybeDefault Style
_ = forall v. v -> MaybeDefault v
SetTo Style
v
combineStyles MaybeDefault Style
_ MaybeDefault Style
v = MaybeDefault Style
v
applyAttrMappings :: [(AttrName, Attr)] -> AttrMap -> AttrMap
applyAttrMappings :: [(AttrName, Attr)] -> AttrMap -> AttrMap
applyAttrMappings [(AttrName, Attr)]
_ (ForceAttr Attr
a) = Attr -> AttrMap
ForceAttr Attr
a
applyAttrMappings [(AttrName, Attr)]
ms (AttrMap Attr
d Map AttrName Attr
m) = Attr -> Map AttrName Attr -> AttrMap
AttrMap Attr
d ((forall k a. Ord k => [(k, a)] -> Map k a
M.fromList [(AttrName, Attr)]
ms) forall k a. Ord k => Map k a -> Map k a -> Map k a
`M.union` Map AttrName Attr
m)
applyAttrMappings [(AttrName, Attr)]
ms (ForceAttrAllowStyle Attr
a AttrMap
m) = Attr -> AttrMap -> AttrMap
ForceAttrAllowStyle Attr
a ([(AttrName, Attr)] -> AttrMap -> AttrMap
applyAttrMappings [(AttrName, Attr)]
ms AttrMap
m)
mapAttrName :: AttrName -> AttrName -> AttrMap -> AttrMap
mapAttrName :: AttrName -> AttrName -> AttrMap -> AttrMap
mapAttrName AttrName
fromName AttrName
ontoName AttrMap
inMap =
[(AttrName, Attr)] -> AttrMap -> AttrMap
applyAttrMappings [(AttrName
ontoName, AttrName -> AttrMap -> Attr
attrMapLookup AttrName
fromName AttrMap
inMap)] AttrMap
inMap
mapAttrNames :: [(AttrName, AttrName)] -> AttrMap -> AttrMap
mapAttrNames :: [(AttrName, AttrName)] -> AttrMap -> AttrMap
mapAttrNames [(AttrName, AttrName)]
names AttrMap
inMap = forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr (forall a b c. (a -> b -> c) -> (a, b) -> c
uncurry AttrName -> AttrName -> AttrMap -> AttrMap
mapAttrName) AttrMap
inMap [(AttrName, AttrName)]
names