Feature generation changed significantly between 1.17 and 1.18. In 1.17, the chunk generator would start at (0,0,0) in the chunk, find the biome in that block, and generate that biome's features over the entire chunk.
The Bug
In 1.18, within a chunk, the game attempts to place the features of every single biome in the dimension. After positioning those features and evaluating their decorators, the game then only places those features which happen to be in a biome which includes them. This means that the game will sometimes waste computing time attempting to place features in an area which could never include those features (because no relevant biomes are in that area.)
Reproducing the bug
A datapack called "lag test pack.zip" has been included along with this bug report. This pack contains an extremely slow feature, in a biome which is referenced in the dimension but can never generate in the world. To reproduce the issue, load the datapack into a world and notice the extremely long load time.
Solution
The game should instead enumerate the biomes in a 3x3 chunk area around the chunk, and only attempt to place features that are included in at least one of these biomes. This provides a substantial improvement to performance without impacting gameplay at all.
@unknown has written some code (released under CC0) which can be used as a drop-in replacement for the current feature placement/biome check code, and implements our proposed solution. This code has been posted in the comments of this bug report. Mojang is free to use this code for any purpose without limit.
We have also run some performance tests on this code, using vanilla generation, as well as an intensive worldgen datapack and the dedicated lag pack. This test was run on a Late 2013 iMac with an Intel Core i7 CPU, and the test consisted of creating a new world and measuring the time it took to generate the spawn chunks.
Vanilla Control: 32.01s
Terralith Control: 51.48s
Lag Control: 132.65s
Vanilla+Fix: 25.87s (19% faster)
Terralith+Fix: 39.01s (24% faster)
Lag+Fix: 23.96s (82% faster)
Attachments
Comments 6
I also noticed this problem a while ago when researching MC 1.13 code. All features attempt to generate in all chunks, the most funny being Nether Fortress trying to generate in the Overworld. Trying to find the screenshot I had of the code running, but that might take a while.
Hi- here's the code that I found to solve the performance issue without causing feature placement regressions at biome borders, in ChunkGenerator#
applyBiomeDecoration:
The other change that would be needed is to change the iterator's next() to be next().get(). It would be possible to flatten the suppliers, but I figured that there was no harm in keeping it like this. This would replacing getting all the configured features via the biome source.
The reasoning behind this change is that features can't expand beyond a 3x3 of chunks centered on the current chunk, so it would be possible to optimize by making it so features that would never have a chance of placing anyway would not be considered for spawning.
This code is CC0 and can be used freely.