66 lines
2.6 KiB
Haskell
66 lines
2.6 KiB
Haskell
{- | Deals with changes in a creature's awareness of other creatures. -}
|
|
module Dodge.Creature.AlertLevel
|
|
where
|
|
import Dodge.Data
|
|
import Dodge.Creature.AlertLevel.Data
|
|
import Dodge.Base.Collide
|
|
import StrictHelp
|
|
|
|
import Control.Lens
|
|
import Control.Monad.Reader
|
|
import qualified Data.IntMap.Strict as IM
|
|
{- | Ties together (currently) an awareness and attention update -}
|
|
basicPerceptionUpdate
|
|
:: [Int] -- ^ List of creature ids that may direct attention and awareness
|
|
-> World
|
|
-> Creature
|
|
-> Creature
|
|
basicPerceptionUpdate is w cr
|
|
= basicAwarenessUpdate w $ basicAttentionUpdate is w cr
|
|
|
|
basicPerceptionUpdateR
|
|
:: [Int] -- ^ List of creature ids that may direct attention and awareness
|
|
-> Creature
|
|
-> Reader World Creature
|
|
basicPerceptionUpdateR is cr = reader $ \w ->
|
|
basicAwarenessUpdate w $ basicAttentionUpdate is w cr
|
|
|
|
{- | Update a creatures awareness based upon the creatures current direction
|
|
of attention -}
|
|
basicAwarenessUpdate
|
|
:: World -> Creature -> Creature
|
|
basicAwarenessUpdate _ cr = case _crAttentionDir cr of
|
|
AttentiveTo is -> cr & crAwarenessLevel %~ updateAwareness is
|
|
Fixated i -> cr & crAwarenessLevel
|
|
%~ ( IM.insert i (Cognizant 100) . IM.mapMaybe decreaseAwareness)
|
|
{- | Increase awareness of a given list of ids -}
|
|
updateAwareness :: [Int] -> IM.IntMap AwarenessLevel -> IM.IntMap AwarenessLevel
|
|
updateAwareness is imawareness
|
|
= foldr (\k -> IM.insertWith (\_ x -> increaseAwareness x) k (AwarenessInt 1))
|
|
(IM.mapMaybe decreaseAwareness imawareness) is
|
|
-- (IM.mapMaybe decreaseAwareness imawareness) is
|
|
{- | Increase awareness level -}
|
|
increaseAwareness :: AwarenessLevel -> AwarenessLevel
|
|
increaseAwareness (AwarenessInt x)
|
|
| x < 100 = AwarenessInt $ x + 2
|
|
| otherwise = Cognizant 1
|
|
increaseAwareness (Cognizant x)
|
|
| x < 100 = Cognizant (x + 2)
|
|
| otherwise = Cognizant 100
|
|
{- | Decrease awareness level. Returns 'Maybe' value for use with 'IM.mapMaybe'
|
|
-}
|
|
decreaseAwareness :: AwarenessLevel -> Maybe AwarenessLevel
|
|
decreaseAwareness (AwarenessInt 0) = Nothing
|
|
decreaseAwareness (AwarenessInt x) = Just $ AwarenessInt (x - 1)
|
|
decreaseAwareness (Cognizant 0) = Just $ AwarenessInt 100
|
|
decreaseAwareness (Cognizant x) = Just $ Cognizant $ x - 1
|
|
{- | Given a fixed group of creatures, direct attention to those of them that
|
|
- are in view. -}
|
|
basicAttentionUpdate
|
|
:: [Int] -- ^ Creatures that may attract this creature's attention
|
|
-> World
|
|
-> Creature
|
|
-> Creature
|
|
basicAttentionUpdate cids w cr = cr & crAttentionDir .~
|
|
AttentiveTo (forceFoldable $ filter (\cid -> canSee (_crID cr) cid w) cids)
|