As I’ve mentioned recently, I’ve been playing with Spine and Sprite Lamp. It’s time to talk a bit about how that’s going and what it means.
Spine files in Sprite Lamp
The main thing I’ve been working on lately is loading up Spine files in Sprite Lamp, so you can view them, animated and dynamically lit, in Sprite Lamp’s preview window. And, it’s working! It looks something like this:
As you can sort of see from the screenshot, the interface is not terribly complex – you load up a .json file and you have your character. You’ll also need to (draw and) load up lighting profiles in atlas form (if the files are named properly Sprite Lamp will automatically grab them), and then off you go. You can select any animation in the Spine file and also select different skins. You can also control the speed and direction of the animation playing.
The walk is a bit slower than I’d like, perhaps, but here’s an illuminated Spineboy, with a static light to make it easier to see what’s happening:
There’s a certain amount of dodginess regarding the bending of the knees, though for artwork that was made without dynamic lighting in mind, I think he came out pretty well. The fact that this is truly dynamically lit, rather than just faked, is most evident on the parts that are rotating the most, particularly the right hand.
The intricacies of rotating normals
It might be helpful, particularly for programmers, to have a bit of a grip on the maths behind this kind of thing. If that’s not your bag, you might want to skip this section.
It’s tempting to think that all you need to render a normal-mapped Spine character is the ability to render a normal mapped sprite combined with the ability to render a conventional Spine character. Unfortunately, the rendering side is slightly more complex than that (NB: I’m just talking about the shader maths here – these complications are not the artist’s problem).
Naturally, rendering a Spine character involves moving and rotating various images about. This is nothing special – rotating a textured quad is something computers have been able to do happily for decades, after all. You paint your character’s leg image or whatever, then you rotate it, and you’re all good. However, when normal maps become involved, things get slightly more complex. If a normal map has a pixel that encodes a vector that faces to the right, and you rotate the whole image 90 degrees clockwise, that pixel should now be facing down. But, its colour hasn’t changed – it still encodes ‘faces to the right’. If you rotate it another 90 degrees, so it should be facing to the left, it still appears to be ‘facing to the right’. This problem gets worse the more the character rotates. Some Spine enthusiasts reading might remember ages ago when Sprite Lamp was in its Kickstarter phase, we had a few shots at Spineboy walking around with dynamic lighting. If I recall correctly, this problem was present in those demos. It was very subtle, because no part of Spine Boy rotates a huge amount during his walk cycle, but it was there. Fortunately, the solution is not terribly complex – you simply have to tell the shader how much each body part has rotated from its default position, and rotate the normal by that amount in the pixel shader Done!
But, you might justifiably be wondering: what of soft skinning? After all, the fine folks at Esoteric Software have been hard at work following their recent Kickstarter adding soft skinning and free form deformation (FFD) to Spine. It’s not obvious what it means to refer to ‘rotation’ when the rotation of a point is going to vary throughout a mesh. And, indeed, this does get a bit more complicated. For Sprite Lamp, I’ve decided to go with a fragment-shader solution to this problem. It involves using the derivative functions in GLSL to compare the the world position and UV coordinate of a fragment with its neighbouring fragments, which enables you to calculate a thing called a TBN matrix (tangent, bitangent, normal). When this release comes along, I’ll talk a bit more about how this is done in the shader. The takeaway is that in the next release, Sprite Lamp should smoothly handle all the different types of animation Spine can throw at it – textured quads, but also soft skinning and FFD. As a demonstration/stress test, Halley has cooked up a slithering snake animation. She wanted me to make it clear that this is not her best work and she’s not very experienced with Spine animation. As far as a clear demonstration of variable rotation on a soft-skinned mesh, though, this does nicely:
You can see here that with the light source on the left, the coils of the snake are picking up the lighting correctly as they wave. It’s not obvious for all animations when the normals aren’t being computed correctly, but in the case of this snake it’s something of a stress test.
Spine and Sprite Lamp in your game engine
So, so far the work has been on getting Spine animations displaying in Sprite Lamp. You might be wondering when you can actually put this in your game.
Unfortunately, the answer to that depends on a bunch of factors. I’m only one programmer, and the crossover between Spine and Sprite Lamp is only one of the many parts of Sprite Lamp. Once Sprite Lamp is out (like, out out, not in alpha like it is now) I’ll be able to give a much more thorough look into engine integration. My policy with Spine will be similar to my policy with the rest of Sprite Lamp’s engine integration: I’ll do as many as I reasonably can myself. Since there are a lot of engines in the world, and I can only cover a few of them, I’ll also do my best to document everything you need to know as a programmer to get things working yourself, be it in an existing game engine that I haven’t been able to cover, or in your own hand-coded system.
That all being said, somewhat predictably, my priorities towards the most widely-used engines will remain, meaning Unity will be first on the list. I’ll be posting more of that as I know it.