jahed.dev

Extracting Sprites from Texture Atlases with GIMP

A common task when contributing data to FrontierNav and working with game dumps is to extract images from sprite sheets and atlases. Games pack multiple images into textures to optimise rendering. It's much faster to load a texture of all weapon icons at once when scrolling through a weapon menu, than to load individual icons as they are scrolled through. Otherwise the scrolling may not be smooth, the icon may not appear immediately, and so on. So to extract these weapon icons into individual images, we need to cut them out of the texture.

A Grid of Sprites

Often, textures can be processed easily. The sprites are equally spread out, say in a 128x128 texture with 32x32 sprites, 4 across, 4 down.

In ImageMagick, it's as simple as:

convert image.png -crop 32x32 +repage +adjoin tile-%d.png

An Atlas of Sprites

When sprites are of different sizes, textures can be automatically optimised to pack as many sprites as possible without following any sort of deterministic grid layout. These textures come with some metadata to indicate the bounding box for each sprite. That metadata isn't always available in texture dumps so identifying sprites can get complicated and often requires some manual work.

Automating the process of finding the boundaries of a sprite is difficult and will require some level of human intervention to adjust thresholds. For example, two separate swords may look like separate icons, but they could in fact be a single sprite in the game's context. It's an interesting problem that I may look in to in the future, but for now, I tend to rely on GIMP. Here's the process.

Extracting Sprites with GIMP

First, make it easier to identify the boundaries of each sprite. Sprites can contain semi-transparent pixels which aren't easy to see and can be easily missed.

Now, let's cut out each sprite from the texture:

Once all sprites have been cut out, the texture layer will be empty and each sprite will have its own layer.

Next to create images for each sprite layer:

And that's the process. There is a more individualistic approach to all of this which is faster if you just want to export some sprites:

GIMP is missing some features which would make both processes a lot less tedious. For example, being able to export layers or selections directly. But overall, it's good enough.

Thanks for reading.