Skip to main content

zero2geospatial3d-sdk

PyPI version Python version support License: MIT Code style: Ruff Test Coverage

Headless 3D terrain and building analysis in Python: sun hours, shadows, sky view factor, solar PV, UTCI/PET comfort, wind, noise and air-quality screening, daylight rules, terrain sections, flooding and cut/fill.

PyPI Package • GitHub • Issue Tracker • QGIS plugin

zero2geospatial3d-sdk is the scriptable, QGIS-free engine behind the 02 Geo3D Analyzer QGIS plugin (zero2geospatial3d). The plugin runs its analyses on the GPU in a browser; this package ports the same mathematics to NumPy so they run in notebooks, batch jobs, servers and CI pipelines. Scene packages are interchangeable: a scene exported by the plugin loads in Python, and a scene built in Python opens in the bundled browser viewer.

Installation

# Core: NumPy only
pip install zero2geospatial3d-sdk

# Optional geospatial extras (GeoTIFF output with rasterio, pyproj, shapely, matplotlib)
pip install "zero2geospatial3d-sdk[geo]"

Python 3.9 to 3.13. The import name is zero2geospatial3d.

Quickstart (runs offline)

import numpy as np
from zero2geospatial3d import Building, Scene, shading, comfort, terrain
from zero2geospatial3d.results import aggregate_by_id

# A 200 m x 200 m level site in Izmir (UTC+3) with a 2 m grid and two buildings.
scene = Scene.flat(200, 200, cell=2.0, lat=38.42, lon=27.14, utc_offset=3.0)
for cx, h in ((-30, 24.0), (30, 12.0)):
    ring = [[cx - 15, -10], [cx + 15, -10], [cx + 15, 10], [cx - 15, 10], [cx - 15, -10]]
    scene.buildings.append(Building([[ring]], height=h))

surface = scene.surface()                     # terrain + buildings as a Grid
_, ids = scene.building_rasters()             # building id per cell (0 = ground)

# BRE 209: sun hours on 21 March
hours = shading.sun_hours(surface, scene.lat, scene.lon, scene.utc_offset, month=3, day=21)
open_ground = hours[ids == 0]
print(f"open ground with >= 2 h of sun: {100 * np.mean(open_ground >= 2):.0f} %")

# Sky view factor and per-building roof statistics
svf = shading.sky_view_factor(surface, n_azimuths=16)
print(aggregate_by_id(ids, svf, cell_area=4.0)[1]["mean"])

# Thermal comfort for one set of conditions
print(comfort.utci(32.0, 55.0, 1.5, 40.0), comfort.pet(32.0, 55.0, 1.5, 40.0))

# Terrain: slope, flooding and earthworks on the DEM
slope, aspect = terrain.slope_aspect(scene.terrain)
pad = [[-20, -20], [20, -20], [20, 20], [-20, 20], [-20, -20]]
print(terrain.cut_fill(scene.terrain, pad, design_level=0.5).fill)

Command line

zero2geospatial3d sun --lat 38.42 --lon 27.14 --date 2026-06-21 --tz 3
zero2geospatial3d comfort --ta 32 --tr 55 --v 1.5 --rh 40
zero2geospatial3d stations --lat 41.01 --lon 28.97 -n 3          # nearest TMYx stations
zero2geospatial3d epw --lat 41.01 --lon 28.97 --out istanbul.epw   # download the nearest one

zero2geospatial3d demo --out demo_scene                            # synthetic scene package
zero2geospatial3d osm --lat 38.4237 --lon 27.1428 --half-size 250 --out izmir_scene
zero2geospatial3d analyze demo_scene sun-hours --date 2026-03-21 --out sun.asc
zero2geospatial3d analyze demo_scene svf --azimuths 36 --out svf.npy
zero2geospatial3d analyze demo_scene irradiation --epw istanbul.epw --out kwh.tif   # .tif needs [geo]
zero2geospatial3d analyze demo_scene flood --level 12 --out depth.asc
zero2geospatial3d view demo_scene --results results/                 # bundled 3D viewer

analyze supports sun-hours, shadow, svf, viewshed, irradiation, slope, aspect, hillshade and flood, and prints summary statistics as JSON. view serves the plugin's three.js viewer on 127.0.0.1 (your data stays on your computer); results sent from the viewer are saved to --results.

How the 3D analyses work headlessly

The plugin renders depth maps of the full 3D scene on the GPU. The SDK works on a 2.5-D surface: the DEM plus the heights of buildings (and optionally tree crowns) rasterised onto the same grid. Sun visibility is tested by marching rays across this surface with bilinear sampling, the sky view factor is 1 - mean(sin^2(horizon)) over azimuth sectors, and irradiation combines direct sun (from EPW or clear-sky sun-direction bins), isotropic diffuse sky and ground reflection, exactly as the plugin's solarRadiation runner does. Overhangs and facade receivers are not represented in 2.5-D.

Public API

Module Main contents
grid Grid (values, cell, min_x, max_y; sample, coords, index_of), make_grid
scene Scene (flat, from_osm, surface, building_rasters, tree_raster, export), Building, Tree, Road, load_scene, rasterize_polygons
solar solar_position, sunrise_sunset, sun_path, sky_hemisphere, sun_vector, day_of_year
shading shadow_mask, sun_hours, shadow_study, horizon_angles, sky_view_factor, viewshed, directional_irradiation, solar_irradiation, pv_yield
comfort utci, pet, mean_radiant_temperature, sky_temperature, projected_area_factor, utci_category, pet_category
weather Weather, parse_epw, read_epw, monthly_summary, wind_rose, clear_sky_year, annual_sun_bins, conditions_at, typical_doy
epw nearest_stations, load_index, download_station, extract_epw, read_header
microclimate surface_temperature, canopy_transmittance, canopy_cooling_grid, diurnal_point_profile, SURFACE_MATERIALS
wind wind_ratio, lawson_class, OPEN_PEDESTRIAN_FACTOR
morphology distance_to_built, macdonald, classify_lcz, block_indicators
dispersion ventilation_efficiency, pollutant_dispersion, ventilation_class, air_quality_class
acoustics noise_propagation, building_facade_noise, maekawa_diffraction, noise_class
road_sources sample_road_lines, street_centrelines, road_weight
daylight prepare_rule, check_rule, vsc_long, allowed_angle, reach25, wall_samples (BRE 209)
urban_form green_view_index, solar_envelope, gvi_class
walkability pedestrian_walkability_index, find_cool_route, subscores
terrain slope_aspect, hillshade, contours, profile, flood, cut_fill, balanced_level, curvature, tpi, ruggedness, aspect_classes, flow_accumulation, wetness, crop_grid
classify equal_breaks, quantile_breaks, jenks_breaks, ramp_stops, ramp_color, RAMPS
nsga2 Problem, nsga2, dominates, non_dominated_sort, crowding_distance
osm, osm_tags fetch (Overpass, timeouts, cache), payload_to_features, building_height, road_traffic
geo lonlat_to_local, local_to_lonlat, bbox_around, utm_epsg_for, grid_shape
results aggregate_by_id, grid_stats, write_ascii_grid, write_grid_npy, write_geotiff, save_result
server serve_scene, ViewerServer, viewer_root

All grids are NumPy arrays of shape (rows, cols) with row 0 at the north edge; coordinates are local metres (x east, y north). Angles from solar are radians with azimuth clockwise from north.

Validation

The test suite reproduces the numeric assertions of the plugin's JavaScript tests (tests/js/*.test.mjs): the NREL SPA reference sun position, UTCI and PET reference values, EPW parsing and wind roses, surface energy balance and canopy cooling, Maekawa diffraction and traffic-noise scaling, ventilation and dispersion, BRE 209 VSC closed forms, solar envelopes and green view, terrain curvature, TPI, TRI, flow accumulation and wetness, flood and cut/fill volumes, Jenks breaks, and the seeded NSGA-II run. The shading engines are checked against closed forms (canyon sky view factor, wall shadow length).

Development and testing

git clone https://github.com/YusufEminoglu/zero2geospatial3d_sdk.git
cd zero2geospatial3d_sdk
pip install -e ".[dev]"
python -m pytest --cov=zero2geospatial3d
python -m ruff check .
python -m mypy src

Academic citation

@software{eminoglu_zero2geospatial3d_sdk,
  author  = {Eminoğlu, Yusuf},
  title   = {zero2geospatial3d-sdk: headless 3D terrain and building analysis in Python},
  year    = {2026},
  version = {0.1.0},
  url     = {https://github.com/YusufEminoglu/zero2geospatial3d_sdk}
}

See also CITATION.cff.

License

MIT, see LICENSE. The bundled viewer includes three.js (MIT) and the UTCI polynomial follows pythermalcomfort (MIT); the station index credits Climate.OneBuilding.Org. Details in THIRD_PARTY_NOTICES.md.

Metadata

Release files for zero2geospatial3d-sdk 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 zero2geospatial3d-sdk 0.1.0
File Size Uploaded Provenance Actions
zero2geospatial3d_sdk-0.1.0.tar.gz 1.2 MB With provenance Details for zero2geospatial3d_sdk-0.1.0.tar.gz

Built distribution (wheel)

Table of built distributions (wheels) for zero2geospatial3d-sdk 0.1.0
File Interpreter ABI Platform Actions
zero2geospatial3d_sdk-0.1.0-py3-none-any.whl Python 3 none any Details for zero2geospatial3d_sdk-0.1.0-py3-none-any.whl

Total release size: 2.3 MB

Release files / zero2geospatial3d_sdk-0.1.0.tar.gz

Download URL zero2geospatial3d_sdk-0.1.0.tar.gz
Size 1.2 MB
Tags Source
SHA-256 checksum
How to use checksums
6ca2bac43b3fc75d6955ba1765cc937e523b729cd77aeb2d5f2a339444acc810
BLAKE2b-256 checksum
How to use checksums
0d1b0ea233093195303c4ff45e562f71fe770d126bf507713fce6839d6a82090
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

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 Nov 8, 2026.

Transparency log

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

Download URL zero2geospatial3d_sdk-0.1.0-py3-none-any.whl
Size 1.2 MB
Tags Python 3
SHA-256 checksum
How to use checksums
b5610ec517169ff04dacc837e86b73df6613d7453f1a6c9ff0a105e15ae3a395
BLAKE2b-256 checksum
How to use checksums
f257806afe229b8f1010682a16863edf504a3421e8539b16d486c1e745fe5a91
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.16

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 Nov 8, 2026.

Transparency log

Security for zero2geospatial3d-sdk 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

Both files in this release have been uploaded with provenance metadata.

Select from 2 files

Attestation for zero2geospatial3d_sdk-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 Nov 8, 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