Starslinger Kings Dev Log

Starslinger Kings DevLog 01 - Custom Robo building = LOTS of art assets

When you're dealing with mechs made up of customisable parts (head, core, legs, arms, shoulder mounted secondary weapon) the way you deal with building and referencing your spritesheets becomes pretty damn important. This article is about coming up against that problem and finding a solution I think is pretty elegant.

First, a problem definition. 


The problem we're dealing with is a tug-of-war between work flow efficiency and how much we tax the load times in-game. The two main considerations I looked at in defining the problem were these:

Consideration 1: Work flow 

Every time a new part is made, it needs to be cut into individual frames, converted from .bmp to .png, given the correct name, packed into a sprite sheet by an automatic texture packer, loaded during gameplay and then have animations pulled out by the code for reference.

That's a hell of a process just to get a spritesheet packed and streamlining it isn't very easy. So if we're going to save time and energy anywhere, it needs to be in the code. The way I had it working previously was that the spritesheet gets loaded, and a uniquely named object gets assigned the frames corresponding to the animation it represents. So for instance, Animation object runRight might have been frames 1-4 (libGDX actually has classes to make referencing frames easy, but I'm trying to keep this general). Then I would reload the spritesheet, flip it, and make runLeft.

Now, when you have 5 pairs of legs, 5 cores, 5 heads, and say 5-10 animations for each one, you can see the complexity of naming each animation individually becoming completely unmanageable, right? It's essentially a data entry nightmare, and woud represent a huge bottleneck in workflow.

Consideration 2: Processing

I made a quick visual representation of the kind of complexity we're dealing with here, and noticed something: the way I've planned to make the animations, they each have the same set. Stand, run, hurt etc. so that they'll all play in sync. Interesting, maybe the solution was simple all along. I thought, if each part, core 1, core 2, ..., core n, are all their own spritesheets, then I can write a general method for extracting stand, run etc and just loop it through all the parts, right?

Well, right, technically, BUT for every new spritesheet loaded, the processor takes a hit. It might not be a huge one, but again we have this problem with how the project scales: if there's 5 part types (head, core, legs) each with 5 individual parts to choose from (core 1-5, legs 1-5) then there's 25 different spritesheets to load. That sounds manage-BUT YOU FORGOT WE DO THIS 4 TIMES OVER FOR EACH COLOUR OH GOD (although I may actually look into gradient mapping to achieve this programmatically). Point being, that's stupid and if I ever wanted to add more, which let's face it I'm the king of scope creep and undoubtedly will, then it just grows exponentially out of control too.


And there was. It occurred to me when I was typing out the above solution in an infographic to send to my brother/dev partner Matt to explain "assets are hard." I figured this method would throw "stand", "run" etc. into an array of animations to use. Hang on...

This next part takes a little specific knowledge. When the TexturePacker packs the textures (say that 12 times over) it gives the frames of each animation a common label and index, and this label is used to reference them in libGDX when unpacking the spritesheet. And it's passed in as a string. And you can build strings from other variables. Which brings us to...


Arrays of arrays of arrays of arrays!

I realised if I just group the 5 cores into a single spread sheet, then I can just run a loop for(i = 1 to 5), and use i to reference each core type. StandAnimation = "core" + i + "stand", that type of thing. Put each array of core i animations in a larger array, and send it off to the player! Great!

Now we're down to 5 spritesheets to load per player MAX. And that should be bearable on the processor. Player assets officially handled.

Have a better way to go about it? I'd love to hear it! Hit me up in the comments below. I'll happily post the code if anyone wants to see it, just ask away.

Joomla BJ Metis template by