Enable CI/CD by adding .onedev-buildspec.yml
| docs | Loading last commit info... | |
| scripts | ||
| src | ||
| tests | ||
| .gitignore | ||
| CMakeLists.txt | ||
| README.md |
README.md
Rhombus Runner
What This Is
Rhombus Runner is a small 3D endless-runner prototype built in C with SDL2.
You dodge and clear obstacles by moving, jumping, and sliding while speed scales up with score.
The codebase is intentionally modular and compact so it is easy to extend with new mechanics.
Play In 60 Seconds
1) Install dependencies
- CMake 3.16+
- C compiler (
clangorgcc; MSVC on Windows is also supported) - SDL2 development libraries
Quick dependency notes:
- macOS (Homebrew):
brew install cmake sdl2 - Ubuntu/Debian:
sudo apt install cmake build-essential libsdl2-dev - Fedora:
sudo dnf install cmake gcc SDL2-devel - Arch:
sudo pacman -S cmake gcc sdl2 - Windows:
- MSYS2: install
mingw-w64-x86_64-cmake, toolchain, andmingw-w64-x86_64-SDL2 - or use vcpkg SDL2 with CMake toolchain integration
- MSYS2: install
2) Build
cmake -S . -B build -DCMAKE_BUILD_TYPE=Release
cmake --build build --config Release
3) Run
./build/rhombus_runner
If you prefer the helper scripts:
./scripts/build.sh
./scripts/run.sh
Controls
A/D: move left/right across the roadW/S: move forward/back in the runner corridorSpace: jumpCtrl: short low slide tackle (cooldown + reduced movement speed)Esc: pause/resumeEnter: resume from pause menuR: restart from pause or game overQ: quit from pause or game over
Current Features
- Endless cube-road recycling
- Obstacle set:
- spinning rhombus
- red jump hurdle
- overhead slide-gate (slide-under)
- Capsule player with lean and slide posture
- Trail particles during movement/slide
- Death burst FX
- Pickup/reward system (speed boost currently implemented)
- HUD + pause/game-over menus + in-game controls hint
- Unit tests for core gameplay logic
Known Limitations
- No signed installer/notarized app pipeline yet.
- Cross-platform source build is supported, but packaged binaries are not shipped.
- Difficulty/balance values are still prototype-level.
Project Structure
src/: gameplay and rendering modulestests/: unit/integration-style logic testsscripts/: build/run/test helpersdocs/: controls, delivery phases, release docs
Module map (high level):
game.*: game loop + state machineworld.*: road, obstacles, pickups, speed scalingplayer.*: movement, jump, slide statecollision.*: player-vs-obstacle checksrenderer.*: 3D software-ish draw path over SDL2fx.*,trail_fx.*: death and movement particlesreward.*: timed reward effects and pickup activationui.*: bitmap-text HUD and menusinput.*: keyboard polling and edge detection
Architecture Notes
- Fixed timestep simulation in
game.c(FIXED_DT). world_stepowns world motion and recycling (road, obstacles, pickups).player_stepowns movement/jump/slide state and local movement constraints.collisiononly decides hit/miss; it does not mutate world state.- Renderer is fed pure state snapshots each frame.
How To Extend
Add a new obstacle type
- Add enum in
src/world.h. - Add spawn/setup branch in
reset_obstacle(src/world.c). - Add collision branch in
src/collision.c. - Add material + wireframe rendering in
src/renderer.c. - Add tests in
tests/test_collision.cand any spawn tests intests/test_world.c.
Add a new reward effect
- Add effect enum in
src/reward.h. - Implement modifier application in
reward_step_active(src/reward.c). - Optionally spawn selective pickup type in
src/world.c. - Add HUD indicator in
src/ui.cand pass-through fromsrc/renderer.c/src/game.c. - Add tests in
tests/test_reward.c.
Add a new player action
- Input fields in
src/input.h+ polling logic insrc/input.c. - Player state and step logic in
src/player.h/.c. - Collision/rule updates if needed in
src/collision.c. - Visual feedback in
src/renderer.cand HUD copy insrc/ui.c. - Add behavior tests in
tests/test_player.c.
Development Workflow
Build:
./scripts/build.sh
Run tests:
./scripts/test.sh
Recommended before pushing:
./scripts/test.sh./scripts/build.sh- quick manual run for controls + collision + menu flow
LLM Context Block
- Core loop invariants:
- Fixed-step update drives gameplay.
- World speed is score-scaled and capped.
GAME_RUNNINGis the only state where gameplay mutates.
- Data ownership:
Worldowns road/obstacles/pickups RNG and score.Playerowns movement state, slide timers, and runtime modifiers.- Reward system mutates player multipliers each tick, then resets when expired.
- Extension seams:
- Obstacles:
world + collision + renderer. - Rewards:
reward + world + game + ui. - New action:
input + player + renderer (+collision if needed).
- Obstacles:
- Do not break:
- Camera constants and existing control mappings unless intentionally changed.
- Pause/restart/game-over flow.
- Existing test contracts in
tests/.
- Test requirements before merge:
scripts/test.shpassingscripts/build.shpassing- no regression in manual control loop