Unreal Engine·Blueprint·Programming

UE5 Level Instances: Loading Levels in Blueprint and C++

Create procedural levels in UE5 with dynamic level instances and ULevelStreamingDynamic. Blueprint and C++ examples for runtime level generation.

Level Instances are how Unreal handles streaming of levels during gameplay. For level instances to work, they have to be set in the Persistent Level and tie them to streaming volumes or other loading mechanisms, but these instances are static.

Dynamic Level Instances let us spawn a level at any transform, including several instances of the same level at once.

Let’s see how to do this.

Load Level Instance in Blueprint

In Blueprint, call Load Level Instance. One variant takes an asset reference and the other takes a level name. The name variant is useful with naming conventions, when we want to build a name from pieces like LVL_ … Factory … Left … 05.

Both take a Location and Rotation in world space for placing the level.

After calling this function you will get a variable of type ULevelStreamingDynamic which represents a singular instance of that level in some coordinates in space.

You should store that variable as it will allow you to work with the level.

For instance, if we wanted the level to be loaded, but not visible, we could manipulate some of it’s properties to do so:

We can also register for when the level finishes loading. This uses Unreal’s streaming system to avoid hitching the game thread, so loading can take some time. C++ exposes extra parameters if we want to load synchronously instead.

After Load Level Instance, bind to the event for when the level is shown. Once that fires, we can query the actors in the level and work with them.

ULevelStreamingDynamic: Load Level Instances in C++

Of course, all of this can also be done using C++, here are the same functions:

There are some extra functions here. The other variants all call the one that takes FLoadLevelInstanceParams.

This struct contains the same parameters we need, and allows you to modify things before they get loaded. ( Remember that this uses the Streaming System of Unreal, so it will be effective on the next Tick of the World )

The streaming functions set bInitiallyLoaded to true by default. We only need to change it if we do not want the level loaded initially.

By the way, if you want an example of Dynamic Level Instance loading in action, the Pocket Worlds plugin uses them to spawn the levels it uses, here is a snippet of that:

Use Dynamic Level Instances as Procedural Level Pieces

For a procedural generator, we can treat each level as a Room or Piece and load it where needed.

We need metadata describing how the pieces connect. This can live in a data asset or in the Asset Manager tags of the level assets.

Once we have that, we can start constructing our procedural levels by combining such pieces one after the other.

Once the initial layout works, you can add art to each piece using the same Unreal tools as for any other level.

I believe Returnal builds its procedural world with Level Instances too, though I haven’t confirmed that.

This covers loading the pieces. A full generator also needs connection rules, collision and overlap checks, and decisions about seeding and determinism. That is where most of the procedural layout work remains. Streaming is asynchronous, so pieces take time to appear; either design around the wait or use synchronous loads in C++.

Recap

  • Regular Level Instances are static and live in the Persistent Level. Dynamic Level Instances let you spawn any level, at any transform, as many times as you want, at runtime.
  • Load Level Instance in Blueprint and the FLoadLevelInstanceParams path in C++ both hand you back a ULevelStreamingDynamic. Store it, because that’s your handle to the instance.
  • Loading goes through Unreal’s streaming system, so it takes effect on the next world tick rather than instantly. Bind to the shown event before you start querying actors in the level.
  • For a generator, treat each level as a room or piece, tag it with connection metadata, and stitch pieces together one after another.

Keep reading

Understanding Entities and Fragments in Unreal Engine's Mass Framework

Understanding Entities and Fragments in Unreal Engine's Mass Framework

The entity handle in Mass is 8 bytes. Mass also stores the information needed to track the entity, plus its fragment data.
Dashes and Knockbacks with Root Motion Sources

Dashes and Knockbacks with Root Motion Sources

No root motion in the clip. The task builds the motion from plain numbers and hands it to the movement component, the animation is just cosmetic.
PlayMontageAndWait in GAS: Montage Replication

PlayMontageAndWait in GAS: Montage Replication

Montage_Play works on your screen and nowhere else. The ASC is the one that tells everybody else.