Use wielded items to calculate damage

Use whatever items the character has wielded, if any, to calculate the
damage they deal when attacking. Currently this shortcuts handedness to
just use the *first* item they have equipped, which is fine since it's
currently only possible to equip something in the right hand.
This commit is contained in:
Griffin Smith 2019-12-23 10:47:09 -05:00
parent 6622dd3018
commit 8ecefddbd4
2 changed files with 35 additions and 26 deletions

View file

@ -238,7 +238,7 @@ handleCommand ShowInventory = showPanel InventoryPanel >> continue
handleCommand Wield = do handleCommand Wield = do
uses (character . inventory . backpack) uses (character . inventory . backpack)
(V.mapMaybe (\item -> (V.mapMaybe (\item ->
(WieldedItem item) <$> item ^. Item.itemType . wieldable)) WieldedItem item <$> item ^. Item.itemType . wieldable))
>>= \case >>= \case
Empty -> say_ ["wield", "nothing"] Empty -> say_ ["wield", "nothing"]
wieldables -> wieldables ->
@ -431,7 +431,7 @@ attackAt pos =
$ \(MenuResult creature) -> attackCreature creature $ \(MenuResult creature) -> attackCreature creature
where where
attackCreature (creatureID, creature) = do attackCreature (creatureID, creature) = do
charDamage <- use $ character . characterDamage charDamage <- uses character characterDamage
let creature' = Creature.damage charDamage creature let creature' = Creature.damage charDamage creature
msgParams = object ["creature" A..= creature'] msgParams = object ["creature" A..= creature']
if Creature.isDead creature' if Creature.isDead creature'

View file

@ -37,20 +37,23 @@ module Xanthous.Entities.Character
-------------------------------------------------------------------------------- --------------------------------------------------------------------------------
import Xanthous.Prelude import Xanthous.Prelude
-------------------------------------------------------------------------------- --------------------------------------------------------------------------------
import Test.QuickCheck import Brick
import Test.QuickCheck.Instances.Vector () import Data.Aeson.Generic.DerivingVia
import Test.QuickCheck.Arbitrary.Generic import Data.Aeson (ToJSON, FromJSON)
import Brick import Data.Coerce (coerce)
import Data.Aeson.Generic.DerivingVia import Test.QuickCheck
import Data.Aeson (ToJSON, FromJSON) import Test.QuickCheck.Instances.Vector ()
import Data.Coerce (coerce) import Test.QuickCheck.Arbitrary.Generic
-------------------------------------------------------------------------------- --------------------------------------------------------------------------------
import Xanthous.Util.QuickCheck import Xanthous.Util.QuickCheck
import Xanthous.Game.State import Xanthous.Game.State
import Xanthous.Entities.Item import Xanthous.Entities.Item
import Xanthous.Data import Xanthous.Data
(TicksPerTile, Hitpoints, Per, Ticks, (|*|), positioned, Positioned(..)) ( TicksPerTile, Hitpoints, Per, Ticks, (|*|), positioned
import Xanthous.Entities.RawTypes (WieldableItem, wieldable) , Positioned(..)
)
import Xanthous.Entities.RawTypes (WieldableItem, wieldable)
import qualified Xanthous.Entities.RawTypes as Raw
-------------------------------------------------------------------------------- --------------------------------------------------------------------------------
data WieldedItem = WieldedItem data WieldedItem = WieldedItem
@ -116,11 +119,9 @@ doubleHanded = prism' DoubleHanded $ \case
DoubleHanded i -> Just i DoubleHanded i -> Just i
_ -> Nothing _ -> Nothing
wieldedItems :: Traversal' Wielded Item wieldedItems :: Traversal' Wielded WieldedItem
wieldedItems k (DoubleHanded wielded) = DoubleHanded <$> wieldedItem k wielded wieldedItems k (DoubleHanded wielded) = DoubleHanded <$> k wielded
wieldedItems k (Hands l r) = Hands wieldedItems k (Hands l r) = Hands <$> _Just k l <*> _Just k r
<$> (_Just . wieldedItem) k l
<*> (_Just . wieldedItem) k r
data Inventory = Inventory data Inventory = Inventory
{ _backpack :: Vector Item { _backpack :: Vector Item
@ -137,7 +138,7 @@ makeFieldsNoPrefix ''Inventory
items :: Traversal' Inventory Item items :: Traversal' Inventory Item
items k (Inventory bp w) = Inventory items k (Inventory bp w) = Inventory
<$> traversed k bp <$> traversed k bp
<*> wieldedItems k w <*> (wieldedItems . wieldedItem) k w
type instance Element Inventory = Item type instance Element Inventory = Item
@ -165,15 +166,15 @@ instance Semigroup Inventory where
let backpack' = inv ^. backpack <> inv ^. backpack let backpack' = inv ^. backpack <> inv ^. backpack
(wielded', backpack'') = case (inv ^. wielded, inv ^. wielded) of (wielded', backpack'') = case (inv ^. wielded, inv ^. wielded) of
(wielded, wielded@(DoubleHanded _)) -> (wielded, wielded@(DoubleHanded _)) ->
(wielded, backpack' <> fromList (wielded ^.. wieldedItems)) (wielded, backpack' <> fromList (wielded ^.. wieldedItems . wieldedItem))
(wielded, wielded@(Hands (Just _) (Just _))) -> (wielded, wielded@(Hands (Just _) (Just _))) ->
(wielded, backpack' <> fromList (wielded ^.. wieldedItems)) (wielded, backpack' <> fromList (wielded ^.. wieldedItems . wieldedItem))
(wielded, Hands Nothing Nothing) -> (wielded, backpack') (wielded, Hands Nothing Nothing) -> (wielded, backpack')
(Hands Nothing Nothing, wielded) -> (wielded, backpack') (Hands Nothing Nothing, wielded) -> (wielded, backpack')
(Hands (Just l) Nothing, Hands Nothing (Just r)) -> (Hands (Just l) Nothing, Hands Nothing (Just r)) ->
(Hands (Just l) (Just r), backpack') (Hands (Just l) (Just r), backpack')
(wielded@(DoubleHanded _), wielded) -> (wielded@(DoubleHanded _), wielded) ->
(wielded, backpack' <> fromList (wielded ^.. wieldedItems)) (wielded, backpack' <> fromList (wielded ^.. wieldedItems . wieldedItem))
(Hands Nothing (Just r), Hands Nothing (Just r)) -> (Hands Nothing (Just r), Hands Nothing (Just r)) ->
(Hands Nothing (Just r), r ^. wieldedItem <| backpack') (Hands Nothing (Just r), r ^. wieldedItem <| backpack')
(Hands Nothing r, Hands (Just l) Nothing) -> (Hands Nothing r, Hands (Just l) Nothing) ->
@ -194,7 +195,6 @@ instance Monoid Inventory where
data Character = Character data Character = Character
{ _inventory :: !Inventory { _inventory :: !Inventory
, _characterName :: !(Maybe Text) , _characterName :: !(Maybe Text)
, _characterDamage :: !Hitpoints
, _characterHitpoints' :: !Double , _characterHitpoints' :: !Double
, _speed :: TicksPerTile , _speed :: TicksPerTile
} }
@ -245,11 +245,20 @@ mkCharacter :: Character
mkCharacter = Character mkCharacter = Character
{ _inventory = mempty { _inventory = mempty
, _characterName = Nothing , _characterName = Nothing
, _characterDamage = 1
, _characterHitpoints' = fromIntegral initialHitpoints , _characterHitpoints' = fromIntegral initialHitpoints
, _speed = defaultSpeed , _speed = defaultSpeed
} }
defaultCharacterDamage :: Hitpoints
defaultCharacterDamage = 1
-- | Returns the damage that the character currently does with an attack
-- TODO use double-handed/left-hand/right-hand here
characterDamage :: Character -> Hitpoints
characterDamage
= fromMaybe defaultCharacterDamage
. preview (inventory . wielded . wieldedItems . wieldableItem . Raw.damage)
isDead :: Character -> Bool isDead :: Character -> Bool
isDead = (== 0) . characterHitpoints isDead = (== 0) . characterHitpoints