- Изменено
Sprite Switcher vs. Skins?
In our game we have several equipment slots for an RPG.
Mainhand
Offhand
Head
Chest
For mainhand and offhand the sprite switcher works perfect by just swapping out 1 sprite in Unity, but for the chest the scenario is getting very complex.
If someone equips a cloth robe it needs to replace "Slot" shoulder, bicept, forearm, robe, and possibly many others. What's the best way to do this? Sprite switcher would require us to not only stage every single image to swap like:
Cloth Robe
- cloth_robe_chest
- cloth_robe_left_shoulder
- cloth_robe_right_shoulder
etc etc... not impossible but for like 100+ items this will become very cumbersome and I also noticed requires you to manually set the pivot within Unity itself to try to line up.. major nightmare.
Is there some easier method to do this? If we built it into Spine it would span dozens of atlases which is fine if it supported it, but I just want to make sure we choose the best way to do this before going forward.
If you change the skin that seems like it might screw up the sprite switcher since you specify a skin when doing it.
Thanks.
You could import all the relevant non-packed pngs in Unity. Then you could implement building a texture and atlas at runtime. Definitely doable in Unity 5.
With that setup, you wouldn't have the workflow nightmare (exporting a million atlases), and you'd get great performance and memory usage outside of equip mode.
The workflow nightmare I was thinking of was having to define that Cloth robe X consists of sprites 1/2/3/4/5/6 so that when equipped in game it swapped out all those slots in unity with sprite switcher. The nightmare is having to try to set the pivot points of all of them.. or am I misunderstanding?
What do you mean by "sprite switcher" anyway? Is this a thing that's built-in somewhere? Sounds like using it may not be a good idea to use it if you have this problem.
But in general (not specific to Unity) it may be helpful to make sure, when you're designing/drawing your images, that your equip variations share the same size/dimensions and ideal pivot, or group them according to similarly sized groups so you only have to align at most 3 or 5 times, instead of 100 times.
The other thing I meant was that yes, you could "build it into spine". ie. align the attachments in Spine and store attachment data with the json. But not let Spine do the packing.
You could also avoid having to define 100 unique attachments in Spine (and avoid the overhead of storing 100 unused attachments on your SkeletonData object) if bunches of your images were the same size. Then you could just custom-populate your atlas based on the knowledge that certain sets of images and resulting attachments would have the same pixel dimensions and pivot/offset.
"Dozens of atlases" used by one skeleton is actually supported but, for performance reasons, not recommended. So to be clear, you could, but you shouldn't, and you don't have to.
On the sprite switcher (attacher sorry, same idea as the examples thread in this forum) ignore the chest slot but basically something like this:
I noticed to get the chest working as an attachment I have to have all the sprites on their sides facing right and manually pivot them at the base. Perhaps I am over abusing the sprite attachment options a bit but they work well for main and offhand weapons if drawn sideways and manually pivoted in unity.
None of the weapons are the same size nor offhands, so I just have the one Weapon and Offhand attachment in Spine and then call the swap in unity from a unity packed atlas of images. At runtime it seems to add a new attachment for every single sprite, but not sure there's any way around that.
We have maybe 80 chest sprites for equipment, 80 helmets, 30 shields, 600 weapons (might need to discuss this one with designer, just now calculated this number and am a bit in non-agreement, lol).
We wanted to use mesh deformation but yea if the dimensions aren't drawn in exactly the same area for all "leather chests" or "plate chests" then it won't be possible. I see possibly create 4 attachment slots each with their own deformation, but im not sure the deform will carry into unity if we use sprite attacher to swap it out at runtime with a unity sprite.
Maybe we need to pay for consulting lol We are making a very complex ARPG and having to cut corners in places as it is due to the performance of the multiplayer host needing to track hundreds of running anims.
06 Aug 2015, 13:56
I re-read this and I think we're doing close to what you're describing, I just used different terminology.
We have packed atlases in unity and define a [SpineSlot] weaponSlot, [SpineSlot] headSlot which i target with:
Spine.Attachment mainhandAttachment = skeletonRenderer.skeleton.Data.AddUnitySprite(weaponSlot, ItemManager.Instance.equipmentSprites[image], skin, "Custom/SpriteAdditive");
skeletonRenderer.skeleton.SetAttachment(weaponSlot, image);
I guess by using Unity sprites you lose all the mesh benefits and get extra overdraw but if they were all the exact same dimensions and pivot yea that would make things easier... just be an issue to draw all daggers in the same pixel space as giant 2h axes etc.
Aside from that this is the other problem that I'm not sure is a problem or not by using my above code.. every image swap adds a new slot.
http://snag.gy/rxIKG.jpg
Also looks like we lose all FFD if we swap out the image with unity (as seen with the weapon slot), so the only option might be to put all equipment in spine atlases if we need that custom of animations?
We're doing something similar in our game and unfortunately since we pack our textures into our own atlas and strip the whitespace out we had to manually set pivots for each individual image. This involved building a rather large system that read in files that arbitrarily defined "equipment slots" that had sets of spine slots and then specifying on each type of "equipment" what images went on what spine slots and what the pivots were. So I can confirm that what you want to do is indeed possible.
If you're not stripping whitespace then I would do what Pharan suggested and just make sure everything lines up on the same pivot in the images themselves.
As far as mesh deformation goes (and please someone correct me if I'm wrong) I believe that since you're using the sprite attacher you're in the same boat as we are. In my understanding mesh deformation is tied to the image attachments in Spine, which means you can't do a single deformation for a slot and have it affect any attachment you decide to place on that slot. This topic seems to discuss this problem: viewtopic.php?f=11&t=2184&p=10895. If you're not using your own texture atlas you can probably still manually do the mesh deformation for each image, but that is not an option for us unfortunately =/
Hopefully sometime in the near future mesh deformations can be reused for multiple attachments.
EDIT:
As far as your issue with your code adding slots, that definitely seems like a bug. In our implementation we just swap out attachments on the slots that have already been defined in Spine.
Also an important step that I forgot to mention in our implementation is that we dynamically generate a skin and set the attachments for each spine slot that the "equipment slot" needs on that skin, then set the skin to the skeleton. Something like this:
foreach(int i in slotIndecies)
{
// psuedo-code
sprite = GetFromAtlas();
slotName = skeleton.slots[slotIndecies].Data.Name;
newAttachment = (RegionAttachment)skeleton.AttachUnitySprite(slotName, sprite, shader); currentSkin.AddAttachment(slotIndecies, skinPlaceHolderNames, newAttachment);
}
And you would reuse the same skin for each "equipment slot" so that all your equipment combines easily. We just stored a map of these skins so that we can use different skins on the same model for different characters and then we clean them up whenever we don't need them anymore.
Since it looks like you're not using skins that might be the source of some of your troubles. I would look into trying to dynamically create a skin and see if that fixes your slot addition issues.
Is the runtime cost really that expensive to have 500 equippable items in your spine? This would only be for the main hero and only 4 players in game at once. All the monsters would have pre-designed 1 weapon animations and basic design.
Essentially what we would lose going with region attachments is the deform which is quite important on our cloth robes and chest breathing, etc. It seems like you need to either pick the flexibility of swapping out images with sprite switcher in unity in custom packed atlases or use spine slots to swap them out and be able to deform them. We haven't gotten too deep into equipment yet, but I'm not quite sure what happens if you animate a mesh and then swap out the robe for a different one.
Depending on how big your atlas gets you might not be able to fit all of your items onto it and still have it be an appropriate size (we're on mobile so we're limited on space). The runtime cost isn't the problem since that should just be a texture coordinate change since its all on an atlas.
As I was saying in my last post, I'm not the most knowledgable on the mesh deformation process, but I believe that since it is tied to the attachment in Spine you have to do it manually for each item that needs mesh deformation information. If you swap out a robe for a different robe, they both need to have the mesh deformation animated on them inside Spine. Then when you export from Spine that information gets stored in the .atlas file and references locations in the atlas image that was created by Spine. (Once again please someone correct me if I'm wrong on any of this.)
To make a long story short, you can't reuse mesh information regardless of what method you pick, and as far as I can tell if you want it to work at all you need to export everything from Spine since the mesh information references locations in the image atlas generated by Spine. I really do wish Spine had better mesh deformation support because it is such a great tool, I just hope that sometime in the near future some more work gets put into it to make it a bit more flexible for use cases like these.
By my calculations we can fit about 100 items per atlas and spine can span multiple atlases, so I don't think 5-6 atlases would really be an issue? I think the dragon example even uses multiple atlases.
I guess the easy method would be to see if we can just change the attachment image and see how that goes, but that requires positioning and rotating every equippable item within spine itself right?
After that we may have skins for robes since they swap out 6 or so sprites at a time, but that seems like a mess to try to define skins and manage all the equippable item swapping, so the best bet seems to define in code what a "Leather Tunic" is as far as what slots it defines and the image names of each.
Example.. player equips Leather Tunic.
- Chest slot: "leather_tunic_chest"
- Bicept slot left: "leather_tunic_left_bicept"
- Bicept slot right: "leather_tunic_right_bicept"
- shins, "none"
etc etc... so in unity on equipment change in game it does a call to the skeleton and just swaps out images?
If you don't have problems with your atlases, great!
Defining what slots a "Leather Tunic" affects is definitely what we did. Though we extrapolated it slightly further and said "Tunics" have these slots and then a "Leather Tunic" places these sets of images on those slots.
When I was talking about skins earlier you're not actually defining the skin in Spine, you're just dynamically creating one at runtime from the different attachments that you want, otherwise you're going to run into issues if you want to key different frames for your "Tunic" during any of your animations.