Skip to content

lennney/adventure-game

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

48 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Echoes of the Labyrinth

A turn-based text adventure with AI-driven adversary powered by PDDL + Pyperplan planning.

SWI-Prolog Python Streamlit


Table of Contents


Overview

Echoes of the Labyrinth is a turn-based dungeon escape game built as a university coursework project. You awaken in a seven-room underground labyrinth and must find your way out before the Warden — an AI guardian — catches you.

The game has multiple endings depending on your choices:

  • Escape empty-handed — flee without taking the Soulstone
  • Ritual ending — take the Soulstone, complete a stabilisation ritual at the shrine, then escape
  • Death — caught by the Warden, health depleted, or turn limit exceeded

Key Features

  • Pure SWI-Prolog game engine — declarative logic for world state, rules, items, and win/lose conditions
  • PDDL + Pyperplan powered AI adversary that dynamically plans paths instead of following hard-coded patrol routes
  • Streamlit web interface with a dungeon-themed UI (optional)
  • Turn-based combat with item-based defence mechanics
  • Undo system that rewinds game state and resets cached AI plans

Quick Start

Prerequisites

# Install optional dependencies
pip install pyperplan streamlit requests

Run in Terminal

cd prolog
swipl
?- [game].
?- start.

Run Web Interface

1. Start the Prolog HTTP API (backend):

cd prolog
swipl
?- [server].
?- server(8000).

2. Start the Streamlit frontend (in a new terminal):

python -m streamlit run app.py

Open http://localhost:8501 in your browser.


Game Rules

Commands

Command Description
look. Observe your surroundings
go(Direction). Move north, south, east, or west
take(Item). Pick up an item
drop(Item). Drop an item
inventory. Check what you are carrying
perform_ritual. Attempt the stabilisation ritual (at the shrine)
undo. Rewind one turn

Win Conditions

  • Ritual ending: Reach exit_gate carrying the Soulstone after completing the ritual at the shrine
  • Escape ending: Reach exit_gate without taking the Soulstone

Lose Conditions

  • Health drops to zero (Warden encounter without defence)
  • Turn limit exceeded
  • Attempting the ritual without the required items (corruption ending)

Map

                    [armory]
                       |
                     north
                       |
[entrance_hall] --east-- [guard_post] --east-- [library]
                      (Warden start)          |
                                            south
                                              |
                    [treasure_chamber] --west-- [shrine] --south-- [exit_gate]
                          (Soulstone)

Technical Architecture

adventure-game/
├── prolog/
│   ├── game.pl              # Main loop, entry point
│   ├── world.pl             # Static world facts (rooms, doors, item locations)
│   ├── rules.pl             # Player actions, win/lose logic, undo
│   ├── adversary.pl         # Warden AI: goal selection, plan execution
│   ├── pyperplan_runner.pl  # PDDL problem generation + Pyperplan integration
│   ├── server.pl            # HTTP API for Streamlit frontend
│   └── ui.pl                # REST endpoint handlers
├── pddl/
│   ├── adversary_domain.pddl # STRIPS planning domain (warden actions)
│   └── adversary_problem_base.pddl  # Problem template (dynamically instantiated)
└── app.py                   # Streamlit web interface

The game logic lives entirely in Prolog. The Streamlit frontend communicates with Prolog via a lightweight HTTP API.


The Warden AI — Planning-based Adversary

This is the core technical contribution of the PDDL implementation.

How It Works

Instead of a hard-coded patrol script, the Warden uses AI planning to decide where to move. Each turn it:

  1. Evaluates the current goal based on game state
  2. Checks whether an existing cached plan is still valid
  3. If not, calls Pyperplan (an external STRIPS planner) to compute a path
  4. Executes only the next step of the plan, then re-evaluates next turn

Three-Phase Goal System

The Warden's behaviour adapts dynamically to player actions:

Phase Trigger Goal Behaviour
Phase 1 Player has no Soulstone Guard treasure chamber Patrol between key rooms
Phase 2 Player took Soulstone Hunt the player Chase player's current position
Phase 3 Player near exit Block exit gate Intercept the exit corridor

PDDL Planning Pipeline

Prolog (adversary.pl)
    │
    ├─ warden_goal/1          ← Select target based on game state
    │
    ├─ build_warden_problem_file/3
    │     └─ Reads adversary_problem_base.pddl
    │     └─ Injects current (at-warden FROM) and (at-warden TO)
    │     └─ Writes adversary_problem_tmp.pddl
    │
    ├─ run_warden_planner/2
    │     └─ Calls: pyperplan domain.pddl problem_tmp.pddl
    │     └─ Parses .soln output → [move(a,b), move(b,c), ...]
    │
    └─ execute_first_action/2
          └─ Validates next step against current world state
          └─ Applies it (retract + assert enemy_at)
          └─ Caches remaining plan for next turn

Robustness: Graceful Degradation

If Pyperplan fails (e.g., planner not installed), the Warden falls back to a deterministic patrol route: guard_post → library → shrine → guard_post. This means the game is always playable.

If a stored plan becomes invalid mid-execution (e.g., player used undo.), the plan is discarded and re-planning is triggered immediately.

Example: Plan Output

When Pyperplan runs, it produces a plan like:

move(guard_post, library)
move(library, shrine)
move(shrine, treasure_chamber)

The Warden executes one step per turn, so the player experiences emergent, adaptive behaviour rather than a teleporting enemy.


Team

Name Role Contribution
LIUGUOHAO PDDL + Pyperplan AI Planning Adversary goal system, PDDL domain, planner integration
liuheng Streamlit Web Interface Web UI, Prolog HTTP API
wuzhengye Presentation Report and presentation

License

This project is licensed under the MIT License. See LICENSE for details.

About

A turn-based text adventure with AI-driven adversary powered by PDDL + Pyperplan planning.

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors