Guide
Chunk Streaming
ChunkDungeonStreamer builds an endless dungeon in chunks. It plans the chunks around the player, builds the nearby ones, and removes or reuses the ones the player leaves behind. Use it for open-ended worlds; use DungeonManager when you want a fixed, authored structure.
On this page
Set up a streamed world#
-
Open and click Create Infinite Dungeon. This adds a
ChunkDungeonStreamerto the scene. -
Assign the player. Set Player to the player's transform, or set Player Prefab so the streamer spawns the player in the entry room of the start chunk. Use one of the two.
-
Assign the Corridor Prefab. It must be a 1 × 1 corridor module from the Room Designer with exactly one
DoorSocketon each of the four sides. There is no built-in fallback corridor. -
Set the entry rooms. Either add prefabs to Entry Prefabs, or turn Use Dedicated Entry off to use pool-only mode, where the first room of each chunk comes from the room pool.
-
Add rooms to Room Pool Prefabs. Each room must have a
DoorSocketon every cardinal side. Different room sizes are allowed. -
Set Cell Size (m) to the tile size of the rooms. It must match the Room Designer grid.
-
Set Chunk Size (Cells) to at least the measured minimum. Once rooms are assigned, the inspector shows the minimum and the recommended value. See Chunk size.
Setup mode: player, rooms, and corridor, with the chunk size below. -
Click Generate in the inspector. The world builds around the player. Use Recenter to move the streamed area to the player's current chunk, Rebuild to build it again, and Clear World to remove it.
Chunk size#
The chunk size must be big enough for the largest room to fit with its corridors:
ChunkSizeMinimumcells- Three times the largest room side, plus twice the safety margin. Below this value the streamer refuses to start.
ChunkSizeRecommendedcells- The minimum plus 2. The extra cells keep corridors away from the chunk border.
Below the minimum, initialization fails with an error. Between the minimum and the recommended size, it logs a warning and continues, and corridors may feel cramped at the chunk border.
Both values are available from code as ChunkDungeonStreamer.ChunkSizeMinimum(width, height, safetyMarginCells) and ChunkSizeRecommended(...).
Settings#
Rooms#
useDedicatedEntrybool default on- Uses the entry prefabs as the first room of every chunk. Off = pool-only mode.
entryPrefabslist- Entry rooms. Each chunk picks one with its chunk seed.
corridorPrefabGameObject required- The 1 × 1 corridor module that joins rooms.
roomPrefabslist- Additional rooms for the pool. Duplicate references are rejected.
minRooms,maxRoomsint default 4 and 4- Rooms per chunk, Entry included.
minRoomsmust be at least 1 and at mostmaxRooms.
World and seed#
useRandomSeedbool default on- Draws a new world seed on every generation. Turn it off to use
worldSeed. worldSeedint default 42- The seed for a repeatable world. The same seed gives the same layout.
cellsPerSideint default 24- Chunk size in cells. It must be at least the minimum in Chunk size.
cellSizefloat default 3- Size of one cell in meters. It must match the tile size of your room prefabs.
safetyMarginCellsint default 1- Cells kept free at the chunk edges so corridors stay clear of the border.
openSubsetRetrySlotsint default 2, range 0 to 2- Extra attempts with derived seeds when a chunk's seams do not fit.
openSubsetExitCountint default 2, range 1 to 4- Minimum number of open seams on the start chunk.
portalSocketTypeslist of DoorSocketType- Socket types for the seams between chunks. The list order decides the type, so do not sort it. An empty list means untyped seams.
Streaming and performance#
plannedRadiusint default 2- Chunks within this radius around the player are planned and cached, but not built. The planned area is (2r + 1)² chunks.
loadedRadiusint default 1- Chunks within this radius are built and active. Must not exceed
plannedRadius. diamondLoadedNeighborhoodbool default off- Builds only the chunks that connect by a side, in a diamond shape. This skips the diagonal corners, which never connect.
materializePerFrameint default 1- Build work per frame (Inspector: Builds per Frame). One work item is a chunk container, one room or corridor instantiate, or one step of corridor planning.
materializeFrameBudgetMsfloat default 0- Optional time budget per frame (Inspector: Frame Budget (ms)). 0 turns it off. When it is set, the builds per frame still run first.
prewarmRoomCopies,prewarmCorridorCopiesint default 4 and 24- Inactive copies created in advance for each room prefab and for the corridor tiles. The first build then reuses them.
Locks and key#
lockChancefloat 0–1 default 0- Fraction of seams that start locked. 0 turns random locks off.
spawnProtectionRadiusint default 1- Chunks around the start that never get locks. The 3 × 3 start area is always protected.
keyPrefabGameObject- The key the player picks up to open locks. It needs a
ChunkKeyPickupcomponent and an enabled trigger collider on its root. Locked worlds need one.
Door locks follow the world seed. Room locks come from the Requires Key setting on each room prefab, which adds a ChunkRoomRequiresKey component.
Debug and logging#
showChunkGizmosbool default on- Master switch for the Scene view overlays. The four overlay toggles below (Show Areas, Show Footprints, Show Corridors, Show Portal Seams) are each on by default.
showLockedEdgeLabelsbool default off- Labels locked seams with red text.
logDetailsbool default on- Informational logs. Errors and warnings are always logged.
Performance#
- Radii: the loaded area is what costs time and memory. Keep
loadedRadiusas small as the gameplay allows. The planned radius is cheaper, because it is computed but not built. - Pacing:
materializePerFramelimits how many items are built per frame. Increase it for faster loading, or set amaterializeFrameBudgetMsto cap the time spent per frame. - Pooling: chunks you leave are deactivated and reused when the player comes back, so revisiting an area costs little.
- Prewarming: raise
prewarmRoomCopiesandprewarmCorridorCopiesif the first builds of a chunk stutter. Each copy costs memory. - Chunk size: a smaller chunk puts rooms and corridors closer together. Below the minimum, planning fails; use the recommended size when you can.
Events and API#
ChunkDungeonStreamer exposes Initialize(), UpdateCenterFromPlayer(), Dispose(), and Rebuild(), plus the WorldChanged event. The event passes the transform of the world root. Full signatures are in the API Reference.
using DungeonGen;
using UnityEngine;
public class StreamedWorldLogger : MonoBehaviour
{
[SerializeField] private ChunkDungeonStreamer streamer;
private void OnEnable() => streamer.WorldChanged += OnWorldChanged;
private void OnDisable() => streamer.WorldChanged -= OnWorldChanged;
private void OnWorldChanged(Transform worldRoot)
{
Debug.Log($"World root: {worldRoot.name}, loaded chunks: {streamer.LoadedCount}");
}
}
Common mistakes#
- The world does not start. Check the Console. The usual causes are a missing corridor socket, a chunk size below the minimum, or a cell size that does not match the rooms.
- Rooms do not line up. The cell size must equal the room grid. Check it on every room kit.
- Locks appear unexpectedly. Set
lockChanceto 0 while you test, or assign a key prefab first.
See also Troubleshooting: chunk streaming.