bevy_map_scatter
Bevy plugin that integrates the map_scatter core crate for object scattering with field-graph evaluation and sampling.

Overview
bevy_map_scatter wires the map_scatter runtime into Bevy in an ECS- and editor-friendly way:
- Asset-based authoring of scatter plans (RON): load
*.scatterfiles viaAssetServer. - Texture integration: snapshot Bevy
Images to CPU textures with configurable domain mapping. - Asynchronous execution: runs scatter jobs on
AsyncComputeTaskPool. - Streaming diagnostics: forward core
ScatterEvents as Bevy messages (ScatterMessage).
Use Cases
Use bevy_map_scatter when you want to populate a Bevy world with many small entities (plants, props, resources, decals) in a way that stays data‑driven, repeatable, and easy to iterate inside your ECS + asset workflow.
You control:
- Where things may appear (scatter plan fields, textures, masks)
- How different categories avoid or complement each other (layer order + overlays)
- Distribution style (blue‑noise, grids, clustered, low‑discrepancy)
- Deterministic seeds for builds, while still allowing variation per run if desired
Three Bevy‑flavoured examples:
-
Stylized forest scene
Load aforest.scatterasset: first layer places large trees sparsely; second layer adds mushrooms only where tree probability is low; third layer fills remaining space with grass sprouts. Tweaking a gradient texture or a numeric threshold in the RON file and hot‑reloading instantly updates placement logic without touching code. -
Town dressing in an in‑editor tool
A scatter plan drives benches near plazas (inside a plaza mask), lamp posts at moderate spacing along exported road splines (converted to a texture/field), and small clutter (barrels/crates) only where neither benches nor lamp posts were placed (using an overlay exclusion). Designers modify masks and rerun a scatter system; results stream in asynchronously without stalling the main thread. -
Dungeon encounter setup Camps (safe zones) are placed first in large rooms. Enemy spawn markers are placed next-never inside camp influence. Rare loot node markers are then sprinkled in dead‑end corridors with a low probability but enforced spacing. All become regular Bevy entities you can query, tag, despawn, or decorate further in subsequent systems.
Why it fits nicely into Bevy:
- Assets: scatter plans are just assets-versioned, hot‑reloadable, serializable.
- ECS: placements become entities; you decide what components to attach for rendering, gameplay, or tooling.
- Async: heavy scatter work happens on the async compute pool; the main schedule stays responsive.
- Determinism: same seed + same plan + same textures = identical placements (useful for networking or reproducible builds).
- Extensibility: hook into events (
ScatterFinished, etc.) to trigger spawning meshes, sprites, or custom logic.
Examples
See the example crate for curated demos you can run locally.
Quick Start
Add the crates to your Bevy application:
# Cargo.toml
[]
= "0.17"
= "0.2"
= "0.2"
Create a scatter plan in assets/simple.scatter:
(
layers: [
(
id: "dots",
kinds: [
(
id: "dots",
spec: (
nodes: {
"probability": Constant(
params: ConstantParams(value: 1.0),
),
},
semantics: {
"probability": Probability,
},
),
),
],
sampling: JitterGrid(
jitter: 1.0,
cell_size: 1.0,
),
selection_strategy: WeightedRandom,
),
],
)
Use the plugin and trigger a single scatter run once the asset is ready:
use *;
use *;
;
/// Loads the scatter plan asset on startup.
/// Triggers a scatter request once the plan asset is loaded.
/// Observes the `EntityEvent` when a scatter run has finished.
Run the application with cargo run. Once the scatter job completes you will see a summary in the log and can continue with your own placement logic.
Compatibility
bevy_map_scatter |
map_scatter |
bevy |
|---|---|---|
0.2 |
0.2 |
0.17 |