Skip to main content

pygeon

Python tools for working with the Leaving the City (LTC) dataset. The package provides lightweight data access for visual(-inertial) odometry, visual geo-localization, land-cover analysis, and orthophoto/DSM references.

This repository contains the Python library, examples, tests, and documentation. The dataset itself is hosted separately.

This release is meant to make the dataset tooling available early. Bugs, issues, and improvement suggestions are welcome, and we plan to keep improving the repository over time.

Features

  • VIOIterator for IMU-aligned visual-inertial streams.
  • VGLIterator for image, pose, optional land-cover, and optional orthophoto/DSM samples.
  • CSV and calibration readers for camera, INS, IMU, GPS, barometer, and magnetometer files.
  • Geometry utilities for camera/body poses, satellite coordinates, footprints, and image handling.
  • Land-cover helpers for CORINE masks and semantic coverage tables.

Installation

Use Python 3.10 or newer.

git clone https://github.com/hlzmnhnry/pygeon.git
cd pygeon
python -m pip install -e .   # distribution name pygeon-ltc, import name pygeon

Orthophoto and DSM lookup use rasterio and georaffer. Install the optional dependencies with python -m pip install -e ".[orthophoto]" before using pygeon.references.OrthoProvider or the VGL example.

georaffer is the central dependency for downloading and handling orthophoto/DSM tiles.

For development and tests:

python -m pip install -e ".[dev]"
python -m pytest

Pixi is also supported via the [tool.pixi.*] configuration in pyproject.toml:

pixi install
pixi run test
pixi run vio-example
pixi run vgl-example

Dataset Layout

By default, pygeon expects data below ./data. You can override this with data_directory, campaign_directory, image_directory, and landcover_directory arguments.

See data/README.md for the expected dataset structure, metadata files, campaign folders, and image/land-cover naming conventions. Supported campaign IDs are defined in pygeon.enums.CampaignDate.

Quick Start

Visual-inertial iteration:

from pathlib import Path

from pygeon.datasets.vio_iterator import VIOIterator
from pygeon.enums import CampaignDate, FrameType, MatchPolicy

it = VIOIterator(
    campaign=CampaignDate.CAMPAIGN_2022_02_23_11_45_35,
    data_directory=Path("./data"),
    match_policy=MatchPolicy.NEAREST_WITHIN_TOL,
    frame=FrameType.CAMERA,
    undistort=True,
)

for sample in it:
    timestamp = sample["timestamp"]
    imu = sample["imu"]
    pose = sample["pose"]
    image = sample["image"]
    break

Visual geo-localization iteration:

from pathlib import Path

from pygeon.datasets.vgl_iterator import VGLIterator
from pygeon.enums import CampaignDate, FrameType

it = VGLIterator(
    campaign=CampaignDate.CAMPAIGN_2022_06_10_10_42_22,
    data_directory=Path("./data"),
    frame=FrameType.CAMERA,
    undistort=True,
    with_landcover=True,
)

sample = it[0]
image = sample["image"]
pose = sample["pose"]
landcover = sample.get("landcover")

Pose Conventions

sample["pose"] is T_world_body (or T_world_body @ T_body_camera for FrameType.CAMERA) built by pygeon.geometry.se3.ins_to_SE3 from the nearest INS sample:

  • Position: latitude/longitude projected to UTM (zone 32N for all LTC campaigns). The RTK corrections come from SAPOS, so the coordinates are ETRS89, i.e. EPSG:25832. altitude is passed through unchanged.
  • Orientation: INS quaternion (body to NED, true north) rotated to ENU. By default it is not rotated by the meridian convergence between true north and UTM grid north (about -0.4 to -1.7 deg over the LTC area, -1.37 deg near 7.2 E / 50.6 N). apply_meridian_convergence=True (optionally with crs="EPSG:25832") expresses the orientation in grid axes. The published LTC extrinsics belong to the default (uncorrected) convention; use the correction only with extrinsics estimated from corrected poses.
  • Precision: geodetic coordinates and quaternions are read as float64. Versions before 0.1.0 read them as float32, which moved positions by up to ~1 m.
  • Accuracies: sample["pose_uncertainty"] holds the INS-stated 1-sigma position (m) and angle (rad) accuracies (NaN if the file lacks the columns). Early internal exports of ins.csv have zero position accuracies; the published files contain the INS-stated values (a few cm).

Examples

Run the VIO example against a local dataset:

python examples/vio_iterator.py \
  --data-directory /path/to/ltc-data \
  --campaign 2022-02-23-11-45-35

Run the VGL viewer after installing the orthophoto extra and configuring georaffer:

python examples/vgl_iterator.py \
  --data-directory /path/to/ltc-data \
  --campaign 2022-02-23-11-45-35 \
  --image-step 1000

Citation

If you use the LTC dataset or pygeon, please cite:

@inproceedings{schleiss2026leaving,
  title={Leaving the City: A Large-Scale Aerial Dataset for Cross-Season Localization in Unstructured Environments},
  author={Schleiss, Michael and H{\"o}lzemann, Henry and Rouatbi, Fahmi and Fiolka, Torsten and Pany, Thomas and F{\"o}rstner, Roger and Cremers, Daniel},
  booktitle={European Conference on Computer Vision},
  pages={96--113},
  year={2026},
  organization={Springer}
}

License

The code in this repository is released under the MIT License; see LICENSE.

The LTC dataset is not part of this repository. It is licensed under the Creative Commons Attribution 4.0 International License (CC BY 4.0), © 2026 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V., represented by Fraunhofer FKIE. The land-cover masks are derived from CORINE Land Cover 5 ha, 2018 (CLC5-2018): © GeoBasis-DE / BKG (2025), dl-de/by-2-0; modified: rasterized into masks aligned with the camera images. Orthophotos and surface models downloaded through georaffer are subject to the licenses of their providers.

Metadata

Release files for pygeon-ltc 0.1.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for pygeon-ltc 0.1.0
File Size Uploaded Provenance Actions
pygeon_ltc-0.1.0.tar.gz 61.5 kB With provenance Details for pygeon_ltc-0.1.0.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for pygeon-ltc 0.1.0
File Interpreter ABI Platform Actions
pygeon_ltc-0.1.0-py3-none-any.whl Python 3 none any Details for pygeon_ltc-0.1.0-py3-none-any.whl

Total release size: 131.9 kB

Release files / pygeon_ltc-0.1.0.tar.gz

Download URL pygeon_ltc-0.1.0.tar.gz
Size 61.5 kB
Tags Source
SHA-256 checksum
How to use checksums
f83a1a94a3078e95221021c671a51f6068e891133139aa7a2804f31c9330e6d8
BLAKE2b-256 checksum
How to use checksums
9b8b3ae9efe7dbb22801cba24388a0d4d2d37a8890390901c85c01ed3bff9b84
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.

Transparency log

Release files / pygeon_ltc-0.1.0-py3-none-any.whl

Download URL pygeon_ltc-0.1.0-py3-none-any.whl
Size 70.4 kB
Tags Python 3
SHA-256 checksum
How to use checksums
9c11f5772186c787a9ff5ca618e78bb26ce61c64f03a939f3dbe7fbd8fab7314
BLAKE2b-256 checksum
How to use checksums
1f7be4fe4e415f5ab3359cc21e55e8c6148ddba7a62485200300d6e9f91df2d9
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.

Transparency log

Security for pygeon-ltc 0.1.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

Full provenance

All 2 files in this release have been uploaded with provenance metadata.

Select from 2 files

Attestation for pygeon_ltc-0.1.0.tar.gz

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Oct 12, 2026.

Transparency log

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Release history Release notifications | RSS feed

This release

0.1.0 This release

2 release files Full provenance

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page