Nanite Streaming and Static Mesh Total Memory

Hello,

We seem to be encountering a disparity between Nanite and our static mesh memory.

We have a level with complete art that is more than 90% nanited. Some of our meshes are pretty large in terms of poly count, but we expect that nanite and nanite streaming will handle this pretty gracefully, so we aren’t too worried about runtime performance.

Unfortunately it looks like there’s an explosion in static mesh memory, which we would expect if we weren’t using nanite. When running Stat Memory we noticed that StaticMesh Total Memory is at about 8456MB, but running Stat NaniteStreaming shows that Total Pool Size Limit is only 2048MB (the default) and Visible Streaming Data Size hovers at around 50MB, which is well under the oversubscription limit for the streaming pool.

Without having investigated the internals of Nanite too much, we’d expect that Nanite streaming (which seems to be working properly) would handle mesh data by fetching from disk when needed, but in our tests in the editor, a -game instance and a Test build we still notice that StaticMesh Total Memory is unusually high and on-par with almost every mesh in the level being loaded into memory at all times.

We noticed that reducing the Keep Triangles Percentage and Fallback Triangle Percentage for meshes across the board does help, but drastically reduces the quality of the resulting meshes, which kind of negates the benefit of nice, high-quality high-poly meshes with good performance.

We would expect that all mesh data lives on disk at runtime until it’s ready to stream in, and only the conservative visible set gets streamed from disk at runtime for any given view, but somehow all mesh data lives in memory when we load the level, on top of the Nanite streaming data. Is there some CPU data that we’re maybe unnecessarily saving off? Are there options in the static mesh editor that aid in this case or is there maybe cvars we can use to unload unnecessary mesh memory?

Hello,

Thank you for reaching out.

I’ve been assigned this issue, and we will be looking into your questions about Nanite Static Mesh memory usage for you.

Hello! Just bumping this so it doesn’t get lost, as we’re ramping up on trying to optimize our game assets.

We did pull up Render Resource Viewer in the editor and noticed that most of the mesh memory is coming from loaded meshes buffers.

Index buffer, tangent buffer, texture coords, index buffer depth-only, and vertex buffer for a single nanite mesh in our levels had a combined 100mb.

This seems like something expected in the editor, but running standalone Test and Development builds doesn’t really drop the StaticMesh Total Memory by much.

Hello,

Nanite meshes will keep the fallback mesh loaded at all times.

You can try reducing the memory impact from fallbacks by reducing the “Fallback Triangle Percentage” only. However, this can affect use-cases that need the fallback.

This ticket discusses the Nanite Fallback in more detail, including it’s uses at runtime:

[Content removed]

Reducing the Keep Triangles Percentage reduces the fallback indirectly by reducing the Nanite mesh used to generate the fallback.

Here are some other tickets discussing Nanite memory management:

[Content removed]

[Content removed]

[Content removed]

[Content removed]

[Content removed]

Please let us know if this helps.

That’s some good info Stephen, thank you! We’ll see about some of the suggestions in these posts and maybe reduce fallback triangle percentage across the board, since our meshes are tending towards very high poly counts in general.