Repository
the-way-out
Top-down pixel-art escape-room shooter. Fight through locked rooms, work the levers, find the way out. Built with pygame; testbed for eeco.
- apple
- eeco
- escape-room
- game-development
- intel
- macos
- pixel-art
- pygame
- python
- silicon
- top-down-shooter
main
Languages
- Python 78.5%
- Markdown 18.1%
- Shell 1.7%
- YAML 0.6%
- Swift 0.6%
- TOML 0.3%
- JSON 0.2%
Readme
The character-select screen: five playables, each with its own HP, speed, damage, fire-rate, and signature ability.
Pick a character, fight your way through locked rooms, work the levers and pressure plates, and find the way out.
Play
pip install pygame
python main.py
Controls
| Input | Action |
|---|---|
| WASD / Arrows | Move & aim (4-way) |
| Space | Shoot |
| Shift | Dash |
| E | Use / interact |
| Esc | Pause / back |
Characters
Five playable characters, each with its own HP, speed, damage and fire-rate profile: the balanced Wizard, the Penguin tank, the rapid-fire Elf, the glass-cannon Shiggy, and the speedster Wolf.
Levels
Three hand-authored escape rooms. Levels are plain text maps under
assets/levels/ (see LEGEND.md for the tile vocabulary) plus a
manifest.json, so new rooms can be added without touching code. An
in-game editor (editor.py) edits them live.
Project layout
| Path | Purpose |
|---|---|
main.py |
Entry point & game loop |
menu.py |
Title, settings, character & level menus |
levels.py |
Level loading & runtime |
units.py |
Player & enemy logic |
interactables.py / static_objects.py / tileset.py |
World objects |
editor.py |
In-game level editor |
theme.py |
Shared palette & UI helpers |
audio.py |
Music & SFX |
assets/ |
Sprites, audio, fonts, level maps |
A deeper walk-through of each subsystem — the game loop, levels, combat, the editor, the save file, and the self-updater — is in Documentation.
Build (macOS)
./build_mac.sh # arm64 .app
./build_mac_intel.sh # x86_64 .app
The app self-updates from this repository on launch via updater.py;
save data lives outside the app bundle and is never touched by updates.
Versioning
Semantic versioning (vMAJOR.MINOR.PATCH); each release is a single
annotated git tag. See CHANGELOG.md for the history.
License
Apache License 2.0 — see LICENSE.
See also
- FlashOS — AArch64 bare-metal kernel for the Raspberry Pi 4 Model B.
Recent commits
-
ac80aa3docs: update Jun 2026 -
8a91af3docs: adopt the house design system — exit-green wordmark, flat-square badges Jun 2026 -
2db4231docs: use the Atom One Light foreground in the light-mode logo Jun 2026 -
d5ad1f5docs: normalize CHANGELOG headers to Keep-a-Changelog form Jun 2026 -
14d01a0docs: add DOCUMENTATION.md, align doc chrome Jun 2026 -
0787a9eeeco init May 2026 -
875fce2docs: the-way-out v1.0.5 — responsive project logo (Orbitron) May 2026 -
21a1a1bdocs: the-way-out v1.0.4 — formal versioning policy (VERSIONING.md) May 2026 -
a23bd97docs: the-way-out v1.0.3 — cross-repo nav design (FlashOS-style per-doc chrome) May 2026 -
c069d36docs: the-way-out v1.0.2 — cross-project fingerprint pass May 2026 -
e6ae2c7update README May 2026 -
1a68fcav1.0.1 May 2026 -
fc32d30v1.0.0 May 2026 -
4c8248ev0.10.0 May 2026 -
7e4c35bv0.9.0 May 2026
Files
-
.github
-
workflows
-
-
assets
-
gui
-
buttons
- Button1.png
- Button2.png
- Button3.png
- Button4.png
- Button5.png
- Button6.png
- ButtonsMap.png
- ButtonsMap2.png
- ButtonTile_01.png
- ButtonTile_02.png
- ButtonTile_03.png
- ButtonTile_04.png
- ButtonTile_05.png
- ButtonTile_06.png
- ButtonTile_07.png
- ButtonTile_08.png
- ButtonTile_09.png
- ButtonTile_10.png
- ButtonTile_11.png
- ButtonTile_12.png
- ButtonTile_13.png
- ButtonTile_14.png
- ButtonTile_15.png
- ButtonTile_16.png
- ButtonTile_17.png
- ButtonTile_18.png
-
font
-
icons
- Icon_01.png
- Icon_02.png
- Icon_03.png
- Icon_04.png
- Icon_05.png
- Icon_06.png
- Icon_07.png
- Icon_08.png
- Icon_09.png
- Icon_10.png
- Icon_11.png
- Icon_12.png
- Icon_13.png
- Icon_14.png
- Icon_15.png
- Icon_16.png
- Icon_17.png
- Icon_18.png
- Icon_19.png
- Icon_20.png
- Icon_21.png
- Icon_22.png
- Icon_23.png
- Icon_24.png
- Icon_25.png
- Icon_26.png
- Icon_27.png
- Icon_28.png
- Icon_29.png
- Icon_30.png
- Icon_31.png
- Icon_32.png
- Icon_33.png
- Icon_34.png
- Icon_35.png
- Icon_36.png
- Icon_37.png
- Icon_38.png
- Icon_39.png
- Icon_40.png
- Icon_41.png
- Icon_42.png
- Icon_43.png
- Icon_44.png
- Icon_45.png
- Icon_46.png
- Icon_47.png
- Icon_48.png
- Icon_49.png
- Icon_50.png
- Icon_51.png
- Icon_52.png
- Icon_53.png
- Icon_54.png
- Icon_55.png
- Icon_56.png
- Icon_57.png
- Icon_58.png
- Icon_59.png
- Icon_60.png
- Iconset1.png
- Iconset2.png
- Iconset3.png
- Iconset4.png
- Iconset5.png
- Iconset6.png
- Iconset7.png
-
interface
- Tile_01.png
- Tile_02.png
- Tile_03.png
- Tile_04.png
- Tile_05.png
- Tile_06.png
- Tile_07.png
- Tile_08.png
- Tile_09.png
- Tile_10.png
- Tile_11.png
- Tile_12.png
- Tile_13.png
- Tile_14.png
- Tile_15.png
- Tile_16.png
- Tile_17.png
- Tile_18.png
- Tile_19.png
- Tile_20.png
- Tile_21.png
- Tile_22.png
- Tile_23.png
- Tile_24.png
- Tile_25.png
- Tile_26.png
- Tile_27.png
- Tile_28.png
- Tile_29.png
- Tile_30.png
- Tile_31.png
- Tile_32.png
- Tile_33.png
- Tile_34.png
- Tile_35.png
- Tile_36.png
- Tile_37.png
- Tile_38.png
- Tile_39.png
- Tile_40.png
- Tile_41.png
- Tile_42.png
- Tile_43.png
- Tile_44.png
- Tile_45.png
- Tile_46.png
- Tile_47.png
- Tile_48.png
- Tile_49.png
- Tile_50.png
- Tile_51.png
- Tile_52.png
- Tile_53.png
- Tile_54.png
- Tile_55.png
- Tile_56.png
- Tile_57.png
- Tile_58.png
- Tile_59.png
- Tile_60.png
- Tile_61.png
- Tile_62.png
- Tile_64.png
- Tile_65.png
- Tile_67.png
- Tile_68.png
- Tile_70.png
- Tile_71.png
- Tile_72.png
- Tile_73.png
- Tile_74.png
- Tile_76.png
- Tile_77.png
- Tile_79.png
- Tile_80.png
- Tile_82.png
- Tile_83.png
- Tile_84.png
- Tile_85.png
- Tile_87.png
- Tile_88.png
- Tile_90.png
- Tile_91.png
- Tile_93.png
- Tile_94.png
- Tile_95.png
- Tile_96.png
- TileMap1.png
- TileMap2.png
- TileMap3.png
- TileMap4.png
- TileMap5.png
- TileMap6.png
- TileMap7.png
- TileMap8.png
-
logo
-
tileset
-
static_objects
-
other
- 1.png
- 10.png
- 11.png
- 12.png
- 13.png
- 14.png
- 15.png
- 16.png
- 17.png
- 18.png
- 19.png
- 2.png
- 20.png
- 21.png
- 22.png
- 23.png
- 24.png
- 25.png
- 26.png
- 27.png
- 28.png
- 29.png
- 3.png
- 30.png
- 31.png
- 32.png
- 33.png
- 34.png
- 35.png
- 36.png
- 37.png
- 38.png
- 39.png
- 4.png
- 40.png
- 41.png
- 42.png
- 43.png
- 44.png
- 5.png
- 6.png
- 7.png
- 8.png
- 9.png
- Fog.png
- Palette.png
-
tiles
- Tile_03.png
- Tile_04.png
- Tile_05.png
- Tile_06.png
- Tile_07.png
- Tile_09.png
- Tile_101.png
- Tile_102.png
- Tile_105.png
- Tile_107.png
- Tile_108.png
- Tile_109.png
- Tile_11.png
- Tile_13.png
- Tile_15.png
- Tile_16.png
- Tile_17.png
- Tile_19.png
- Tile_20.png
- Tile_21.png
- Tile_22.png
- Tile_23.png
- Tile_24.png
- Tile_26.png
- Tile_27.png
- Tile_28.png
- Tile_30.png
- Tile_31.png
- Tile_32.png
- Tile_33.png
- Tile_34.png
- Tile_35.png
- Tile_36.png
- Tile_37.png
- Tile_39.png
- Tile_41.png
- Tile_42.png
- Tile_43.png
- Tile_44.png
- Tile_45.png
- Tile_46.png
- Tile_47.png
- Tile_48.png
- Tile_49.png
- Tile_51.png
- Tile_52.png
- Tile_53.png
- Tile_54.png
- Tile_55.png
- Tile_56.png
- Tile_57.png
- Tile_58.png
- Tile_59.png
- Tile_60.png
- Tile_61.png
- Tile_62.png
- Tile_63.png
- Tile_65.png
- Tile_72.png
- Tile_73.png
- Tile_74.png
- Tile_75.png
- Tile_76.png
- Tile_77.png
- Tile_79.png
- Tile_80.png
- Tile_81.png
- Tile_82.png
- Tile_83.png
- Tile_84.png
- Tile_86.png
- Tile_87.png
- Tile_88.png
- Tile_89.png
- Tile_91.png
- Tile_92.png
- Tile_93.png
- Tile_94.png
- Tile_95.png
- Tile_96.png
- Tile_97.png
- Tile_98.png
- Tile_99.png
- Tileset.png
-
units
- icon_1024.png
- icon.icns
- logo_dark.png
- logo_light.png
- screenshot.png
-
scripts
- .gitignore
- audio.py
- build_mac_intel.sh
- build_mac.sh
- CHANGELOG.md
- DOCUMENTATION.md
- editor.py
- effects.py
- interactables.py
- launcher.py
- level_catalog.py
- levels.py
- LICENSE
- loading_screen.py
- main.py
- menu.py
- pyproject.toml
- README.md
- save.py
- settings.py
- static_objects.py
- theme.py
- tiles.py
- tileset.py
- units.py
- updater.py
- VERSION
- version.py
- VERSIONING.md