Game-agnostic weather and atmosphere engine for Godot 4.7: climate contracts, a reduced atmospheric runtime, wind field and the frozen plant-kernel forcing ABI.
  • GDScript 89.1%
  • Python 7.9%
  • Shell 3%
Find a file
Repository files (latest commit first)
Filename Latest commit message Latest commit date
cmkrist 309c57476a Match SeaState's build/decay defaults to EnC's water
EnC's water_view used 12 s to build and 30 s to decay; 0.3.0 shipped 26/90 as a
placeholder. Set them to 12/30 so a consumer moving to advance_toward keeps the
sea's response, and bump to 0.3.1 because 0.3.0 is published.

Verified: tools/run_tests.sh, 5 suites, 0 failures.
2026-09-16 10:04:40 -04:00
addons/weather_pp Match SeaState's build/decay defaults to EnC's water 2026-09-16 10:04:40 -04:00
bench Reduce to the contracts a presenter needs 2026-09-16 06:38:49 -04:00
docs Reduce to the contracts a presenter needs 2026-09-16 06:38:49 -04:00
scenes Reduce to the contracts a presenter needs 2026-09-16 06:38:49 -04:00
tests Give SeaState EnC's fetch-limited wave model 2026-09-16 10:03:35 -04:00
tools Add a standalone benchmark harness with a committed baseline 2026-09-15 19:16:00 -04:00
.gitignore Add a standalone benchmark harness with a committed baseline 2026-09-15 19:16:00 -04:00
LICENSE Initial commit: weatherpp plugin skeleton 2026-09-15 16:57:39 -04:00
project.godot Initial commit: weatherpp plugin skeleton 2026-09-15 16:57:39 -04:00
README.md Give SeaState EnC's fetch-limited wave model 2026-09-16 10:03:35 -04:00

WeatherPP

Presentation and quality contracts for weather in Godot 4.7: quality tiers, the frozen forcing ABI a compiled plant kernel reads, the climate clock, and sea state.

The weather simulation is not here. It lives in the WorldMaker plugin, which owns the world and therefore owns its climate. WeatherPP describes weather for a presenter.

Status

Version 0.3.0. 0.2.0 was a scope reduction: the plugin previously shipped its own weather engine, sampler, wind field, climate profile and grid. Those moved to WorldMaker when EnC's real simulation did, which left this plugin as a second implementation of the same atmosphere. 0.3.0 then gave SeaState the fetch-limited wave model EnC's water actually uses: a growth (wave age) term with build/decay, and a WaveSpectrum that couples each band to the local wind. What remains is what a game actually consumes. See docs/MIGRATION_FROM_ENC.md.

What it provides

WeatherConfig Quality tiers: edge scaling, relaxation passes, worker caps, cloud display heights
WeatherSample One tile's weather, and forcing() — the frozen Vector4 axis contract
ClimateCalendar Ticks per day, year length, axial tilt, season phase, declination
SeaState Swell growth from wind and exposure, build/decay easing, chop, foam
WaveSpectrum Wave shape as a pure static function: per-band wind alignment, mesh fade

Install

python3 tools/package_addon.py /path/to/consumer/project

Installs addons/weather_pp/. Runtime use does not require the editor plugin; the dock only reports which version and ABI are installed.

# Quality for the terrain the atmosphere is running on.
var config := WeatherConfig.for_tier(WeatherConfig.QualityTier.HIGH)
var edge := config.effective_edge(terrain_edge)

# The contract a compiled kernel reads. Check the ABI version first.
if WeatherPPManifest.forcing_abi_version() == WeatherSample.FORCING_VERSION:
    var forcing := sample.forcing()   # (temperature_c, rain, snow, evaporation)

# Sea state for a water presenter.
var sea := SeaState.from_wind(weather.wind_speed, weather.wind_direction, tile)
sea.exposure = shelter_factor(tile)          # 0 sheltered cove .. 1 open ocean
sea.advance_toward(fetch_target(tile), dt)   # wave age: build/decay, or omit for open ocean
var y := sea.height(vertex, cells_across, stride, time)

Layout

addons/weather_pp/   the installable plugin
  core/              data contracts (config, sample, calendar, sea state, spectrum)
  runtime/           the manifest reader
docs/                architecture, API, and what moved out of this plugin
scenes/              playground.tscn — a runnable headless demonstration
tests/               standalone SceneTree suites
bench/               standalone benchmarks + committed baseline
tools/               package_addon.py, run_tests.sh, run_bench.sh, compare_bench.py

Verify

godot --headless --path .        # the playground demo, then quits
./tools/run_tests.sh             # 5 suites
./tools/run_bench.sh --compare   # benchmarks against the committed baseline

Everything runs with no game and no world present: the contracts are pure, and the benchmarks construct no grid, no engine and no terrain.

Benchmarks

Case Median Notes
sample_forcing_100k 68 ns/op The per-tile ABI packing a kernel reads.
sea_height_10k ~2.0 µs/op Per-vertex cost. Worth knowing before evaluating it across a large mesh.
calendar_season_100k ~810 ns/tick Three calendar queries per tick.
config_resolve_1000 ~3.5 µs/op Allocates a WeatherConfig; do not call it per frame.

Not in this plugin

The weather simulation (WeatherSystem, AtmosphereGrid, WorldTopology) — that is WorldMaker's. Rendering: cloud lobes and the water mesh stay in the game, which also supplies sea exposure and the fetch-limited growth target because only it knows the coastline.

Licence

MIT. See LICENSE.