ViZDoom Development Guide

Tech stack + deps

  • C++11 core + ZDoom engine fork, built with CMake and make.

  • C++ code relies on Boost, SDL2, OpenAL, and other common libraries (BZip2, JPEG, Zlib, GME, etc., included in the src), they are found via CMake.

  • Python bindings via pybind11; packaging via setuptools.

  • Python runtime deps: numpy, gymnasium, pygame-ce (see setup.py).

  • Tests: pytest, pytest-xdist, psutil.

  • Docs: Sphinx (see docs/ and docs/conf.py).

Project structure

  • src/: C++ core and engine (src/lib/, src/vizdoom/) plus Python bindings (src/lib_python/).

  • include/: public C++ headers for the ViZDoom API.

  • CMakeLists.txt, cmake_modules/: CMake build configuration.

  • scenarios/: .cfg and .wad scenario assets.

  • gymnasium_wrapper/: Gymnasium integration for Python.

  • examples/: example code and assets.

  • tests/: pytest suite plus manual test scripts.

  • docs/: Sphinx documentation sources.

  • bin/pythonX/vizdoom: assembled package output from the CMake build.

Coding conventions

Main library (src/lib/, src/lib_python/, and include/)

  • Always update documentation in docs/api/cpp when changing public API and corresponding Python module docs in src/lib_python.

  • To update Python docs and docstrings, modify the C++ doc comments run python scripts/create_python_docs_from_cpp_docs.py and python scripts/create_python_docstrings_from_cpp_docs.py.

  • Stubs (src/lib_python/vizdoom.pyi) are generated by cmake/make (using pybind11-stubgen).

  • src/ is excluded from pre-commit hooks, so follow the existing C/C++ style in nearby files.

ZDoom engine (src/vizdoom)

  • Keep changes minimal. Avoid refactoring or style changes unrelated to the feature/bugfix especially in the engine code.

  • Use the coding style used in a file you are changing. Generally, follow the existing style in nearby code.

  • Every code change in ZDoom engine (src/vizdoom) must be marked with //VIZDOOM_CODE comment.

Python code (gymnasium_wrapper, examples, tests)

  • Python formatting/linting is enforced by pre-commit: Black, isort, flake8, pyupgrade, codespell. Configuration lives in pyproject.toml and .pre-commit-config.yaml.

  • Type checking uses pyright with settings in pyproject.toml.

Editable install (builds C++ + Python package)

Install a project in editable mode

Work on the project by installing it in editable mode. This way, changes to C++ code are reflected in the installed package without reinstalling. First, install dependencies (depending on your system, see Building from source for more details). Now you should be able to install ViZDoom in editable mode by running the following commands in the project root:

pip install -U pip setuptools wheel
pip install -e . --no-build-isolation

Notes:

  • pip install -e . runs CMake + make via setup.py and assembles the package under bin/pythonX/vizdoom.

  • Use --no-build-isolation to keep CMake stable (avoids temp build env paths).

  • Due to --no-build-isolation, pip, setuptools, and wheel need to be installed beforehand and be up-to-date.

Rebuild after changes

make -j

This updates bin/pythonX/vizdoom, which is what the editable install points at. If you switch Python versions, remove CMakeCache.txt and rebuild via pip install -e . --no-build-isolation.

Running tests

Run tests after every change to ensure nothing is broken:

pytest -s tests

to run the test suite in parallel using all available CPU cores you can use (recommended for faster feedback):

pytest -n auto -s tests

Manual tests live in tests/manual_test_*.py and are not run by default.

Running pre-commit hooks

Pre-commit hooks are used to enforce code formatting and linting for Python code (Black, isort, flake8, pyupgrade, codespell).

To install pre-commit hooks, run:

pre-commit install

To run pre-commit hooks manually, use:

pre-commit run --all-files