This week started with reworking the room building pipeline so that it didn't try to rebuild all the rooms every time. The existing script was fine to get things going, but it can take several seconds to build one room so it obviously wasn't going to scale very far.

A test roomA test room

The main headache was that the blit masks are shared across all rooms in a world (there will be maybe four or five "worlds" in the game), so I had to save intermediate files for each inividual room and combine them together in a world building stage. It can still take several seconds per room to do this, but it now only runs for rooms that have changed.

While working on the pipeline changes I experimented with different compression schemes for the room data. zopfli is a favourite of mine but this time I ran into semmingly random crashes while unpacking. After sending the developer of the decompression code on a wild goose chase (sorry, Kier) I eventually traced the problem to a race with the vertical blank interrupt! It was using the A4 register assuming it was pointing at the C data area, but the inflate code was also using A4, and chaos ensued when the two bumped into each other. This was an easy fix, adding "__saveds" to the interrupt handler.

The new room data now includes lists of isometric blocks sorted by their screen x and y coordinates. These are used to optimise the edge strip updates for scrolling rooms, as mentioned in the previous devlog, and I wanted to pre-bake them as they can take 5-10s to create and sort at runtime on a 68000. That's too slow for room transitions.

Initially these lists were compressing down to a few Kb for large rooms, so I was thinking perhaps I could only include them for a subset of rooms. However, on a hunch, I tried delta encoding and they compressed MUCH better - 4.5Kb down to under 200 bytes - and now every room gets a list!

The kicker is, after all the time spent debugging the zopfli decompression, the zx0 compressor performed better with the delta-encoded data and I ended up using that instead.

Having prebaked sorted block lists available also allowed optimising the initial render of a room. Instead of checking thousands of blocks it will now typically only look at a few hundred. With this, and removing several sort operations, long pauses between rooms will be no more. Nice.

Next, I think I will look at isometric sprite sorting and get some objects moving around in the world.

Related Links