DOOMQL
SELECT * FROM HELL
A playable first-person shooter whose framebuffer is a SQL query.
DOOMQL started with a deliberately unreasonable question: what if SQLite were
the game engine, not merely the place where a game stores data?
The result is a small, original Doom-like game in which SQL owns movement,
collision, enemies, combat, progression and every RGB pixel on screen. There is
no SVG, browser, Canvas or game engine, and the playable runtime contains no
Python graphics code.
How does SQL become a picture?
For each frame, SQL reads the player and map tables and produces one row per
pixel:
x y red green blue
40 20 232 240 248
41 20 30 35 45
A second SQL view turns those RGB rows into coloured ▀ terminal blocks. The
Python host does no drawing: it supplies raw keys, time and terminal size to
SQLite, then prints the completed query result unchanged.
player + map tables
↓
SQL simulation and raycasting
↓
frame_pixels(x, y, r, g, b)
↓
render_frame(y, coloured scanline)
↓
terminal
The complete visible frame is returned by one query:
SELECT scanline FROM render_frame ORDER BY y;
Play
You need:
- macOS, Linux or another Unix-like environment; Windows users can use WSL
- Python 3.11 or newer
- SQLite 3.45 or newer with mathematical functions enabled
- A terminal with 24-bit colour and Unicode
▀ support
- At least 80 columns × 33 rows recommended
There are no third-party Python dependencies. From the repository root, run:
make run
The game follows the live terminal size. Enlarge the window for more
SQL-rendered pixels, or increase the terminal font size to make each pixel
physically larger.
Controls
| Keys | Action |
|---|
W / S | Move forward / backward |
A / D | Strafe left / right |
J / L or arrow keys | Turn left / right |
| Space | Fire |
E | Use the index gate |
P | Pause |
R | Restart after death or victory |
Ctrl-C | Exit |
Objective
- Find the cyan-and-gold INDEX TOKEN.
- Return to the amber gate and press
E.
- Defeat the red DEADLOCK.
- Reach the cyan commit portal.
Along the way you will meet ORPHAN enemies, ranged LOCK WAITERS, health tuples
and ammo pages.
Watch the real SQL while you play
This is the best way to demonstrate