CUGER_building
Introduction
CUGER is a Python-based open-source representation tool that decomposes complex building shapes/plans into convex geometry and encodes them into an improved LPG (Logical Property Graph) structure.
It further supports bidirectional conversion between LPG and RDF, enabling seamless interoperability across heterogeneous building data ecosystems. 🔄
CUGER is not only designed for converting design models into engineering-level BIM/BEM structures, but also for transforming building models into graph datasets for GNN training—supporting downstream tasks such as performance prediction, spatial reasoning, and surrogate simulation. 🧠📐
Conceptually, the framework draws inspiration from Arkin, Ronald C. (1987), “Path Planning for a Vision-Based Autonomous Robot.”
CUGER is built on top of Moosas, and to access its full functionality—including building-model conversion, geometric/semantic recognition, and structured graph generation—you need to install both CUGER and Moosas.
The algorithm is also integrated into Moosas+, and its implementation can be found in: 👉 moosas/MoosasPy/encoding
New: Simplify (LOD) Module
CUGER now includes a geometry simplification stage before convex decomposition.
precise: keep original geometry (no simplification)medium: simplify to multi-layer OBB representationlow: simplify to single OBB representation
This feature is integrated in the processing pipeline as:
Simplify (LOD) -> Convexify -> (optional) Moosas export -> (optional) Graph generation
Installation
Install from PyPI
pip install cuger
The core package only contains the code under cuger/cuger.
If you also need Moosas-based export (.geo/.xml/.idf/.owl) and graph generation,
please install Moosas separately.
Install from git
git clone https://github.com/Romeo_Leeyh/CUGER_building.git
cd cuger
pip install -e .
# or install requirements directly
pip install -r requirements.txt
Install Moosas+
If you just want to try the algorithm to split building models, this step can be ignored. For full installation instructions, please visit the Moosas+ repository.
Usage
Run with Test Script
You can run the example script in test.py.
This will process sample building models under tests/examples/
and generate outputs in tests/example_results/.
tests
├── examples
│ └── example0.geo # Sample test case
└── example_results
├── geo_s # Simplified geometry (_s_<lod>.geo)
├── figure_convex # Convex decomposition figures
├── figure_graph # Graph visualization figures
├── geo_c # Convex converted geometric files
├── graph # Generated graph nodes and edges
├── new_geo # Exported .geo files
├── new_idf # Exported .idf files
├── new_rdf # Exported .rdf files
└── new_xml # Exported .xml files
To run the test:
python test.py
Use as a Python package
The public API follows the same main flow used in test.py:
from cuger import PipelineOptions, process_geo_directory, process_geo_file
options = PipelineOptions(lod="medium")
process_geo_file("tests/examples/example0.geo", "tests/example_results", options=options)
process_geo_directory("tests/examples", "tests/example_results", options=options)
If you only want simplification + convex decomposition and do not want to depend on Moosas:
from cuger import PipelineOptions, process_geo_file
options = PipelineOptions(
lod="medium",
run_moosas=False,
generate_graph=False,
)
process_geo_file("tests/examples/example0.geo", "tests/example_results", options=options)
CLI
After installation, you can also use the packaged command:
cuger -s tests/examples/example0.geo -o tests/example_results -l medium
cuger -i tests/examples -o tests/example_results -l medium
Publish to PyPI
Before publishing, update the version in pyproject.toml.
Build the package:
python -m pip install -U build twine
python -m build
This generates:
dist/cuger-<version>.tar.gzdist/cuger-<version>-py3-none-any.whl
Validate the distribution metadata locally:
python -m twine check dist/*
Upload to TestPyPI first:
python -m twine upload --repository testpypi dist/*
Then test installation:
pip install --index-url https://test.pypi.org/simple/ --extra-index-url https://pypi.org/simple cuger
If everything looks good, upload to the official PyPI index:
python -m twine upload dist/*
After release, verify installation from PyPI:
pip install -U cuger
Optional: configure credentials with .pypirc or environment variables such as
TWINE_USERNAME and TWINE_PASSWORD to avoid typing them each time.
GitHub Actions Auto Publish (PyPI)
This repository includes CI workflow: .github/workflows/publish-pypi.yml.
- Push tag
v*(for examplev0.1.1) -> build and publish to PyPI - Manual run (
workflow_dispatch) -> choose testpypi or pypi
One-time configuration (Trusted Publisher)
-
In PyPI project settings (
cuger), add a Trusted Publisher. -
Owner: your GitHub org/user.
-
Repository:
cugerrepository. -
Workflow name:
publish-pypi.yml. -
Environment:
pypi. -
In TestPyPI project settings (
cuger), add another Trusted Publisher. -
Use the same repository and workflow.
-
Environment:
testpypi. -
In GitHub repository settings, create environments:
pypiandtestpypi.
No PyPI API token secret is required when using Trusted Publisher (OIDC).
Release commands
# 1) bump version in pyproject.toml
# 2) commit and push
git tag v0.1.1
git push origin v0.1.1
If you want to dry-run to TestPyPI first, use Actions -> Publish Python Package -> Run workflow -> repository=testpypi.
Run with CLI (main.py)
main.py supports interactive mode and command-line mode.
# interactive mode
python main.py
# batch process a directory
python main.py -i tests/examples -o tests/example_results -l medium
# process a single file
python main.py -s tests/examples/example0.geo -o tests/example_results -l low
LOD options:
precise(default copy/no simplify in simplify stage)medium(recommended)low
Module I/O Explanation
CUGER operates through a series of processing modules. Each module consumes specific input files and produces standardized outputs that together form the unified graph-based representation of the building model.
Input
.geofile
The primary geometric description of the building.
This file contains surfaces, edges, vertex positions, and semantic tags used to reconstruct the building’s spatial structure.
Intermediate Outputs
-
geo_s/<case_name>_s_<lod>.geo
Simplified geometry generated by the new simplify stage.lod=precise: copied from input geometrylod=medium: multi-layer OBB simplified geometrylod=low: single OBB simplified geometry
-
figure_convex/<case_name>_convex.png
Visualization of the convex decomposition process, showing how non-convex polygons are split. -
figure_graph/<case_name>_graph.png
Graph-level visualizations illustrating nodes, edges, and spatial relationships. -
geo_c/<case_name>_c.geo
Converted or cleaned geometric files after preprocessing and convex decomposition.
Graph Outputs
-
graph/<case_name>.json
Encodes all nodes (faces, spaces, openings, etc.) with geometric, semantic, and topological attributes.Encodes adjacency relations, directional edges, and multi-scale topology for downstream GNN tasks.
Exported Model Formats
new_geo/<case_name>.geo
Reconstructed geometry exported back into.geoformat.new_idf/<case_name>.idf(in development)
Prototype EnergyPlus IDF export based on the generated graph structure.new_rdf/<case_name>.owl
Semantic web representation exported as RDF, suitable for linked-data workflows, which is dumped in.owlformat.new_xml/<case_name>.xml
XML-based representation for interoperability with external BIM or simulation environments.
Processing Stages
- Simplify (
simplify_process)
Input.geo-> simplified.geoingeo_s/according to selected LOD. - Convexify (
convex_process)
Simplified.geo-> convex.geoingeo_c/. - Model Export (Moosas, optional)
Convex.geo->.geo/.xml/.owl/.idfexports. - Graph Construction (
graph_process, optional)
Build LPG JSON graph and visualization figures.
Function
Core entry points:
main.py(CLI + interactive processing)test.py(example pipeline run)cuger/__transform/process.pysimplify_process(...)convex_process(...)graph_process(...)
Citation
If you used this project in your research, please cite the paper below:
@article{liGeometryGraphAutomation2026,
title = {From Geometry to Graph: {{Automation}} of Building Performance Modeling via Convex Graph Encoding},
shorttitle = {From Geometry to Graph},
author = {Li, Yihui and Xiao, Jun and Zhou, Hao and Lin, Borong},
year = 2026,
month = mar,
journal = {Automation in Construction},
volume = {183},
pages = {106815},
issn = {0926-5805},
doi = {10.1016/j.autcon.2026.106815},
}
@inproceedings{Li2024GraphConvex,
author = {Li, Yihui and Xiao, Jun and Zhou, Hao and Lin, Borong.},
title = {A Cross-Scale Normative Encoding Representation Method for 3D Building Models Suitable for Graph Neural Networks},
booktitle = {Proceedings of the Building Simulation Conference 2025},
publisher = {IBPSA},
address = {Brisbane, Australia},
month = {August},
year = {2025},
pages = {},
doi = {10.26868/25222708.2025.1305}
}
Metadata
Release files for cuger 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | |
|---|---|---|---|
| cuger-0.1.0.tar.gz | 43.5 kB | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| cuger-0.1.0-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 88.8 kB
Release files / cuger-0.1.0.tar.gz
| Download URL | cuger-0.1.0.tar.gz |
|---|---|
| Size | 43.5 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
40e10f1816db1151fa4da4b3b78a3e21ad36485f11b2aff885ca0ffa9b0159ae
|
|
BLAKE2b-256 checksum How to use checksums |
7cada0a8fa1d0988f37a3bb9022098588e8d7f034acc0ed5cd3a94d90f5841b0
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.7
|
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 Mar 10, 2026.
Transparency logRelease files / cuger-0.1.0-py3-none-any.whl
| Download URL | cuger-0.1.0-py3-none-any.whl |
|---|---|
| Size | 45.3 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
b2542a649d4fcfe38c6148c215833214dc43858cc909d69097b1adc2c09f5f24
|
|
BLAKE2b-256 checksum How to use checksums |
656913a392fd332d8b5955d36daccfc404ae1175e97faa057ccef7a430194fc4
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
Yes |
| Uploaded via |
twine/6.1.0 CPython/3.13.7
|
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 Mar 10, 2026.
Transparency log