#9 Added level selection render
This commit is contained in:
parent
0786a41006
commit
2055ef234e
17 changed files with 401 additions and 34 deletions
34
README.md
34
README.md
|
@ -64,7 +64,7 @@ TODO
|
||||||
|
|
||||||
- An example playthrough, with pictures and explanations
|
- An example playthrough, with pictures and explanations
|
||||||
|
|
||||||
\pagebreak
|
<div style="page-break-after: always; visibility: hidden">\pagebreak</div>
|
||||||
|
|
||||||
## Writing your own stages
|
## Writing your own stages
|
||||||
|
|
||||||
|
@ -250,10 +250,22 @@ If we look at the example, all the objects are
|
||||||
Entry = empty ConditionList + Action ('leave()')
|
Entry = empty ConditionList + Action ('leave()')
|
||||||
```
|
```
|
||||||
|
|
||||||
\pagebreak
|
<div style="page-break-after: always; visibility: hidden">\pagebreak</div>
|
||||||
|
|
||||||
## Development notes
|
## Development notes
|
||||||
|
|
||||||
|
### Engine architecture
|
||||||
|
|
||||||
|
<mark>TODO</mark>
|
||||||
|
|
||||||
|
#### Monads/Monad stack
|
||||||
|
|
||||||
|
<mark>TODO</mark>
|
||||||
|
|
||||||
|
### Tests
|
||||||
|
|
||||||
|
<mark>TODO</mark>
|
||||||
|
|
||||||
### Assets & dependencies
|
### Assets & dependencies
|
||||||
|
|
||||||
The following assets were used (and modified if specified):
|
The following assets were used (and modified if specified):
|
||||||
|
@ -268,6 +280,7 @@ The following assets were used (and modified if specified):
|
||||||
|
|
||||||
RPG-Engine makes use of the following libraries:
|
RPG-Engine makes use of the following libraries:
|
||||||
|
|
||||||
|
- [directory](https://hackage.haskell.org/package/directory) for listing levels in a directory
|
||||||
- [gloss](https://hackage.haskell.org/package/gloss) for game rendering
|
- [gloss](https://hackage.haskell.org/package/gloss) for game rendering
|
||||||
- [gloss-juicy](https://hackage.haskell.org/package/gloss-juicy) for rendering images
|
- [gloss-juicy](https://hackage.haskell.org/package/gloss-juicy) for rendering images
|
||||||
- [hspec](https://hackage.haskell.org/package/hspec) for testing
|
- [hspec](https://hackage.haskell.org/package/hspec) for testing
|
||||||
|
@ -278,12 +291,23 @@ RPG-Engine makes use of the following libraries:
|
||||||
|
|
||||||
The following ideas could (or should) be implemented in the future of this project.
|
The following ideas could (or should) be implemented in the future of this project.
|
||||||
|
|
||||||
- [ ] Entity system: With en ES, you can implement moving entities and repeated input. It also resembles the typical
|
- [ ] **Entity system:** With en ES, you can implement moving entities and repeated input. It also resembles the typical
|
||||||
game loop more closely which can make it easier to implement other ideas in the future.
|
game loop more closely which can make it easier to implement other ideas in the future.
|
||||||
|
- [ ] **Game music:** Ambient game music and sound effects can improve the gaming experience I think.
|
||||||
|
- [ ] **Expand configuration file:** Implement the same methods for parsing stage description files to a configuration file,
|
||||||
|
containing keybinds, dimension sizes, even window titles, making this a truly customizable engine.
|
||||||
|
- [ ] **Camera follows player:** The camera should follow the player, making it always center. This allows for larger levels
|
||||||
|
increases the immersion of the game.
|
||||||
|
|
||||||
- [ ] Game music: Ambient game music and sound effects can improve the gaming experience I think.
|
<div style="page-break-after: always; visibility: hidden">\pagebreak</div>
|
||||||
|
|
||||||
\pagebreak
|
## Conclusion
|
||||||
|
|
||||||
|
Parsing was way harder than I initially expected. About half of my time on this project was spent writing the parser.
|
||||||
|
|
||||||
|
<mark>TODO</mark>
|
||||||
|
|
||||||
|
<div style="page-break-after: always; visibility: hidden">\pagebreak</div>
|
||||||
|
|
||||||
## References
|
## References
|
||||||
|
|
||||||
|
|
BIN
assets/environment/overlay.png
Normal file
BIN
assets/environment/overlay.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 494 B |
Before Width: | Height: | Size: 870 B After Width: | Height: | Size: 870 B |
|
@ -19,8 +19,8 @@ levels: [
|
||||||
items: [
|
items: [
|
||||||
{
|
{
|
||||||
id: "key",
|
id: "key",
|
||||||
x: 1,
|
x: 0,
|
||||||
y: 2,
|
y: 1,
|
||||||
name: "Sleutel",
|
name: "Sleutel",
|
||||||
description: "Deze sleutel kan een deur openen",
|
description: "Deze sleutel kan een deur openen",
|
||||||
useTimes: 1,
|
useTimes: 1,
|
||||||
|
@ -35,8 +35,8 @@ levels: [
|
||||||
entities: [
|
entities: [
|
||||||
{
|
{
|
||||||
id: "door",
|
id: "door",
|
||||||
x: 1,
|
x: 0,
|
||||||
y: 4,
|
y: 3,
|
||||||
name: "Deur",
|
name: "Deur",
|
||||||
description: "Deze deur kan geopend worden met een sleutel",
|
description: "Deze deur kan geopend worden met een sleutel",
|
||||||
direction: up,
|
direction: up,
|
||||||
|
|
|
@ -69,8 +69,8 @@ levels: [
|
||||||
|
|
||||||
actions: {
|
actions: {
|
||||||
[inventoryContains(potion)] increasePlayerHp(potion),
|
[inventoryContains(potion)] increasePlayerHp(potion),
|
||||||
[inventoryContains(sword)] decreaseHp(m1, sword),
|
[inventoryContains(sword)] decreaseHp(devil, sword),
|
||||||
[] decreaseHp(m1, dagger),
|
[] decreaseHp(devil, dagger),
|
||||||
[] leave()
|
[] leave()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
134
levels/level4.txt
Normal file
134
levels/level4.txt
Normal file
|
@ -0,0 +1,134 @@
|
||||||
|
player: {
|
||||||
|
hp: 50,
|
||||||
|
inventory: [
|
||||||
|
{
|
||||||
|
id: "dagger",
|
||||||
|
x: 0,
|
||||||
|
y: 0,
|
||||||
|
name: "Dolk",
|
||||||
|
description: "Basis schade tegen monsters",
|
||||||
|
useTimes: infinite,
|
||||||
|
value: 10,
|
||||||
|
|
||||||
|
actions: {}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
levels: [
|
||||||
|
{
|
||||||
|
layout: {
|
||||||
|
| * * * * * *
|
||||||
|
| * s . . e *
|
||||||
|
| * * * * * *
|
||||||
|
},
|
||||||
|
|
||||||
|
items: [],
|
||||||
|
|
||||||
|
entities: []
|
||||||
|
},
|
||||||
|
{
|
||||||
|
layout: {
|
||||||
|
| * * *
|
||||||
|
| * e *
|
||||||
|
| * . *
|
||||||
|
| * . *
|
||||||
|
| * . *
|
||||||
|
| * . *
|
||||||
|
| * s *
|
||||||
|
| * * *
|
||||||
|
},
|
||||||
|
|
||||||
|
items: [
|
||||||
|
{
|
||||||
|
id: "key",
|
||||||
|
x: 0,
|
||||||
|
y: 1,
|
||||||
|
name: "Sleutel",
|
||||||
|
description: "Deze sleutel kan een deur openen",
|
||||||
|
useTimes: 1,
|
||||||
|
value: 0,
|
||||||
|
actions: {
|
||||||
|
[not(inventoryFull())] retrieveItem(key),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
|
||||||
|
entities: [
|
||||||
|
{
|
||||||
|
id: "door",
|
||||||
|
x: 0,
|
||||||
|
y: 3,
|
||||||
|
name: "Deur",
|
||||||
|
description: "Deze deur kan geopend worden met een sleutel",
|
||||||
|
direction: up,
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
[inventoryContains(key)] useItem(key),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
layout: {
|
||||||
|
| * * * * * * * *
|
||||||
|
| * . . . . . . *
|
||||||
|
| * s . . . . . *
|
||||||
|
| * . . . . . e *
|
||||||
|
| * . . . . . . *
|
||||||
|
| * * * * * * * *
|
||||||
|
},
|
||||||
|
|
||||||
|
items: [
|
||||||
|
{
|
||||||
|
id: "sword",
|
||||||
|
x: 2,
|
||||||
|
y: 3,
|
||||||
|
name: "Zwaard",
|
||||||
|
description: "Meer schade tegen monsters",
|
||||||
|
useTimes: infinite,
|
||||||
|
value: 25,
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
[not(inventoryFull())] retrieveItem(sword),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: "potion",
|
||||||
|
x: 3,
|
||||||
|
y: 1,
|
||||||
|
name: "Levensbrouwsel",
|
||||||
|
description: "Geeft een aantal levenspunten terug",
|
||||||
|
useTimes: 1,
|
||||||
|
value: 50,
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
[not(inventoryFull())] retrieveItem(potion),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
|
||||||
|
entities: [
|
||||||
|
{
|
||||||
|
id: "devil",
|
||||||
|
x: 4,
|
||||||
|
y: 3,
|
||||||
|
name: "Duivel",
|
||||||
|
description: "Een monster uit de hel",
|
||||||
|
hp: 50,
|
||||||
|
value: 5,
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
[inventoryContains(potion)] increasePlayerHp(potion),
|
||||||
|
[inventoryContains(sword)] decreaseHp(devil, sword),
|
||||||
|
[] decreaseHp(devil, dagger),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
138
levels/level_more_levels.txt
Normal file
138
levels/level_more_levels.txt
Normal file
|
@ -0,0 +1,138 @@
|
||||||
|
# Dit gehele bestand is een Block
|
||||||
|
|
||||||
|
# Dit is een entry: key + value
|
||||||
|
player: { # Value is hier een block
|
||||||
|
hp: 50,
|
||||||
|
inventory: [ # BlockList
|
||||||
|
{
|
||||||
|
id: "dagger",
|
||||||
|
x: 0,
|
||||||
|
y: 0,
|
||||||
|
name: "Dolk",
|
||||||
|
description: "Basis schade tegen monsters",
|
||||||
|
useTimes: infinite,
|
||||||
|
value: 10,
|
||||||
|
|
||||||
|
actions: {}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
# Dit is een entry
|
||||||
|
levels: [
|
||||||
|
{
|
||||||
|
layout: {
|
||||||
|
| * * * * * *
|
||||||
|
| * s . . e *
|
||||||
|
| * * * * * *
|
||||||
|
},
|
||||||
|
|
||||||
|
items: [],
|
||||||
|
|
||||||
|
entities: []
|
||||||
|
},
|
||||||
|
{
|
||||||
|
layout: {
|
||||||
|
| * * *
|
||||||
|
| * e *
|
||||||
|
| * . *
|
||||||
|
| * . *
|
||||||
|
| * . *
|
||||||
|
| * . *
|
||||||
|
| * s *
|
||||||
|
| * * *
|
||||||
|
},
|
||||||
|
|
||||||
|
items: [
|
||||||
|
{
|
||||||
|
id: "key",
|
||||||
|
x: 1,
|
||||||
|
y: 2,
|
||||||
|
name: "Sleutel",
|
||||||
|
description: "Deze sleutel kan een deur openen",
|
||||||
|
useTimes: 1,
|
||||||
|
value: 0,
|
||||||
|
actions: {
|
||||||
|
[not(inventoryFull())] retrieveItem(key),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
|
||||||
|
entities: [
|
||||||
|
{
|
||||||
|
id: "door",
|
||||||
|
x: 1,
|
||||||
|
y: 4,
|
||||||
|
name: "Deur",
|
||||||
|
description: "Deze deur kan geopend worden met een sleutel",
|
||||||
|
direction: up,
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
[inventoryContains(key)] useItem(key),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
},
|
||||||
|
{
|
||||||
|
layout: {
|
||||||
|
| * * * * * * * *
|
||||||
|
| * . . . . . . *
|
||||||
|
| * s . . . . . *
|
||||||
|
| * . . . . . e *
|
||||||
|
| * . . . . . . *
|
||||||
|
| * * * * * * * *
|
||||||
|
},
|
||||||
|
|
||||||
|
items: [
|
||||||
|
{
|
||||||
|
id: "sword",
|
||||||
|
x: 2,
|
||||||
|
y: 3,
|
||||||
|
name: "Zwaard",
|
||||||
|
description: "Meer schade tegen monsters",
|
||||||
|
useTimes: infinite,
|
||||||
|
value: 25,
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
[not(inventoryFull())] retrieveItem(sword),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: "potion",
|
||||||
|
x: 3,
|
||||||
|
y: 1,
|
||||||
|
name: "Levensbrouwsel",
|
||||||
|
description: "Geeft een aantal levenspunten terug",
|
||||||
|
useTimes: 1,
|
||||||
|
value: 50,
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
[not(inventoryFull())] retrieveItem(potion),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
|
||||||
|
entities: [
|
||||||
|
{
|
||||||
|
id: "devil",
|
||||||
|
x: 4,
|
||||||
|
y: 3,
|
||||||
|
name: "Duivel",
|
||||||
|
description: "Een monster uit de hel",
|
||||||
|
hp: 50,
|
||||||
|
value: 5,
|
||||||
|
|
||||||
|
actions: {
|
||||||
|
[inventoryContains(potion)] increasePlayerHp(potion),
|
||||||
|
[inventoryContains(sword)] decreaseHp(m1, sword),
|
||||||
|
[] decreaseHp(m1, dagger),
|
||||||
|
[] leave()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
]
|
||||||
|
}
|
||||||
|
]
|
|
@ -48,6 +48,7 @@ instance Living Player where
|
||||||
|
|
||||||
-- Current state of the game.
|
-- Current state of the game.
|
||||||
data State = Menu
|
data State = Menu
|
||||||
|
| LvlSelect
|
||||||
| Playing
|
| Playing
|
||||||
| Pause
|
| Pause
|
||||||
| Win
|
| Win
|
||||||
|
|
|
@ -14,7 +14,7 @@ import RPGEngine.Data
|
||||||
|
|
||||||
-- Get the next state based on the current state
|
-- Get the next state based on the current state
|
||||||
nextState :: State -> State
|
nextState :: State -> State
|
||||||
nextState Menu = Playing
|
nextState Menu = LvlSelect
|
||||||
nextState Playing = Pause
|
nextState Playing = Pause
|
||||||
nextState Pause = Playing
|
nextState Pause = Playing
|
||||||
nextState _ = Menu
|
nextState _ = Menu
|
||||||
|
|
|
@ -15,8 +15,9 @@ import Graphics.Gloss.Interface.IO.Game
|
||||||
|
|
||||||
-- Handle all input for RPG-Engine
|
-- Handle all input for RPG-Engine
|
||||||
handleAllInput :: InputHandler Game
|
handleAllInput :: InputHandler Game
|
||||||
handleAllInput ev g@Game{ state = Playing } = handlePlayInputs ev g
|
handleAllInput ev g@Game{ state = Playing } = handlePlayInputs ev g
|
||||||
handleAllInput ev g = handleAnyKey setNextState ev g
|
handleAllInput ev g@Game{ state = LvlSelect } = handleLvlSelectInput ev g
|
||||||
|
handleAllInput ev g = handleAnyKey setNextState ev g
|
||||||
|
|
||||||
----------------------------------------------------------------------
|
----------------------------------------------------------------------
|
||||||
|
|
||||||
|
@ -38,6 +39,10 @@ handlePlayInputs = composeInputHandlers [
|
||||||
handleKey (Char 'a') $ movePlayer West
|
handleKey (Char 'a') $ movePlayer West
|
||||||
]
|
]
|
||||||
|
|
||||||
|
-- Input for selection a level to load
|
||||||
|
handleLvlSelectInput :: InputHandler Game
|
||||||
|
handleLvlSelectInput = composeInputHandlers []
|
||||||
|
|
||||||
-- Go to the next stage of the Game
|
-- Go to the next stage of the Game
|
||||||
setNextState :: Game -> Game
|
setNextState :: Game -> Game
|
||||||
setNextState game = game{ state = newState }
|
setNextState game = game{ state = newState }
|
||||||
|
|
12
lib/RPGEngine/Input/LvlSelect.hs
Normal file
12
lib/RPGEngine/Input/LvlSelect.hs
Normal file
|
@ -0,0 +1,12 @@
|
||||||
|
module RPGEngine.Input.LvlSelect
|
||||||
|
( getLvlList
|
||||||
|
) where
|
||||||
|
|
||||||
|
import GHC.IO (unsafePerformIO)
|
||||||
|
import System.Directory (getDirectoryContents)
|
||||||
|
|
||||||
|
lvlFolder :: FilePath
|
||||||
|
lvlFolder = "levels"
|
||||||
|
|
||||||
|
getLvlList :: [FilePath]
|
||||||
|
getLvlList = unsafePerformIO $ getDirectoryContents lvlFolder
|
|
@ -9,14 +9,24 @@ module RPGEngine.Render
|
||||||
|
|
||||||
import RPGEngine.Data
|
import RPGEngine.Data
|
||||||
( State(..),
|
( State(..),
|
||||||
Game(..) )
|
Game(..), Player (..) )
|
||||||
import RPGEngine.Render.Level
|
import RPGEngine.Render.Level
|
||||||
( renderLevel )
|
( renderLevel )
|
||||||
|
|
||||||
import Graphics.Gloss
|
import Graphics.Gloss
|
||||||
( white, pictures, text, Display(InWindow), Color, Picture )
|
( white,
|
||||||
import RPGEngine.Render.Player (renderPlayer)
|
pictures,
|
||||||
|
text,
|
||||||
|
Display(InWindow),
|
||||||
|
Color,
|
||||||
|
Picture,
|
||||||
|
scale,
|
||||||
|
translate )
|
||||||
|
import RPGEngine.Render.Player (renderPlayer, focusPlayer)
|
||||||
import RPGEngine.Render.GUI (renderGUI)
|
import RPGEngine.Render.GUI (renderGUI)
|
||||||
|
import Graphics.Gloss.Data.Picture (color)
|
||||||
|
import RPGEngine.Render.Core (overlay)
|
||||||
|
import RPGEngine.Input.LvlSelect (getLvlList)
|
||||||
|
import RPGEngine.Render.LvlSelect (renderLvlList)
|
||||||
|
|
||||||
----------------------------- Constants ------------------------------
|
----------------------------- Constants ------------------------------
|
||||||
|
|
||||||
|
@ -32,11 +42,12 @@ initWindow = InWindow
|
||||||
|
|
||||||
-- Render the game
|
-- Render the game
|
||||||
render :: Game -> Picture
|
render :: Game -> Picture
|
||||||
render g@Game{ state = Menu } = renderMenu g
|
render g@Game{ state = Menu } = renderMenu g
|
||||||
render g@Game{ state = Playing } = renderPlaying g
|
render g@Game{ state = LvlSelect } = renderLevelSelection g
|
||||||
render g@Game{ state = Pause } = renderPause g
|
render g@Game{ state = Playing } = renderPlaying g
|
||||||
render g@Game{ state = Win } = renderWin g
|
render g@Game{ state = Pause } = renderPause g
|
||||||
render g@Game{ state = Lose } = renderLose g
|
render g@Game{ state = Win } = renderWin g
|
||||||
|
render g@Game{ state = Lose } = renderLose g
|
||||||
|
|
||||||
----------------------------------------------------------------------
|
----------------------------------------------------------------------
|
||||||
|
|
||||||
|
@ -44,6 +55,10 @@ render g@Game{ state = Lose } = renderLose g
|
||||||
renderMenu :: Game -> Picture
|
renderMenu :: Game -> Picture
|
||||||
renderMenu _ = text "[Press any key to start]"
|
renderMenu _ = text "[Press any key to start]"
|
||||||
|
|
||||||
|
-- TODO
|
||||||
|
renderLevelSelection :: Game -> Picture
|
||||||
|
renderLevelSelection _ = renderLvlList getLvlList
|
||||||
|
|
||||||
renderPlaying :: Game -> Picture
|
renderPlaying :: Game -> Picture
|
||||||
renderPlaying g@Game{ playing = lvl, player = player } = pictures [
|
renderPlaying g@Game{ playing = lvl, player = player } = pictures [
|
||||||
renderLevel lvl,
|
renderLevel lvl,
|
||||||
|
@ -51,9 +66,12 @@ renderPlaying g@Game{ playing = lvl, player = player } = pictures [
|
||||||
renderGUI g
|
renderGUI g
|
||||||
]
|
]
|
||||||
|
|
||||||
-- TODO
|
|
||||||
renderPause :: Game -> Picture
|
renderPause :: Game -> Picture
|
||||||
renderPause _ = text "[Press any key to continue]"
|
renderPause g = pictures [renderPlaying g, pause]
|
||||||
|
where pause = pictures [
|
||||||
|
overlay,
|
||||||
|
color white $ scale 0.5 0.5 $ text "[Press any key to continue]"
|
||||||
|
]
|
||||||
|
|
||||||
-- TODO
|
-- TODO
|
||||||
renderWin :: Game -> Picture
|
renderWin :: Game -> Picture
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
module RPGEngine.Render.Core where
|
module RPGEngine.Render.Core where
|
||||||
|
|
||||||
import Graphics.Gloss ( Picture, translate )
|
import Graphics.Gloss ( Picture, translate, pictures )
|
||||||
import GHC.IO (unsafePerformIO)
|
import GHC.IO (unsafePerformIO)
|
||||||
import Graphics.Gloss.Juicy (loadJuicyPNG)
|
import Graphics.Gloss.Juicy (loadJuicyPNG)
|
||||||
import Data.Maybe (fromJust)
|
import Data.Maybe (fromJust)
|
||||||
|
@ -21,7 +21,7 @@ assetsFolder :: FilePath
|
||||||
assetsFolder = "assets/"
|
assetsFolder = "assets/"
|
||||||
|
|
||||||
unknownImage :: FilePath
|
unknownImage :: FilePath
|
||||||
unknownImage = "unkown.png"
|
unknownImage = "unknown.png"
|
||||||
|
|
||||||
allEntities :: [(String, FilePath)]
|
allEntities :: [(String, FilePath)]
|
||||||
allEntities = [
|
allEntities = [
|
||||||
|
@ -32,6 +32,7 @@ allEntities = [
|
||||||
allEnvironment :: [(String, FilePath)]
|
allEnvironment :: [(String, FilePath)]
|
||||||
allEnvironment = [
|
allEnvironment = [
|
||||||
("void", "void.png"),
|
("void", "void.png"),
|
||||||
|
("overlay", "overlay.png"),
|
||||||
("tile", "tile.png"),
|
("tile", "tile.png"),
|
||||||
("wall", "wall.png"),
|
("wall", "wall.png"),
|
||||||
("entrance", "entrance.png"),
|
("entrance", "entrance.png"),
|
||||||
|
@ -47,7 +48,7 @@ allItems = [
|
||||||
-- Map of all renders
|
-- Map of all renders
|
||||||
library :: [(String, Picture)]
|
library :: [(String, Picture)]
|
||||||
library = unknown:entities ++ environment ++ gui ++ items
|
library = unknown:entities ++ environment ++ gui ++ items
|
||||||
where unknown = ("unkown", renderPNG (assetsFolder ++ unknownImage))
|
where unknown = ("unknown", renderPNG (assetsFolder ++ unknownImage))
|
||||||
entities = map (\(f, s) -> (f, renderPNG (assetsFolder ++ "entities/" ++ s))) allEntities
|
entities = map (\(f, s) -> (f, renderPNG (assetsFolder ++ "entities/" ++ s))) allEntities
|
||||||
environment = map (\(f, s) -> (f, renderPNG (assetsFolder ++ "environment/" ++ s))) allEnvironment
|
environment = map (\(f, s) -> (f, renderPNG (assetsFolder ++ "environment/" ++ s))) allEnvironment
|
||||||
gui = []
|
gui = []
|
||||||
|
@ -71,4 +72,14 @@ getRender id = get filtered
|
||||||
setRenderPos :: Int -> Int -> Picture -> Picture
|
setRenderPos :: Int -> Int -> Picture -> Picture
|
||||||
setRenderPos x y = translate floatX floatY
|
setRenderPos x y = translate floatX floatY
|
||||||
where floatX = fromIntegral x * zoom * resolution
|
where floatX = fromIntegral x * zoom * resolution
|
||||||
floatY = fromIntegral y * zoom * resolution
|
floatY = fromIntegral y * zoom * resolution
|
||||||
|
|
||||||
|
overlay :: Picture
|
||||||
|
overlay = setRenderPos offX offY $ pictures voids
|
||||||
|
where voids = [setRenderPos x y void | x <- [0 .. width], y <- [0 .. height]]
|
||||||
|
void = getRender "overlay"
|
||||||
|
intZoom = round zoom :: Int
|
||||||
|
height = round $ 4320 / resolution / zoom
|
||||||
|
width = round $ 7680 / resolution / zoom
|
||||||
|
offX = negate (width `div` 2)
|
||||||
|
offY = negate (height `div` 2)
|
15
lib/RPGEngine/Render/LvlSelect.hs
Normal file
15
lib/RPGEngine/Render/LvlSelect.hs
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
module RPGEngine.Render.LvlSelect
|
||||||
|
( renderLvlList
|
||||||
|
) where
|
||||||
|
|
||||||
|
import Graphics.Gloss ( Picture, pictures, translate, scale )
|
||||||
|
import Graphics.Gloss.Data.Picture (blank, text)
|
||||||
|
import RPGEngine.Render.Core (resolution, zoom)
|
||||||
|
|
||||||
|
-- Render all level names, under each other.
|
||||||
|
renderLvlList :: [FilePath] -> Picture
|
||||||
|
renderLvlList list = pictures $ map render entries
|
||||||
|
where entries = zip [0::Int .. ] list
|
||||||
|
render (i, path) = scale zoomed zoomed $ translate 0 (offset i) $ text path
|
||||||
|
zoomed = 0.1 * zoom
|
||||||
|
offset i = negate (2 * resolution * zoom * fromIntegral i)
|
|
@ -1,11 +1,17 @@
|
||||||
module RPGEngine.Render.Player
|
module RPGEngine.Render.Player
|
||||||
( renderPlayer
|
( renderPlayer
|
||||||
|
, focusPlayer
|
||||||
) where
|
) where
|
||||||
|
|
||||||
import RPGEngine.Data (Player(..))
|
import RPGEngine.Data (Player(..), Game(..))
|
||||||
|
|
||||||
import Graphics.Gloss (Picture, text)
|
import Graphics.Gloss (Picture, text)
|
||||||
import RPGEngine.Render.Core (getRender, setRenderPos)
|
import RPGEngine.Render.Core (getRender, setRenderPos, zoom, resolution)
|
||||||
|
import Graphics.Gloss.Data.Picture (translate)
|
||||||
|
|
||||||
renderPlayer :: Player -> Picture
|
renderPlayer :: Player -> Picture
|
||||||
renderPlayer Player{ position = (x, y) } = setRenderPos x y $ getRender "player"
|
renderPlayer Player{ position = (x, y) } = setRenderPos x y $ getRender "player"
|
||||||
|
|
||||||
|
focusPlayer :: Game -> Picture -> Picture
|
||||||
|
focusPlayer Game{ player = Player{ position = (x, y)}} = translate centerX centerY
|
||||||
|
where centerX = resolution * zoom * fromIntegral (negate x)
|
||||||
|
centerY = resolution * zoom * fromIntegral (negate y)
|
|
@ -8,6 +8,7 @@ library
|
||||||
hs-source-dirs: lib
|
hs-source-dirs: lib
|
||||||
build-depends:
|
build-depends:
|
||||||
base >= 4.7 && <5,
|
base >= 4.7 && <5,
|
||||||
|
directory >= 1.3.6.0,
|
||||||
gloss >= 1.11 && < 1.14, gloss-juicy >= 0.2.3,
|
gloss >= 1.11 && < 1.14, gloss-juicy >= 0.2.3,
|
||||||
parsec >= 3.1.15.1
|
parsec >= 3.1.15.1
|
||||||
exposed-modules:
|
exposed-modules:
|
||||||
|
@ -20,6 +21,7 @@ library
|
||||||
RPGEngine.Input
|
RPGEngine.Input
|
||||||
RPGEngine.Input.Core
|
RPGEngine.Input.Core
|
||||||
RPGEngine.Input.Level
|
RPGEngine.Input.Level
|
||||||
|
RPGEngine.Input.LvlSelect
|
||||||
RPGEngine.Input.Player
|
RPGEngine.Input.Player
|
||||||
|
|
||||||
RPGEngine.Parse
|
RPGEngine.Parse
|
||||||
|
@ -31,6 +33,7 @@ library
|
||||||
RPGEngine.Render.Core
|
RPGEngine.Render.Core
|
||||||
RPGEngine.Render.GUI
|
RPGEngine.Render.GUI
|
||||||
RPGEngine.Render.Level
|
RPGEngine.Render.Level
|
||||||
|
RPGEngine.Render.LvlSelect
|
||||||
RPGEngine.Render.Player
|
RPGEngine.Render.Player
|
||||||
|
|
||||||
executable rpg-engine
|
executable rpg-engine
|
||||||
|
|
BIN
verslag.pdf
BIN
verslag.pdf
Binary file not shown.
Reference in a new issue