Jumpbacks and continue

This commit is contained in:
Tibo De Peuter 2022-12-22 09:43:17 +01:00
parent dab6fadad4
commit b7278d6afc
11 changed files with 59 additions and 44 deletions

View file

@ -11,35 +11,37 @@ import RPGEngine.Render.Core ( Renderer )
-- A game is the base data container. -- A game is the base data container.
data Game = Game { data Game = Game {
state :: State, state :: State
levels :: [Level],
player :: Player
} }
------------------------------- State -------------------------------- ------------------------------- State --------------------------------
-- Code reusability -- Code reusability
data StateBase = StateBase { data StateBase = StateBase {
renderer :: Renderer Game, renderer :: Renderer State,
inputHandler :: InputHandler Game inputHandler :: InputHandler Game
} }
-- Main menu -- Main menu
data State = Menu { base :: StateBase } data State = Menu { base :: StateBase }
-- Select the level you want to play -- Select the level you want to play
| LevelSelection { base :: StateBase, | LevelSelection { base :: StateBase,
levelList :: [FilePath], levelList :: [FilePath],
selector :: ListSelector } selector :: ListSelector }
-- Playing a level -- Playing a level
| Playing { base :: StateBase, | Playing { base :: StateBase,
level :: Level } levels :: [Level],
level :: Level,
player :: Player,
restart :: State }
-- Paused while playing a level -- Paused while playing a level
| Paused { base :: StateBase, | Paused { base :: StateBase,
level :: Level } continue :: State }
-- Won a level -- Won a level
| Win { base :: StateBase } | Win { base :: StateBase }
-- Lost a level -- Lost a level
| Lose { base :: StateBase } | Lose { base :: StateBase,
restart :: State }
------------------------------- Level -------------------------------- ------------------------------- Level --------------------------------

View file

@ -6,15 +6,15 @@ import RPGEngine.Data
( Player(Player, position), ( Player(Player, position),
Direction, Direction,
Physical(Exit, Walkable, Entrance), Physical(Exit, Walkable, Entrance),
State(Playing, level), State(..),
Game(Game, state, player) ) Game(..) )
import RPGEngine.Data.Level (findAt, directionOffsets) import RPGEngine.Data.Level (findAt, directionOffsets)
------------------------------ Exported ------------------------------ ------------------------------ Exported ------------------------------
-- Check if a move is legal by checking what is located at the new position. -- Check if a move is legal by checking what is located at the new position.
isLegalMove :: Direction -> Game -> Bool isLegalMove :: Direction -> Game -> Bool
isLegalMove dir g@Game{ state = Playing { level = lvl }, player = p@Player{ position = (x, y) }} = legality isLegalMove dir g@Game{ state = Playing { level = lvl, player = p@Player{ position = (x, y) }}} = legality
where legality = physical `elem` [Walkable, Entrance, Exit] where legality = physical `elem` [Walkable, Entrance, Exit]
physical = findAt newPos lvl physical = findAt newPos lvl
newPos = (x + xD, y + yD) newPos = (x + xD, y + yD)

View file

@ -2,11 +2,16 @@ module RPGEngine.Input.Paused
( handleInputPaused ( handleInputPaused
) where ) where
import RPGEngine.Input.Core ( InputHandler ) import RPGEngine.Input.Core ( InputHandler, handleAnyKey )
import RPGEngine.Data ( Game ) import RPGEngine.Data ( Game (..), State (..) )
------------------------------ Exported ------------------------------ ------------------------------ Exported ------------------------------
handleInputPaused :: InputHandler Game handleInputPaused :: InputHandler Game
handleInputPaused = undefined handleInputPaused = handleAnyKey continueGame
continueGame :: Game -> Game
continueGame g@Game{ state = Paused{ continue = state }} = newGame
where newGame = g{ state = state }
continueGame g = g

View file

@ -15,7 +15,7 @@ import RPGEngine.Data
Level(Level, layout), Level(Level, layout),
State(..), State(..),
StateBase(StateBase, renderer, inputHandler), StateBase(StateBase, renderer, inputHandler),
Game(Game, state, player) ) Game(..) )
import RPGEngine.Data.Level ( findFirstOf, directionOffsets ) import RPGEngine.Data.Level ( findFirstOf, directionOffsets )
import RPGEngine.Data.Game ( isLegalMove ) import RPGEngine.Data.Game ( isLegalMove )
import RPGEngine.Input.Paused ( handleInputPaused ) import RPGEngine.Input.Paused ( handleInputPaused )
@ -53,19 +53,22 @@ spawnPlayer l@Level{ layout = lay } p@Player{ position = prevPos } = p{ position
---------------------------------------------------------------------- ----------------------------------------------------------------------
pauseGame :: Game -> Game pauseGame :: Game -> Game
pauseGame g@Game{ state = Playing{ level = level } } = pausedGame pauseGame g@Game{ state = playing@Playing{} } = pausedGame
where pausedGame = g{ state = pausedState } where pausedGame = g{ state = pausedState }
pausedState = Paused{ base = newBase, level = level } pausedState = Paused{ base = newBase, continue = playing }
newBase = StateBase { renderer = renderPaused, inputHandler = handleInputPaused } newBase = StateBase { renderer = renderPaused, inputHandler = handleInputPaused }
pauseGame g = g
-- Move a player in a direction if possible. -- Move a player in a direction if possible.
movePlayer :: Direction -> Game -> Game movePlayer :: Direction -> Game -> Game
movePlayer dir g@Game{ player = p@Player{ position = (x, y) }} = newGame movePlayer dir g@Game{ state = s@Playing{ player = p@Player{ position = (x, y) }}} = newGame
where newGame = g{ player = newPlayer } where newGame = g{ state = newState }
newState = s{ player = newPlayer }
newPlayer = p{ position = newCoord } newPlayer = p{ position = newCoord }
newCoord | isLegalMove dir g = (x + xD, y + yD) newCoord | isLegalMove dir g = (x + xD, y + yD)
| otherwise = (x, y) | otherwise = (x, y)
(xD, yD) = directionOffsets dir (xD, yD) = directionOffsets dir
movePlayer _ g = g
-- TODO -- TODO
goToNextLevel :: Game -> Game goToNextLevel :: Game -> Game

View file

@ -26,13 +26,14 @@ initWindow = InWindow
-- Initialize the game -- Initialize the game
initGame :: Game initGame :: Game
initGame = Game { initGame = Game {
state = Menu{ base = StateBase{ renderer = renderMenu, inputHandler = handleInputMenu }}, state = Menu{ base = StateBase{
levels = [defaultLevel], renderer = renderMenu,
player = spawnPlayer defaultLevel defaultPlayer inputHandler = handleInputMenu
}}
} }
-- Render all different states -- Render all different states
render :: Game -> Picture render :: Game -> Picture
render g@Game{ state = state } = renderFunc g render g@Game{ state = state } = renderFunc state
where stateBase = base state where stateBase = base state
renderFunc = renderer stateBase renderFunc = renderer stateBase

View file

@ -15,8 +15,8 @@ import Graphics.Gloss.Data.Color (red)
------------------------------ Exported ------------------------------ ------------------------------ Exported ------------------------------
renderLevelSelection :: Renderer Game renderLevelSelection :: Renderer State
renderLevelSelection Game{ state = state } = result renderLevelSelection state = result
where result = renderLevelList state where result = renderLevelList state
---------------------------------------------------------------------- ----------------------------------------------------------------------

View file

@ -4,11 +4,11 @@ module RPGEngine.Render.Lose
import RPGEngine.Render.Core ( Renderer ) import RPGEngine.Render.Core ( Renderer )
import RPGEngine.Data ( Game ) import RPGEngine.Data ( State )
import Graphics.Gloss ( text ) import Graphics.Gloss ( text )
---------------------------------------------------------------------- ----------------------------------------------------------------------
-- TODO -- TODO
renderLose :: Renderer Game renderLose :: Renderer State
renderLose _ = text "Win" renderLose _ = text "Win"

View file

@ -4,11 +4,11 @@ module RPGEngine.Render.Menu
import RPGEngine.Render.Core ( Renderer ) import RPGEngine.Render.Core ( Renderer )
import RPGEngine.Data ( Game ) import RPGEngine.Data ( State )
import Graphics.Gloss (text) import Graphics.Gloss (text)
---------------------------------------------------------------------- ----------------------------------------------------------------------
-- TODO -- TODO
renderMenu :: Renderer Game renderMenu :: Renderer State
renderMenu _ = text "[Press any key to start]" renderMenu _ = text "[Press any key to start]"

View file

@ -4,7 +4,7 @@ module RPGEngine.Render.Paused
import RPGEngine.Render.Core ( Renderer, overlay ) import RPGEngine.Render.Core ( Renderer, overlay )
import RPGEngine.Data ( Game ) import RPGEngine.Data ( State (..) )
import Graphics.Gloss ( pictures, scale, text ) import Graphics.Gloss ( pictures, scale, text )
import RPGEngine.Render.Playing ( renderPlaying ) import RPGEngine.Render.Playing ( renderPlaying )
import Graphics.Gloss.Data.Picture (color) import Graphics.Gloss.Data.Picture (color)
@ -12,9 +12,10 @@ import Graphics.Gloss.Data.Color (white)
------------------------------ Exported ------------------------------ ------------------------------ Exported ------------------------------
renderPaused :: Renderer Game renderPaused :: Renderer State
renderPaused g = pictures [renderPlaying g, pause] renderPaused state = pictures [playing, pause]
where pause = pictures [ where playing = renderPlaying $ continue state
pause = pictures [
overlay, overlay,
color white $ scale 0.5 0.5 $ text "[Press any key to continue]" color white $ scale 0.5 0.5 $ text "[Press any key to continue]"
] ]

View file

@ -16,14 +16,17 @@ import RPGEngine.Data
import Graphics.Gloss ( Picture, pictures ) import Graphics.Gloss ( Picture, pictures )
import Graphics.Gloss.Data.Picture (translate) import Graphics.Gloss.Data.Picture (translate)
import RPGEngine.Config (resolution, zoom) import RPGEngine.Config (resolution, zoom)
import Graphics.Gloss (text)
import Graphics.Gloss (blank)
------------------------------ Exported ------------------------------ ------------------------------ Exported ------------------------------
renderPlaying :: Renderer Game renderPlaying :: Renderer State
renderPlaying g@Game{ state = Playing { level = lvl }, player = player } = pictures [ renderPlaying Playing { level = lvl, player = player } = pictures [
renderLevel lvl, renderLevel lvl,
renderPlayer player renderPlayer player
] ]
renderPlaying _ = blank
------------------------------- Player ------------------------------- ------------------------------- Player -------------------------------
@ -35,7 +38,7 @@ renderPlayer Player{ position = (x, y) } = move picture
-- Center the player in the middle of the screen. -- Center the player in the middle of the screen.
-- Not in use at the moment, might be useful later. -- Not in use at the moment, might be useful later.
focusPlayer :: Game -> Picture -> Picture focusPlayer :: Game -> Picture -> Picture
focusPlayer Game{ player = Player{ position = (x, y)}} = move focusPlayer Game{ state = Playing{ player = Player{ position = (x, y) }}} = move
where move = translate centerX centerY where move = translate centerX centerY
centerX = resolution * zoom * fromIntegral (negate x) centerX = resolution * zoom * fromIntegral (negate x)
centerY = resolution * zoom * fromIntegral (negate y) centerY = resolution * zoom * fromIntegral (negate y)

View file

@ -4,11 +4,11 @@ module RPGEngine.Render.Win
import RPGEngine.Render.Core ( Renderer ) import RPGEngine.Render.Core ( Renderer )
import RPGEngine.Data ( Game ) import RPGEngine.Data ( State )
import Graphics.Gloss (text) import Graphics.Gloss (text)
---------------------------------------------------------------------- ----------------------------------------------------------------------
-- TODO -- TODO
renderWin :: Renderer Game renderWin :: Renderer State
renderWin _ = text "Win" renderWin _ = text "Win"