Skip to content

Blockout Lab

Type: Custom Asset Editor (Pattern B) · Asset class: UBlockoutLayout · Category: Labs

A complete in-engine level blockout editor. Draw layouts on a top-down 2D canvas; the 3D preview extrudes geometry in real time; one click exports the whole layout as named, collision-ready actors in your level. 26 element types cover walls, terrain, water, navigation, cover, zones, gameplay markers, and annotations. Multi-story support with staircase connectors. Procedural scatter zones drive weighted mesh distributions through three pattern algorithms. Auto-Connect Paths runs Prim’s MST across selected points. Roll Layout reseeds every procedural element with one button. JSON preset library persists scatter recipes across projects. The asset is a real .uasset with version-tagged serialization that survives the full production lifecycle.

Screenshot 01 — Hero shot — Editor open with a populated multi-room layout — 2D Canvas on the left showing colored elements, 3D Preview on the right showing the extruded blockout in a level.


  • Pre-production layout passes — design level flow entirely in 2D before committing to final geometry, with player-capsule and door-frame overlays for scale validation
  • Floorplan-driven design — import a reference floorplan PNG, threshold + auto-trace walls (V2), iterate in 3D from a real-world basis
  • Multi-story building blockouts — stack floors with correct stair connectors, per-floor visibility, and accurate per-story height controls
  • Combat encounter prototyping — block in cover positions, sightlines, elevation changes, and gameplay zones (spawn / objective / trigger / hazard) before any art pass
  • Procedural scatter setup — define ScatterZones, attach weighted UBlockoutAssetSet mesh distributions, roll the layout to generate variation iterations
  • Level art handoff — deliver clean, named, collision-ready blockout actors to environment artists with the source .uasset preserved for design reference
  • Don’t expect optimized final geometry — exported meshes are blockout-grade (placeholder grid materials, basic triangulation). They’re meant to be replaced by hand-modeled assets at the end of blockout.
  • Don’t use it for organic terrain sculpting — Blockout Lab handles flat zones, slopes, and cliffs. For sculpted terrain, use Landscape.
  • Don’t use it for World Partition cell layout — it places actors in the active level. WP sub-levels need the relevant cell loaded before exporting.
  • Concave room polygons may extrude with reflex-angle artifacts — V1 uses a simple inward-extrude algorithm. Workaround: split concave rooms into convex pieces; ear-clipping triangulation is a V2 addition.

From the Content Browser:

  1. Right-click in the Content Browser
  2. Pick EQLabs → Blockout Lab → Blockout Layout
  3. Name it; double-click to open

From the EQLabs Hub:

  1. Open Window → EQLabs Hub
  2. Search Blockout or browse to Design → Level Design
  3. Click the Blockout Lab tile — pick Create New or open from the recent layouts list

There’s a second asset type — Blockout Asset Set — created the same way (EQLabs → Blockout Lab → Blockout Asset Set). It’s a UDataAsset holding a weighted list of static meshes used by ScatterZone / VegetationZone elements.


ControlWhat it does
Drawing ModePolygon / Polyline / WallPoint / TwoPoint / Point / Select / Eraser
Element TypePicks the active element (Wall / Room / River / etc.)
Grid Snap25 / 50 / 100 / 200 / 500 cm
Roll LayoutReseeds every Cliff + ScatterZone with new procedural seeds (single undo)
Auto-Connect PathsBuilds Prim’s MST across selected POIMarker / SpawnPoint / Obstacle elements (one Path per edge)
Generate Scatter Children(Re)runs scatter algorithm on selected ScatterZone(s)
Export to LevelOne-click level export
Undo / RedoStandard Ctrl+Z / Ctrl+Y

Categorized list of all 26 element types. Click an entry to set it as the active element type. Categories are color-coded for quick visual scan.

Orthographic top-down drawing surface. Active grid snap is visible. All placed elements are color-coded by type. Live overlays:

  • Player capsule outline at any clicked location for scale reference
  • Door frame height guide on selected wall segments
  • World-scale ruler showing the current view size in centimeters

Drag to pan, scroll to zoom. Single-click selects, drag-select for box selection. Whole-row selection in the Outliner mirrors canvas selection (and vice versa).

Live perspective viewport of the same layout, extruded. Updates instantly as you draw. Camera orbit / zoom / pan supported. Per-floor visibility toggles isolate single stories during review.

Per-element property panel for the currently-selected element:

SectionFields
CommonLabel, Color, Height, Width, Elevation, FloorIndex, Pivot
Type-specificSlope’s LowEdgeStart/End indices, Stairs’ step count, Cliff’s Closed toggle + style (Jagged / Stepped / Smooth), Bridge’s deck/abutment params, Sightline’s cone toggle, etc.
ProceduralProceduralSeed, DensityFalloff, bPinnedForProcgen (gates whether scatter rerolls touch this element)
Scatter (ScatterZone only)ScatterPattern (Scatter / Mandala / Cluster), ScatterCount, ZoneAssetSet (weighted mesh distribution)
Material (Gameplay zones only)ZoneOpacity, ZoneWidth, ZoneMultiplier, ZoneSpeed, ZoneDirection — drives the animated MI_Zones material

Outliner / Floor Manager (right — bottom)

Section titled “Outliner / Floor Manager (right — bottom)”

Hierarchical view of every element in the layout, grouped by floor. Click a row to select the corresponding canvas + 3D-preview element. Floor Manager controls add / remove floors, set per-floor base height + ceiling height, and toggle floor visibility.

FieldDefault
Output Folder/Game/Blockout/
Actor Name PrefixBlockout_
Mesh LODNone (blockout)
Collision PresetBlockAll
Clear Previous Exportfalse

CategoryElementsDrawing mode
StructureWall, Room, Opening, StairsPolyline / Polygon / WallPoint / TwoPoint
TerrainGroundZone, Slope, CliffPolygon / Polygon / Polyline
WaterWaterBody, RiverPolygon / Polyline
NavigationPath, BridgePolyline / TwoPoint
CoverObstacle, TreeLinePoint / Polyline
ZoneVegetationZone, Boundary, ScatterZonePolygon
AnnotationPOIMarker, Sightline, RouteFlow, CoverLinePoint / Polyline
GameplaySpawnPoint, SpawnZone, ObjectiveZone, TriggerZone, EncounterZone, HazardZonePoint / Polygon (zones)

Screenshot 02 — Element palette + 26 types — Palette panel showing all 26 element types organized into the 8 categories (Structure / Terrain / Water / Navigation / Cover / Zone / Annotation / Gameplay), color-coded for fast visual scan.

  • Wall (Polyline) — extruded box per segment, opening cutouts split walls cleanly
  • Room (Polygon) — polygon defines the outer edge; walls extrude inward by Width (default 15 cm). Centroid heuristic picks inward direction
  • Opening (WallPoint) — cutout-only; references parent Wall / Room via ParentWallId. Doesn’t export as a separate actor
  • Stairs (TwoPoint) — N stepped boxes ascending; height from Elem.Height or derived from target floor
  • Slope (Polygon) — tilted ramp using SlopeLowEdgeStart/EndIdx (defaults 0/1 on creation)
  • Cliff (Polyline) — bCliffClosed toggle: closed = plateau (loop walls + interior cap), open = linear strip with CliffStyle (Jagged / Stepped / Smooth) using procedural seed for variation
  • River / Path (Polyline) — Catmull-Rom smoothed mitered ribbon; River uses water material at water Z, Path uses MI_BaseColor at BaseZ + 2cm
  • Bridge (TwoPoint) — parametric: deck (top slab) + 2 abutments + 2 railings, structure-grid material
  • TreeLine (Polyline) — distributed cylinder-trunk + cone-crown trees along the polyline (two material slots: trunk brown / crown green); honors IsProceduralPointAllowed (skips trees in HazardZones)
  • Boundary (Polyline) — BoundaryType enum: MinimalistWall (default, thin solid) or WoodenFence (posts + 2 horizontal rails)
  • Annotation elements — exported as USplineComponent actors pivoted at Points[0] so the gizmo lands on the corner

Each FBlockoutFloor stores:

  • Base Height — world Z offset
  • Ceiling Height — clearance above base
  • Visibility — toggle isolates one floor in the 2D canvas + 3D preview

Stairs elements span between floors — TargetFloor resolves the upper floor’s base height for automatic step generation. Per-floor visibility lets you draw on one story at a time without clutter from others.


A polygon zone that procedurally distributes children using one of three pattern algorithms:

PatternAlgorithmLook
ScatterBridson Poisson-discWell-spaced, no clumping — ideal for trees, debris
MandalaConcentric rings around centroidsqrt(N×0.8) rings, perimeter-proportional slot count — formal, symmetrical
ClusterPerlin noise rejectionClumpy, biome-like — natural variation

All patterns honor:

  • IsProceduralPointAllowed — skips HazardZones, respects closed Boundary inclusion
  • GetProceduralDensityAtDensityFalloff curve weights distribution from centroid outward
  • Pinned anchors — children with bPinnedForProcgen=true survive rerolls; only algorithmic fills change

Screenshot 03 — Procgen pipeline, all passes — Canvas showing a ScatterZone with all three pattern algorithms applied to different zones — Scatter (Poisson-disc), Mandala (concentric rings), Cluster (Perlin-rejection) — visible side by side with weighted-mesh results in the 3D preview.

UBlockoutAssetSet — weighted mesh distributions

Section titled “UBlockoutAssetSet — weighted mesh distributions”

A UDataAsset holding TArray<FBlockoutAssetEntry>. Each entry:

FieldWhat it does
MeshTSoftObjectPtr<UStaticMesh>
WeightAuto-normalized; relative likelihood of selection
MinScale / MaxScalePer-entry random scale range
bRandomYawPer-instance yaw randomization toggle

PickRandomEntry() runs an inverse-CDF weighted pick. Attach an asset set to a ScatterZone (ZoneAssetSet) and exporting builds a HISM (Hierarchical Instanced Static Mesh) actor with AddInstance per child position, using weighted picks + per-entry scale / yaw.

Resolution priority for scatter zones:

  1. Elem.ZoneAssetSet (per-zone weighted distribution) — wins if set
  2. Layout->VegetationMeshes (V6 fallback) — uniform random + global [0.8, 1.2] scale
  3. Empty → exports as flat POIMarkers only

Single toolbar button. Reseeds every Cliff + ScatterZone with new non-zero ProceduralSeed. Auto-regenerates each ScatterZone’s algorithmic children. One FScopedTransaction covers the whole roll — Ctrl+Z reverts the entire iteration. Cliffs use the seed for jagged / stepped variation; ScatterZones for child distribution and HISM-instance variation.

Toolbar action that runs Prim’s MST across the currently-selected point-like elements (POIMarker / SpawnPoint / Obstacle). Emits one 2-point Path per edge. New paths inherit the first-selected node’s FloorIndex. Single transaction.

Screenshot 04 — MI_Zones animated material — 3D Preview showing several Gameplay zones (SpawnZone / ObjectiveZone / TriggerZone / EncounterZone / HazardZone) with the animated MI_Zones material running — different colors, opacities, and pattern speeds per zone.

Save / load scatter recipes as JSON files at [Project]/Saved/EQLabs/BlockoutScatterPresets/<Name>.json. Schema V1 captures pattern, count, density falloff curve, and the asset set reference (as FSoftObjectPath). Skips polygon points and procedural seed (recipes, not snapshots).

UI lives in the ScatterZone properties section: Save As input + Apply / Delete buttons + dropdown of saved presets. Filenames are sanitized to alphanumeric + dash / underscore / space.


UBlockoutLayout ctor wires four default materials, picked per-element by category:

MaterialUsed byPer-element params
MI_Blockout_Structure (StructureMaterial)Wall / Room / Opening / Stairs / BridgeFrontColor / RightColor / TopColor / TileX / TileY / TileSpacing
MI_BaseColor (BlockoutMaterial)Path / Obstacle / Cliff / Boundary / non-Gameplay zonesBaseColor (= Elem.Color)
MI_Water (WaterMaterial)River / WaterBody(no per-element params)
MI_Zones (ZonesMaterial)5 Gameplay polygon zones (Spawn / Objective / Trigger / Encounter / Hazard)Color / Opacity / Width / Multiplier / Speed / Direction

The MI_Zones material is animated — Direction is a 0-1 scalar driving panning angle, Speed controls animation rate, Width / Multiplier control pattern density. Each gameplay zone gets its own MID instance so per-zone params don’t bleed.

TreeLine has two extra material slots — TreeTrunkMaterial (brown) + TreeCrownMaterial (green), both MI_BaseColor with hardcoded BaseColor values.


UBlockoutLayout serializes (V13 magic-numbered + version-tagged):

  • ElementsTArray<FBlockoutElement> with all per-element fields (geometry, type-specific params, procedural state, gameplay zone material params)
  • FloorsTArray<FBlockoutFloor> with base + ceiling heights and visibility
  • Reference image — soft pointer to the imported floorplan
  • Materials — soft pointers to the four defaults (overridable per asset)
  • Vegetation Meshes — fallback array for VegetationZone scatter
  • Canvas Settings — zoom / pan / grid snap / layout area size
  • Scatter preset state

The format is forward-compatible append-only: pre-V6 saves still load; new fields default. Pattern proven through 8 incremental version bumps (V6 → V13).


  1. Open / create the layout asset
  2. Pick a Drawing Mode (Polygon for rooms / terrain zones, WallPoint for walls, Polyline for paths / rivers)
  3. Pick an Element Type from the palette
  4. Click on the canvas to place points; close polygons by clicking the first point or pressing Enter
  5. Adjust the placed element’s Height / Width / etc. in the Properties panel

Screenshot 06 — Floorplan import + auto-trace — A PNG floorplan loaded as the canvas backdrop. Threshold slider isolates wall regions; Auto-Trace turns detected edges into Wall elements over the source image — perfect seed for an architectural-reference layout. 6. Repeat — the 3D Preview updates live

  1. Open the Floor Manager panel → Add Floor
  2. Set the new floor’s base height and ceiling height
  3. Use Floor Visibility to focus on one story while drawing
  4. Add Stairs elements between floors — set TargetFloor to the upper floor
  1. Draw a ScatterZone polygon
  2. In Properties, set the ScatterPattern (Scatter / Mandala / Cluster) and ScatterCount
  3. (Optional) Create a UBlockoutAssetSet data asset with weighted meshes; assign it to the ScatterZone’s ZoneAssetSet field
  4. Click Generate Scatter Children in the toolbar — children appear at scattered positions
  5. Click Roll Layout to reseed and reroll variation iterations
  6. Pin specific children (bPinnedForProcgen = true) to lock them through future rolls
  1. Drag-select a group of POIMarker / SpawnPoint / Obstacle elements (3+)
  2. Click Auto-Connect Paths in the toolbar
  3. The minimum spanning tree is built and emitted as Path elements
  4. Edit the resulting paths individually as needed
  1. With a ScatterZone selected, configure pattern + count + density falloff + asset set
  2. In the ScatterZone Properties section, type a preset name in Save As → click Save
  3. The preset is written to [Project]/Saved/EQLabs/BlockoutScatterPresets/<Name>.json
  4. Apply that preset to any other ScatterZone via the dropdown + Apply

Screenshot 05 — Exported actors in level — A real Unreal level with the exported blockout actors placed (rooms, walls, water, scatter HISM), all on-grid, with grid materials visible.

  1. Open the target level
  2. Open the Export Settings panel — set output folder + actor name prefix
  3. Click Export to Level
  4. Each element becomes a properly-named AStaticMeshActor (or AActor for annotations / HISM scatter), placed at the correct world transform with collision + materials applied
  5. (Optional) Toggle Clear Previous Export before re-exporting to dedupe stale AStaticMeshActor actors

FieldDefaultRange / Type
Grid Snap100 cm25 / 50 / 100 / 200 / 500
Default Wall Height300 cmfloat
Default Extrusion Depth30 cmfloat
Floor Base Height0 cmfloat
Floor Ceiling Height320 cmfloat
Image Trace Threshold0.501
Export Name PrefixBlockout_string
Export Output Folder/Game/Blockout/path
Collision PresetBlockAllenum
Clear Previous Exportfalsebool
ScatterCountvariesint
DensityFalloffcurveenum (Constant / Linear / Smoothstep / etc.)
ZoneOpacity (Gameplay)0.501
ZoneWidth (Gameplay)1.005
ZoneMultiplier (Gameplay)1.005
ZoneSpeed (Gameplay)1.0010
ZoneDirection (Gameplay)0.001 (mapped to angle)

Asset persistence: all layout state lives inside the .uasset. Scatter presets live separately at [Project]/Saved/EQLabs/BlockoutScatterPresets/<Name>.json — they’re shared across layouts and projects.


  • Export to Level places AStaticMeshActor per element, named with the configured prefix + element type (e.g., Blockout_Wall_001, Blockout_Room_003)
  • Annotations export as USplineComponent actors instead of static meshes (Sightline / CoverLine / RouteFlow)
  • ScatterZone with AssetSet exports as a Hierarchical Instanced Static Mesh actor — collision QueryAndPhysics, folder Blockout/<Layout>/Scatter/
  • VegetationZone exports as HISM (collision NoCollision) using Layout->VegetationMeshes fallback list
  • Materials applied at export — structure / blockout / water / zones / tree, plus per-element MID overrides
  • Source asset preserved — re-open and iterate any time; export workflow is repeatable

  • Wrong UProject path = silent no-op. When developing the plugin from source, building against the wrong target name finishes in <2s with “Target is up to date.” Real rebuilds are 20s+ per .cpp. (Plugin folder is Plugins/EQLabs/, not Plugins/EqulocityLab/.)
  • Concave Room polygons may extrude with reflex-angle artifacts. V1 uses a simple inward-extrude algorithm. Workaround: split concave rooms into convex pieces. Ear-clipping triangulation is in the V2 backlog.
  • Replace mode in exporter doesn’t dedupe annotations + HISM scatter. It currently extends only AStaticMeshActor. Re-export creates duplicate spline / HISM actors — clean manually until V2.
  • Pin elements before rerolling scatter. bPinnedForProcgen=true survives Roll Layout; algorithmic children are deleted and regenerated. Pin the ones you want to keep.
  • ScatterZone children aren’t typed today. The exporter spawns POIMarkers (or HISM via AssetSet). Spawning Obstacle / SpawnPoint children is V2.
  • Image Auto-Trace is V2. V1 supports importing the reference image as a backdrop; the threshold + edge-detect autotrace pipeline is on the V2 list.
  • MI_Zones direction is a 0-1 scalar, not 0-360°. Internal mapping handles the angle conversion. (V12 briefly used a bool — V13 reverted to scalar for diagonal angles.)
  • World Partition cells must be loaded before exporting. The export targets the active persistent level; sub-level cells need streaming-in first.
  • Quick EdMode is a sketch tool, not a full editor. It supports basic drawing only — no floor management, no procedural scatter, no preset library. Use the full asset editor for production work.

  • World Partition Inspector — verify streaming setup after exporting blockout geometry to a partitioned world
  • Level Analysis Suite — run Actor Inventory + Room Metric Analyzer on the exported blockout
  • Procedural Scattering Suite — feed exported blockout zones as density-map inputs for full-scale procedural foliage
  • Modular Kit Auditor — transition from blockout to modular-kit assembly using the blockout as spatial guide
  • OFPA Nexus — manage one-file-per-actor source-control concerns for exported blockout actors

Report an issue with this tool

Opens our feedback form in a new tab with the tool name pre-filled.