You weren’t using that 100MB, were you?

So I was grumbling to myself today about how tricky it is to be dealing with such a large world in MMORPG Tycoon 2;  since the world terrain is generated procedurally as you move around in the world, it means that data such as the height of the terrain simply isn’t stored anywhere for locations which aren’t currently near the camera.

This can be a problem in many situations.  One example is when you have AI developers putting monsters into a quest zone.  The AI developers know approximately where the quest zone is, but if the camera isn’t actually near the quest zone, they have no way of knowing what the slope of the ground is, or precisely how high the ground might be.  Often, I’ve found that these quest areas end up having all their monsters placed down at sea level, with the terrain being twenty or thirty meters above there, so the monsters can never actually be reached by the players.

As I was thinking about the problem, I worked out the maths and calculated that for the size world I’m talking about (20km x 20km), it would take nearly 100 megabytes of memory to store the terrain height, if I kept the whole world in memory at once.  My old-school programmer brain immediately told me that this was complete madness, and threw away the possibility of doing this, and I went back to designing complicated queued fetch-and-correct systems for placing objects when not all the required data was actually present in memory, and it wasn’t until almost ten minutes later that something in the back of my mind clicked, and realised that no, 100 megabytes isn’t very much any more.  So I did it.

As a result, I’ve increased MMORPG Tycoon 2’s memory footprint from 256 megabytes of RAM to 384 megabytes of RAM to store this terrain data.  (To a programmer, those are nice round numbers;  256 is 2^8, and 384 is 2^8 + 2^7.  Aren’t those nice and round?)

Anyhow.  I set the game up to procedurally generate the whole world’s terrain when it starts.  And on my (rather fast) computer, it takes between 70 and 90 seconds to do so.  Which is completely unacceptable to me, so I changed the system to generate-and-cache-upon-demand, which means that the first time you visit an area, it runs at about the same speed as it did before, but is substantially faster each time you revisit an area you’ve been to before.  This also solves the “no terrain data for areas which are far away from the camera” problem, solves lots and lots of different of bugs, and actually makes the terrain generation code much simpler overall.  I’m quite pleased with how it’s turned out.  And I could quite probably create a background thread to generate terrain data for areas you haven’t visited yet, while you’re working on other things.

But it does now use an extra 128 megabytes of RAM.  This thing certainly won’t ever be running on the iPhone!