No description
  • C# 95.4%
  • HTML 2.4%
  • Python 1.5%
  • Shell 0.7%
Find a file
Flexhd41 6a94511790
All checks were successful
Build / build (push) Successful in 1m59s
Build / vintage-story-version (push) Successful in 2s
Strata 0.4.1 public source release
2026-07-27 23:18:54 +02:00
.forgejo/workflows Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
build Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
release Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
Strata Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
Strata.Diffusion Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
Strata.Diffusion.Cli Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
tools Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
.gitignore Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
Directory.Build.props Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
LICENSE Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
MODEL_SHA256SUMS.txt Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
README.md Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
Strata.sln Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00
THIRD_PARTY_NOTICES.md Strata 0.4.1 public source release 2026-07-27 23:18:54 +02:00

Strata

Strata is a Vintage Story 1.22 world-generation mod that replaces the initial vanilla terrain height fill with the infinite terrain-diffusion ONNX pipeline. Vintage Story still performs its normal rock-strata, cave, ore, soil, vegetation, and structure generation afterward. Vintage Story's latitude-driven temperature remains authoritative and conditions the model in realistic-climate worlds; the model supplies the precipitation field. Clients do not need to install the mod; an optional client installation adds directional river animation when experimental Rivers V4 is enabled.

Building from source

Strata compiles against Vintage Story's own assemblies. tools/fetch_vintage_story.sh downloads them from the official CDN — the Linux server tarball, which carries every referenced assembly, is far smaller than a game install and needs no account:

export VINTAGE_STORY="$(tools/fetch_vintage_story.sh)"   # or: tools/fetch_vintage_story.sh 1.22.5
dotnet build Strata.sln -c Release

Passing no version resolves the current stable release from api.vintagestory.at. The script is idempotent, so re-running it reuses an existing download of the same version. If you already have the game installed, just point VINTAGE_STORY at that directory instead.

.forgejo/workflows/build.yml runs the same steps in CI on a docker runner and publishes all three packages. It also reports, without failing the build, when the latest stable Vintage Story release has moved past the version declared in Strata/modinfo.json.

One ModDB-compatible ZIP with Windows GPU acceleration

Build the release package:

dotnet build build/Strata.Package.proj -t:PackageUniversalDirectML

This produces artifacts/packages/Strata-0.4.1-universal-directml.zip (36,366,053 bytes), below the Vintage Story ModDB 40 MB limit. Install it directly in the server or single-player Mods directory; do not unpack it. Windows x64 uses DirectML on DirectX 12 GPUs from NVIDIA, AMD, or Intel. Windows Arm64, Linux x64/Arm64, and Apple Silicon retain CPU-capable runtimes in the same ZIP. auto falls back to CPU if an accelerator cannot create a model session.

The compact Windows runtime uses the DirectML component supplied by supported Windows versions; Windows 10 version 1903 or newer and a DirectX 12-capable GPU are required for acceleration. The large CUDA developer build remains available with -t:PackageUniversalAccelerated, but its native libraries make it about 431 MB and therefore unsuitable for ModDB. The CPU-only universal target and per-platform Package/PackageAll targets remain available for testing.

What the CUDA package requires

The CUDA package (Strata-<version>-universal-accelerated.zip) bundles ONNX Runtime 1.27.1's CUDA provider but not the CUDA libraries themselves, which remain a system dependency. Most Windows users should prefer the DirectML package instead: it needs none of the following, works on AMD and Intel GPUs too, and is a tenth of the download.

  • Windows x64 or Linux x64. No CUDA build exists for Windows Arm64, Linux Arm64, or macOS; those platforms fall back to the CPU runtime inside the same ZIP.
  • An NVIDIA GPU of Turing generation or newer. The provider is compiled for compute capabilities 7.0, 7.5, 8.0, 8.6, 8.9, 9.0, 10.0 and 12.0 — that is Volta, Turing (GTX 16 / RTX 20), Ampere (RTX 30), Ada (RTX 40), Hopper and Blackwell (RTX 50). Pascal (GTX 10 series) and older are not supported, because CUDA 13 dropped them; those cards must use DirectML or CPU.
  • CUDA 13.x runtime libraries. The provider links libcudart.so.13, libcublas.so.13, libcublasLt.so.13, libcufft.so.12 and libcurand.so.10 (cublas64_13.dll, cublasLt64_13.dll, cufft64_12.dll on Windows). CUDA 12 is not sufficient.
  • cuDNN 9.x (libcudnn.so.9 / cudnn64_9.dll).
  • An NVIDIA driver new enough for CUDA 13. Check NVIDIA's CUDA release notes for the minimum version for your platform; installing a current driver is the simplest route.
  • Free VRAM. The base model's weights alone are 2.0 GB in FP32, so allow roughly 4 GB of free VRAM in addition to whatever the game itself is using.

The libraries must be discoverable at load time — on the default PATH on Windows, or on the loader path on Linux. Installing the CUDA Toolkit and cuDNN handles this. If a CUDA session cannot be created, InferenceDevice: "auto" logs the reason and falls back to CPU rather than failing generation, so a missing dependency shows up as slow terrain rather than a crash. Use InferenceDevice: "cuda" to require it and get a hard error instead.

The models are intentionally separate from the mod ZIP. On first uncached terrain generation, Strata downloads five files totaling about 2.3 GB directly over HTTPS from Alexander Goslin's official Hugging Face ONNX repository. They are stored in the game data directory's StrataModels folder and reused for all worlds. Set AutoDownloadModels to false if you prefer to install the files manually.

Release downloads are pinned to immutable Hugging Face revision ad2df557eca5645f588766101cf3bc3682455c3e. Strata verifies the expected byte length and SHA-256 of every official file before first use and refuses to load a mismatch. Successful verification is remembered beside each model; the published values are in MODEL_SHA256SUMS.txt and in the ZIP's licenses folder. ONNX files are model graphs/weights rather than game plugins, and no data is uploaded during inference; they are nevertheless large third-party inputs to ONNX Runtime, so manual installation with AutoDownloadModels=false remains available for cautious servers.

World height

Set the world height to 512 on Vintage Story's create-world screen. For a dedicated server, set MapSizeY to 512 before creating the save. A code mod is initialized only after Vintage Story has fixed the new save's vertical chunk layout, so Strata warns about a mismatch but does not risk resizing a world. Existing worlds cannot be safely resized.

The configured WorldHeight is the recommended/expected height used by that warning. Heights are made of 32-block vertical chunks, and taller worlds cost additional vanilla worldgen time even when the terrain surface stays at the same elevation.

Performance and diagnostics

Run this as a server administrator while chunks are generating:

/strata stats

It reports pipeline state, each model's actual ONNX provider, generated/fallback chunk counts, Strata block-fill time, cache hit rates, tile bakes and queue depth, and per-model inference time. The startup log reports the platform, world height, effective settings, model readiness, and confirms that downstream vanilla cave/worldgen passes remain active.

Useful settings in VintagestoryData/ModConfig/strata.json:

  • TerrainStyle: realistic preserves the existing official terrain distribution and remains the default. fantasy reorganizes macro elevation into stronger ridge systems and selectively raises established highlands. extreme makes those systems more frequent and amplifies them further. Every style still uses the full-resolution base and decoder models, vanilla caves, and the plains shaping pass.
  • InferenceDevice: leave this at auto to use DirectML automatically on Windows x64 and CPU or the available platform provider elsewhere. Use directml to require DirectML, or cpu to disable GPU inference. gpu requires any usable GPU provider and reports a clear error if none works.
  • GpuDeviceId: DirectML/CUDA adapter index, normally 0.

Apple Silicon GPU (Metal via WebGPU)

The base model dominates generation time and previously produced garbage terrain on ONNX Runtime's WebGPU provider (Dawn → Metal). The cause is a WebGPU convolution bug that only affects an input with exactly 6 channels; 3, 5, 7, 8, 12 and 16 channels all match the CPU provider. Exactly one of the base model's 95 convolutions hits that shape — the first one — so its error propagated through the whole network.

tools/make_webgpu_base_model.py widens that single convolution from 6 to 8 input channels by appending zero channels to both its input and its weight. The added terms contribute exactly zero, so the patched model is bit-identical to the original on the CPU provider; nothing is retrained or quantized.

python3 tools/make_webgpu_base_model.py models/base_model.onnx models/base_model_webgpu.onnx

Then select it with ModelVariant: "custom" and CustomBaseModelFile: "base_model_webgpu.onnx", and send only the base model to WebGPU via STRATA_DEV_BASE=webgpu.

Measured on an Apple M2, one 128-block tile including drainage and carving: 98.7 s → 24.8 s, with an identical elevation range and identical river output. Keep the coarse model on CoreML and the decoder on CPU — the decoder is independently wrong on WebGPU (a different defect, since it has no 6-channel convolution) and running it there corrupts elevations. Because GPU and CPU accumulate in different orders, WebGPU-generated terrain differs from CPU terrain by roughly 1e-6 m; that is far below one block and cannot produce a visible seam, but it is not bit-reproducible across providers.

  • ModelVariant: fp32 selects the official models and remains the default. fp16 selects local base_model_fp16.onnx, coarse_model_fp16.onnx, and decoder_model_fp16.onnx files. auto prefers that complete local FP16 set and otherwise uses FP32. custom uses the five configurable Custom*File names.
  • InferenceBatchSize: batches independent windows without reducing resolution or diffusion steps. CPU-heavy model stages automatically remain at batch 1 because batching was slower there.
  • TileChunks: larger tiles reuse more intermediate work, but the first new tile takes longer.
  • MemoryCacheTiles: bounded in-memory LRU for baked heightmaps.
  • DiskCache: reuses deterministic baked tiles after restarts.
  • PrefetchRadius: defaults to 0 so background model work cannot block an urgently requested tile. Try 1 only when the server has spare inference capacity.
  • IntraOpThreads: defaults to 0, letting ONNX Runtime choose its CPU thread pool.
  • SummitCompressionHeadroom: defaults to 96 blocks. Model elevations entering this top band are progressively compressed toward the ceiling instead of hard-clipped, retaining distinct summits and ridges rather than producing large flat top-of-world plateaus. Set it to 0 for the old clamp.
  • ExposeMountainRock: defaults to true. After the normal block-layer pass, sufficiently steep mountain surfaces reveal Vintage Story's locally selected rock type instead of remaining fully soil-covered. MountainRockMinHeightAboveSeaLevel, MountainRockFullHeightAboveSeaLevel, MountainRockReliefRadius, and the two MountainRock*Relief settings tune that transition.
  • ExperimentalRivers: defaults to false. Rivers V4 builds deterministic macro drainage plans, routes ocean-connected channels downhill, turns each macro reach into a slope-aware meander, then rasterizes it as a noise-warped distance field: a valley is drawn down around each reach before the channel itself is carved with a monotonically descending freshwater surface.
  • RiverValleyWidthBlocks and RiverValleyRiseMeters: default to 48 blocks and 120 meters, the width of the valley beside each channel and how far its floor climbs toward the rim. The valley only ever lowers terrain and its weight reaches zero at the rim, so flat country is untouched and coastlines cannot be cut below sea level. Set the width to 0 for the old narrow shoulders.
  • RiverBankNoiseStrength and RiverBankNoiseFrequency: default to 22 blocks and 0.006, warping the bank outline so channel edges wander instead of tracing the planned polyline. Set the strength to 0 for geometrically straight banks.
  • RiverGravelBanks: defaults to true, replacing block-layer soil within RiverGravelReachBlocks (default 10) of a channel with the locally correct gravel variant, giving rivers gravel beds and banks. The affected width is noise-modulated, so the gravel edge does not trace the channel.
  • RiverMacroRegionCells: defaults to 32, an 8,192×8,192-block drainage plan. Larger values plan farther at once but increase the one-time coarse-model cost. Synthetic terminal lakes are off by default; ExperimentalRiverLakes and RiverLakeGoalsPerRegion opt into the unfinished behavior.
  • RiverMinimumDropMetersPerMacroCell and RiverMaximumDropMetersPerMacroCell bound the water surface drop per 256 horizontal blocks. At the default 15 meters per VS block, shallow gradients appear as periodic one-block steps instead of a perfectly flat water plane.
  • RiverVisualFlowSpeed: controls optional client-side directional water animation. Clients that do not install Strata still see ordinary water and can join normally.
  • RiverPhysicalFlowStrength: controls the server-authoritative current applied to entities in river columns. Set it to 0 to retain visual/elevation flow without entity drift.
  • RiverHydrologyHalo: retained only so older configuration files remain readable; regional rivers no longer treat independently generated tile edges as drainage outlets.
  • RiverFlowThreshold: defaults to 1400 precipitation-weighted upstream cells. Lower values add more headwater streams. RiverMaxWidthBlocks, RiverMinDepthBlocks, RiverMaxDepthBlocks, and RiverMinElevationMeters control the channel geometry.
  • PlainsSmoothing: defaults to 0.65. Set it from 0 to 1 to control how strongly naturally low-relief inland terrain is blended toward a broader, gentler surface. Set it to 0 for the raw model output.
  • PlainsSmoothingRadius: defaults to 16 blocks. Larger values make broader plains and add a correspondingly larger seamless halo to each tile request.
  • PlainsMaxReliefMeters: defaults to 180. Lower values protect more hills; higher values allow smoothing to affect rougher rolling terrain.
  • PlainsCoastProtectionMeters: defaults to 90, fading the filter out near sea level so coastlines, beaches and small islands retain their model detail.

Strata downloads only the validated official FP32 set. FP16 and custom weights are local-only and must preserve the official tensor names, shapes, and float32 inputs/outputs. They may use reduced precision internally. The selected variant and configured file paths are included in the disk-cache identity, so different configured sets do not silently share baked heightmaps.

The terrain style is also part of the disk-cache identity. Pick a style before exploring a new world: changing it later cannot reshape chunks that Vintage Story has already saved and will create a border between old and newly generated terrain.

No model resolution or diffusion step count is reduced. The optional plains pass runs after full-detail inference and intentionally softens only low-relief terrain; mountains and protected coasts retain the original model elevation. Its settings are part of the disk-cache filename, so a changed profile cannot silently reuse a differently filtered height tile. Change shaping settings only before creating a world or expect borders against chunks that were already generated.

Mod compatibility

  • Terrain Slabs 1.0.17: expected to be compatible. It runs a later world-generation pass that replaces suitable exposed blocks with slabs rather than replacing GenTerra. Terrain Slabs and its required PlaceOnSlabs dependency are both-side mods, so install them on the server and clients. This combination still needs longer playtesting.
  • Algernon's Watersheds: incompatible. Both mods change GenTerra; Strata detects mod ID watersheds, logs a prominent error, and leaves its own terrain patch inactive to prevent broken generation. Remove one of the two mods and use a new world rather than trying to solve it through load order.
  • Rivers: incompatible in its current form. Rivers disables vanilla GenTerra and supplies a complete replacement, while Strata supplies its own terrain heights. Strata detects mod ID rivers and leaves its patch inactive instead of allowing two terrain generators to collide. The two cannot be reconciled by load order: Rivers seeds river mouths from Vintage Story's own ocean noise and grows channels inland from them, whereas Strata's coastlines come from the diffusion model, so its mouths would land inland. Strata instead adapts the MIT-licensed VSRiverGen fork's channel rasterization and gravel banks on top of its own drainage routing; see THIRD_PARTY_NOTICES.md.

The Terrain Diffusion models provide elevation and climate fields, but no river-channel output. Strata therefore derives a deterministic regional drainage graph from the model's coarse elevation and precipitation fields. Priority-flood routing connects ocean catchments before any detailed tile is carved, so cache-tile order cannot invent arbitrary river ends. A cached slope-aware subdivision adds continuous local bends without another model call; broad low-gradient reaches meander more than steep reaches. Full-detail carving stores the descending surface and downstream vector with each tile. Treat this as an experimental new-world feature; changing its settings cannot recarve saved chunks.

Preliminary benchmark

In a packaged Vintage Story 1.22.3 server smoke test on an Apple M2 with a 512-block world, Strata processed 225 terrain callbacks with zero fallbacks and baked four diffusion tiles in about 90 seconds. The cache reached a 98.2% hit rate, while Strata's block fill used only 11 ms. ONNX time was about 53 seconds for base, 36 seconds for decoder, and 1 second for coarse; coarse used CoreML while base and decoder used CPU. Model loading took 12.8 seconds. A separate 64x64 deterministic regression sample took about 35 seconds, and optimized/baseline outputs were byte-for-byte identical.

On an RTX 5070 Ti with a Ryzen 9800X3D, all three models resolved to DirectML. A mixed-cache test generated 23 new tiles in 10 seconds of pipeline time (16 seconds bake wall time), with 1,429 chunks reported at 1m38s uptime, 98.4% cache hits, and zero fallbacks or failures. Eleven additional tiles were loaded from disk, so this should not be presented as a fully cold benchmark.

Development

dotnet build Strata.sln

Cross-builds need a local Vintage Story installation for compile-time API references. If it is not in a standard location, set VINTAGE_STORY to the directory containing VintagestoryAPI.dll.

The Vintage Story integration is organized by responsibility under Strata/: Configuration, Caching, Generation (including Hydrology and surface rules), and Patches. The diffusion runtime remains isolated in Strata.Diffusion.

AI assistance

I designed and wrote Strata. I used AI tools as supporting aids for research, occasional code completion, polishing descriptions and documentation, and drafting some code comments. I reviewed and tested the changes and am responsible for the released code.

Credits

The diffusion pipeline and 30 m/px models are based on Alexander Goslin's Terrain Diffusion and ONNX model release. See THIRD_PARTY_NOTICES.md and the packaged licenses directory for licenses and attribution.

License

Strata's original code and documentation are licensed under the Apache License 2.0. Bundled and adapted third-party components retain their original licenses as documented in THIRD_PARTY_NOTICES.md.