I'm working in MonoGame (C#) and making a game which uses 2D billboards to render characters in a 3D world. Everything is currently working well using basic textures applied to billboarded quads. However, I am now working to try and get Spine wired into this flow as we are going to use it for the characters and animations.
However, I am currently running into an issue trying to get Spine rendering properly into my 3D world. I believe the major issues is that the SkeletonRenderer class always sets the Z value of its vertices to 0 in the following code snippet from the Draw function:
// submit to batch
MeshItem item = batcher.NextItem(verticesCount, indicesCount);
item.texture = texture;
for (int ii = 0, nn = indicesCount; ii < nn; ii++) {
item.triangles[ii] = indices[ii];
}
VertexPositionColorTextureColor[] itemVertices = item.vertices;
for (int ii = 0, v = 0, nn = verticesCount << 1; v < nn; ii++, v += 2) {
itemVertices[ii].Color = color;
itemVertices[ii].Color2 = darkColor;
itemVertices[ii].Position.X = vertices[v];
itemVertices[ii].Position.Y = vertices[v + 1];
itemVertices[ii].Position.Z = 0;
itemVertices[ii].TextureCoordinate.X = uvs[v];
itemVertices[ii].TextureCoordinate.Y = uvs[v + 1];
if (VertexEffect != null) VertexEffect.Transform(ref itemVertices[ii]);
}
I see three solutions to the problem but all have some issues:
1) Use the "World" matrix in the SpineEffect shader to achieve my 3D placement. While this works and is pretty easy to implement, it will be pretty slow because of the fact that I need to set this parameter for each character in the game level, which means I can no longer set the World / View / Proj once and then batch render everything.
2) Render all Spine characters to a render texture, and then use proper UV calculations to essentially cut that up into the textures used by the billboarded quads. This should be more performant than option 1, but the render texture may end up being fairly large if we have a level with a large number of characters, especially if we have multiple characters of drastically different shapes and sizes.
3) Since I'm building from source, just edit the SkeletonRenderer class to have a new z position variable. Then in the above code snippet when calculating the Position values, assign that z value to the verts instead of 0. My main concern here is mucking about in code I don't have a great understanding of and potentially causing issues down the line.
If anyone has had any success doing something similar, or if someone much more familiar with the Spine runtimes could weigh in, it would be very helpful. Thanks!