https://github.com/oliviersohn/hamazed
Monorepo for a multi-player game engine, and game examples
https://github.com/oliviersohn/hamazed
addition animation ascii-art ascii-game ascii-graphics collision game haskell laser mathematics retrogaming
Last synced: about 2 months ago
JSON representation
Monorepo for a multi-player game engine, and game examples
- Host: GitHub
- URL: https://github.com/oliviersohn/hamazed
- Owner: OlivierSohn
- Created: 2017-11-08T00:05:57.000Z (over 7 years ago)
- Default Branch: master
- Last Pushed: 2022-02-13T22:25:10.000Z (about 3 years ago)
- Last Synced: 2025-03-16T12:07:33.242Z (about 2 months ago)
- Topics: addition, animation, ascii-art, ascii-game, ascii-graphics, collision, game, haskell, laser, mathematics, retrogaming
- Language: Haskell
- Homepage:
- Size: 4.45 MB
- Stars: 42
- Watchers: 2
- Forks: 7
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- Contributing: CONTRIBUTING.md
Awesome Lists containing this project
README
- [What is it?](#what-is-it)
- [Packages](#packages)
- [Development setup](#development-setup)
- [Install dependencies (C libraries)](#install-dependencies-c-libraries)
- [Build](#build)
- [Run the games in single-player mode](#run-the-games-in-single-player-mode)
- [Run the games in Multi-player mode](#run-the-games-in-multi-player-mode)
- [Connect to a running game server](#connect-to-a-running-game-server)
- [Connect to a Heroku-hosted server](#connect-to-a-heroku-hosted-server)
- [CI](#ci)
- [Game engine highlights](#game-engine-highlights)
- [Supported platforms](#supported-platforms)
- [Music](#music)
- [Notation](#notation)
- [Playback](#playback)
- [Rendering](#rendering)# What is it?
Monorepo for a Haskell multi-player game engine and games made with it.
The games can be played locally, in single-player mode, or in multi-player mode, after having run the [deployment script]
to host the game server on [Heroku].You can even create your own multi-player game, starting from the [tutorial-game](/imj-game-tutorial-increment).
# Supported platforms
Officially supported client platforms are (recent versions of) macOS and Ubuntu,
where a C++17-enabled compiler is available.# Packages
List of packages, inverse-topologically sorted wrt dependencies, with keywords / short description for each of them:
- [imj-audio]
- Bindings to a C++17 lock-free audio engine.
- The C++ sources are located in [submodules](/imj-audio/c).
- [imj-music](/imj-music)
- Polyphonic music scores creation and playback.
- [imj-prelude](/imj-prelude)
- Prelude library used by packages hereunder, mainly to factorize imports.
- [imj-time]
- Timing library based on the system monotonic clock.
- [imj-base]
- Containers (Graph, Matrix, Cyclic matrix, Dynamic vector, etc...)
- Geometry, text animations
- 8-bit color manipulation in different color spaces
- Easing, inverse-easing, interpolation, rectangular frame morphing.
- Physics
- UI components building blocks
- Chat
- Rendering backends, using [delta-rendering](/imj-base/src/Imj/Graphics/Render/Delta.hs):
- In a GLFW-driven OpenGL window
- In the terminal
- Player input, window management.
- [imj-space](/imj-space)
- Randomized creation of 2D game levels, given some topological constraints.
- [imj-particlesystem](/imj-particlesystem) (formerly `imj-animation`)
- Physics-based and geometric particle systems.
- [imj-measure-stdout](/imj-measure-stdout)
- An executable to measure the maximum capacity of stdout, and observe
the effect of different buffering modes. This was used while developing
[delta-rendering](/imj-base/src/Imj/Graphics/Render/Delta.hs).
- [imj-server](/imj-server)
- Using [websockets] to communicate between server and clients.
- Broadcast messages to all clients
- Handle connection failures generically (so that a client handler, when broadcasting a message,
won't have to handle exceptions due to another client's connection being down.)
- Detect client reconnection (keep track of clients identities using their MAC address)
- Logging
- [imj-serve-highscores]
- [Servant]-based web service to persist and access highscores.
- [imj-game]
- Multi-player game engine
- Listens to server events, and player events
- [Handles generic events](/imj-game/src/Imj/Game/Update.hs), so that the game implementation
contains only game-specific code.
- Real-time music playback.
- Debugging features : record and display events graphically, event logging.
- [imj-game-tutorial-increment](/imj-game-tutorial-increment)
- A tutorial on how to use [imj-game] to build a multi-player game.
- [imj-game-synths]
- "A jam session, in the cloud, with loops and synthesizers."
- Players are playing music together, in real-time, using either real MIDI devices,
or computer keyboards.
- [imj-game-hamazed]
- You're a ship pilot, shooting at flying numbers.
- Each level has its own original music!
- Levels generation is randomized, so that you will (very likely) never play the same game twice.
- Demo (when the game was mono-player and had no music):
[](https://asciinema.org/a/156059)
- [imj-profile](/imj-profile)
- An executable precomputing optimal strategies used for random level generation.
- And other profiling tests.# Development setup
After checking out the repo, run `git submodule init && git submodule update` to download the submodules.
## Install dependencies (C libraries)
- [ftgl] is needed by [imj-base] to render fonts with OpenGL.
- [portaudio 19] is needed by [imj-audio] for audio I/O.
- [libpq] and [postgresql] are needed by a dependency of [imj-serve-highscores].To install them:
- On OSX:
```shell
brew install ftgl
brew install portaudio
brew install postgresql
```- On Linux:
```shell
sudo apt-get update
sudo apt-get install ftgl-dev
sudo apt-get install portaudio19-dev
sudo apt-get install postgresql
sudo apt-get install libpq-dev
```# Build
[stack] is the preferred tool to build the project:
```shell
stack build --pedantic
```A recent enough C compiler should be used by GHC, so as to be able to build C++17.
# Run the games in single-player mode
Passing no command line argument will run the games in single player mode:
```shell
stack exec
```# Deploy a game server for Multi-player mode
Use the [deployment script] to host the games on a [Heroku] server.
# Run the games in Multi-player mode
### Connect to a running game server
```shell
stack exec -- -n -p
```### Connect to a Heroku-hosted server
When the game server is hosted on [Heroku], the port to connect to is `80`:
```shell
stack exec -- -n -p80
```# CI
The [CI script](/.travis.yml) verifies that compilation and tests succeed with
GHC versions 8.2.2 and 8.4.3.# Game engine highlights
## Music
### Notation
[Melodies](/imj-game-hamazed/src/Imj/Game/Hamazed/Music.hs)
are written using the `notes` quasiquoter, where:- notes names follow [the solfege notation]
- a note can be shifted by octaves using `v` and `^`
- `-` extends the preceding note
- `.` indicates a pause### Playback
Every game made with [imj-game] can have the server send midi-like
note on / note off events to game clients, allowing to perfectly synchronize the music with the game.The music won't pause during garbage collection because we use
[an audio engine](/imj-audio) whose audio realtime thread is
not managed by the GHC runtime.## Rendering
The screen is conceptually divided in small blocks of equal size,
where each block can contain a character with 8-bit background and foreground colors.The [fonts](/imj-base/fonts) and font size for rendering can be modified at run time.
[deployment script]: ./deploy-heroku.sh
[ftgl]: http://ftgl.sourceforge.net/docs/html/
[Heroku]: https://www.heroku.com/
[imj-base]: /imj-base
[imj-audio]: /imj-audio
[imj-game]: /imj-game
[imj-game-hamazed]: /imj-game-hamazed
[imj-game-synths]: /imj-game-synths
[imj-serve-highscores]: /imj-serve-highscores
[imj-time]: /imj-time
[libpq]: https://www.postgresql.org/docs/9.5/static/libpq.html
[postgresql]: https://www.postgresql.org/
[portaudio 19]: http://www.portaudio.com/
[Servant]: http://haskell-servant.readthedocs.io/en/stable/
[stack]: https://docs.haskellstack.org
[the solfege notation]: https://en.wikipedia.org/wiki/Solf%C3%A8ge#Fixed_do_solf%C3%A8ge
[websockets]: http://hackage.haskell.org/package/websockets# Build status
Currently, the CI build errors because the "build from scratch" process plus unit tests takes more than one hour and hits a timeout :
[](https://travis-ci.org/OlivierSohn/hamazed)