Skip to content

Commit

Permalink
[Broken] Working on Entities
Browse files Browse the repository at this point in the history
  • Loading branch information
Ashe committed Mar 31, 2018
1 parent 6bef3ef commit 42ef9fe
Show file tree
Hide file tree
Showing 4 changed files with 98 additions and 58 deletions.
35 changes: 7 additions & 28 deletions src/Entity.hs
Expand Up @@ -2,11 +2,9 @@
{-# LANGUAGE PatternSynonyms #-}
module Entity
( Entity(Entity)
, position
, velocity
, tag
, animation
, frame
, eID
, update
, render
) where

import Control.Monad
Expand All @@ -15,29 +13,10 @@ import SDL.Vect
import SDL (($=))
import qualified SDL
import qualified SDL.Image
import Data.List (foldl')
import SDL.Raw.Timer as SDL hiding (delay)
import Text.Pretty.Simple

-- The fundamental structures of all our objects in the game
data Entity =
Entity
{ position :: Point V2 CDouble
, velocity :: V2 CDouble
, tag :: String
, animation :: String
, frame :: Int
} deriving (Show, Eq)


-- Our initial guy starts out with him roughly in the middle
initialGuy :: (CDouble, CDouble) -> Entity
initialGuy pos =
Entity
{ position = P $ V2 (fst pos) (snd pos)
, velocity = V2 0 0
, tag = "male"
, animation = "idle"
, frame = 0
}

{ eID :: Int
, update :: CDouble -> Entity
, render :: IO ()
}
11 changes: 11 additions & 0 deletions src/GameState.hs
Expand Up @@ -5,6 +5,8 @@ module GameState
, initialState
, entities
, options
, updateGameState
, renderGameState
, initialOptions
, screenRes
, frameLimit
Expand Down Expand Up @@ -58,3 +60,12 @@ processEvent :: SDL.EventPayload -> Maybe (SDL.Keycode, Bool)
processEvent (SDL.KeyboardEvent (SDL.KeyboardEventData _ SDL.Pressed False (SDL.Keysym _ code _))) = Just (code, True)
processEvent (SDL.KeyboardEvent (SDL.KeyboardEventData _ SDL.Released _ (SDL.Keysym _ code _))) = Just (code, False)
processEvent _ = Nothing

-- Updates the game state's entities
updateGameState :: GameState -> CDouble -> GameState
updateGameState state delta = state { entities = map (\(Entity _ up _) -> up delta) (entities state)}

-- Renders the game state's entities
renderGameState :: GameState -> IO [()]
renderGameState state = sequence $ map (\(Entity _ _ rend) -> rend) $ entities state
-- SDL.copy renderer player (getCurrentFrame newAnimState) $ Just $ SDL.Rectangle (truncate <$> position (entities newState)) (V2 100 100)
57 changes: 57 additions & 0 deletions src/Guy.hs
@@ -0,0 +1,57 @@
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE PatternSynonyms #-}
module Guy
( Guy(Guy)
, position
, velocity
, tag
, animation
, guy
, updateGuy
) where

import Control.Monad
import Foreign.C.Types
import SDL.Vect
import qualified SDL

import Entity
import SDLAnimations

-- The fundamental structures of all our objects in the game
data Guy =
Guy
{ position :: V2 CDouble
, velocity :: V2 CDouble
, tag :: String
, animation :: AnimationState
} deriving (Show)

guy :: Guy -> Int -> Entity
guy g i =
Entity
{ eID = i
, update = flip guy i . updateGuy g
, render = print (i)
}

updateGuy :: Guy -> CDouble -> Guy
updateGuy guy dt =
guy
{ position =
let (V2 newPosX newPosY) = position guy + velocity guy * V2 dt dt
in V2 newPosX newPosY
, animation = updateAnimationState dt 0.1 (animation guy)
}

-- -- Our initial guy starts out with him roughly in the middle
-- initialGuy :: (CDouble, CDouble) -> Entity
-- initialGuy pos =
-- Entity
-- { position = P $ V2 (fst pos) (snd pos)
-- , velocity = V2 0 0
-- , tag = "male"
-- , animation = "idle"
-- , frame = 0
-- }

53 changes: 23 additions & 30 deletions src/Main.hs
Expand Up @@ -16,6 +16,8 @@ import GameState
import SDLAnimations
import InputModule

import Guy

import Paths_FirstGameHS(getDataFileName)

jumpVelocity :: V2 CDouble
Expand All @@ -27,14 +29,6 @@ walkingSpeed = V2 300 0
gravity :: V2 CDouble
gravity = V2 0 300

updateWorld :: CDouble -> GameState -> GameState
updateWorld delta state@(State (Options res _ _) (Guy (P pos) vel tag anim frame)) =
let (V2 newPosX newPosY) = pos + (gravity + vel) * V2 delta delta
fixedX = max 0 $ min newPosX (fromIntegral (fst res) - 50)
fixedY = max 0 $ min (fromIntegral (snd res) - 100) newPosY
in state {entities = Guy (P $ V2 fixedX fixedY) vel tag anim frame }


-- Takes file and creates a texture out of it
getTextureFromImg :: SDL.Renderer -> FilePath -> IO SDL.Texture
getTextureFromImg renderer img = do
Expand All @@ -50,21 +44,23 @@ main = do
SDL.initialize [SDL.InitVideo]

-- Set up the first state
let jump state@(State _ oldGuy@(Guy _ curVel _ _ _)) = state { entities = oldGuy { velocity = curVel * V2 1 0 + jumpVelocity }}
fall state@(State _ oldGuy@(Guy _ curVel _ _ _)) = state { entities = oldGuy { velocity = curVel - jumpVelocity }}
right state@(State _ oldGuy@(Guy _ curVel _ _ _)) = state { entities = oldGuy { velocity = walkingSpeed + curVel }}
left state@(State _ oldGuy@(Guy _ curVel _ _ _)) = state { entities = oldGuy { velocity = curVel - walkingSpeed }}

initOptions = initialOptions { keybindings =
addBatchBindings
[ ((SDL.KeycodeUp, True), Just jump)
, ((SDL.KeycodeUp, False), Just fall)
, ((SDL.KeycodeRight, True), Just right)
, ((SDL.KeycodeRight, False), Just left)
, ((SDL.KeycodeLeft, True), Just left)
, ((SDL.KeycodeLeft, False), Just right)
] blankKeyBindings }
state = initialState { options = initOptions }
-- let jump p@(Guy _ curVel _ _) = p { velocity = curVel * V2 1 0 + jumpVelocity }
-- fall p@(Guy _ curVel _ _) = p { velocity = curVel - jumpVelocity }
-- right p@(Guy _ curVel _ _) = p { velocity = walkingSpeed + curVel }
-- left p@(Guy _ curVel _ _) = p { velocity = curVel - walkingSpeed }
--
-- initOptions = initialOptions { keybindings =
-- addBatchBindings
-- [ ((SDL.KeycodeUp, True), Just (\s@(GameState _ es) -> s {entities = jump (head es) : tail es}))
-- , ((SDL.KeycodeUp, False), Just fall)
-- , ((SDL.KeycodeRight, True), Just right)
-- , ((SDL.KeycodeRight, False), Just left)
-- , ((SDL.KeycodeLeft, True), Just left)
-- , ((SDL.KeycodeLeft, False), Just right)
-- ] blankKeyBindings }
-- state = initialState { options = initOptions }

let state = initialState

-- Create a window with the correct screensize and make it appear
window <- SDL.createWindow "FirstGameHS"
Expand All @@ -89,11 +85,10 @@ main = do
animsList <- loadAnimations "Assets/rogue.json"
let animationSet = getAnimationSet "rogue" "male" =<< animsList
animation = getAnimation "walk" =<< animationSet
frame = fmap (getFrame 0) animation
initAnimationState =
AnimationState animationSet animation [] "idle" 0 0

let loop lastTicks state animState = do
let loop lastTicks state = do

ticks <- SDL.getTicks
events <- SDL.pollEvents
Expand All @@ -104,22 +99,20 @@ main = do

-- Update functions
let worldAfterInput = foldl' processInput state payloads
newState = updateWorld delta worldAfterInput
newAnimState = updateAnimationState delta 0.1 animState
newState = updateGameState worldAfterInput delta

-- Render functions (Background and player)
SDL.copy renderer texture Nothing Nothing
SDL.copy renderer player (getCurrentFrame newAnimState) $ Just $ SDL.Rectangle (truncate <$> position (entities newState)) (V2 100 100)

-- Delay time until next frame to save processing power
let frameDelay = 1000 / fromIntegral (frameLimit (options newState))
when (delta < frameDelay) $ SDL.delay (truncate $ frameDelay - delta)

SDL.present renderer
unless quit $ loop ticks newState newAnimState
unless quit $ loop ticks newState

ticks <- SDL.getTicks
loop ticks state initAnimationState
loop ticks state

SDL.destroyWindow window
SDL.quit
Expand Down

0 comments on commit 42ef9fe

Please sign in to comment.