Search Unity

  1. Megacity Metro Demo now available. Download now.
    Dismiss Notice
  2. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

[Release][Free] Unity Sprites And Bones - 2D skeleton animation

Discussion in 'Assets and Asset Store' started by TheRealBanbury, Dec 29, 2013.

  1. horeaper

    horeaper

    Joined:
    Oct 30, 2013
    Posts:
    46
    This is really interesting, I'll give it a try after my current project (which uses Spine) finished.
     
  2. reiniat

    reiniat

    Joined:
    Apr 3, 2014
    Posts:
    6
    Ok flipping the normals works with planes:

    Component [] meshFilters;
    void start(){
    meshFilters = GetComponentsInChildren<MeshFilter>();
    }
    void Flip(){
    transform.Rotate (0, 180, 0);
    foreach (MeshFilter filter in meshFilters) {
    //GetComponent(typeof (MeshFilter)) as MeshFilter;
    if (filter != null)
    {
    Mesh mesh = filter.mesh;

    Vector3[] normals = mesh.normals;
    for (int i=0;i<normals.Length;i++)
    normals = -normals;
    mesh.normals = normals;

    for (int m=0;m<mesh.subMeshCount;m++)
    {
    int[] triangles = mesh.GetTriangles(m);
    for (int i=0;i<triangles.Length;i+=3)
    {
    int temp = triangles[i + 0];
    triangles[i + 0] = triangles[i + 1];
    triangles[i + 1] = temp;
    }
    mesh.SetTriangles(triangles, m);
    }}
    }
    }


    Problem is, its harder to work with an object that is rotated 180° in Y, and the above solution doesnt work with sprites as i couldnt find a way to reference the normals.
    So im working in a solution for flipping, basically im flipping the sprites with:

    Vector3 theScale = transform.localScale;
    theScale.x *= -1;
    transform.localScale = theScale;

    And then, im changing the position of the IK Helpers:

    Vector3 thePos = transform.localPosition;
    thePos.x *= -1;
    transform.localPosition = thePos;

    And it works with everything except the animated parts, because they are obviously using the helpers to animate... So my particular solution is to make 2 animations one for flipped and one for not flipped, which is quite easy as i only need to switch the Helpers positions like above, only within the animation.

    And after that i ran into another problem .
    Having an Animator attached to the Skeleton immediately causes jittering even if no animation is being actually displayed....
    I tried Interpolation, removing gravity, and nothing worked. Im not using a camera so its not due to that. And the controller script that moves the player works well with anything else including the Skeleton without animator...
    I looked into the Valar's animation test and i noticed it does have jitter when jumping, but i couldnt see if it had when moving in the platforms, maybe it does and the camera is replicating it in the environment....
    So my question is, any idea of how to remove jittering?

    Oh and btw... When you search for skeletal animation in google, this thread is the first result, so its strange that youre not receiving enough attention. And the Assets Store will never accept free open source projects... Its a store after all.
     
    Last edited: Apr 28, 2014
  3. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    The jittering comes from the IK controller. If you don't have any animation, it's best to turn the IK off altogether. This can be animated. I would prefer to bake the animation for playback, but I haven't found a way to do it.

    Unity users are somewhat peculiar in this way. Nothing exists unless it's on the Asset Store :). And there are free and open source projects on the Store. They just force them to be relicensed under their own custom license. I find this obnoxious.
     
  4. oskarszulc

    oskarszulc

    Joined:
    Dec 6, 2013
    Posts:
    9
    Hello, I've been struggling to get the "create mesh" option to work. I've seen tutorials and your responses here to similar question, and however it seemed resolved for the one who reported it, i can't make it work in my case.

    The most basic scenario: I have a sprite with Advanced properties set to Read/Write, I'm using a "Create mesh" option on it, the mesh is created, but when i preview it in inspector it consists only of one property, which is uv, in contrary to meshes provided in tutorials, which have uv, colors, skin properties.

    I've been trying with different properties of the sprite, but the outcome is always the same - mesh with uv property and Mesh Renderer attached instead of Skinned Mesh Renderer. Do you have any clues? I'll appreciate them.
     
  5. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    You'll have to give me access to your project. Otherwise I can't help you.
     
  6. oskarszulc

    oskarszulc

    Joined:
    Dec 6, 2013
    Posts:
    9
    I'm able to recreate this issue in every project, so I created a sample one. In the sample scene there is a sprite that i'm using in "CreateMesh" option. The "New UnityEngine.Mesh.asset" is outcome of that feature.
     

    Attached Files:

  7. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    I finally found the time to look at your project. The problem is, that a mesh on its own isn't very useful. You need a game object with a mesh filter and a mesh renderer component. Assign the mesh to the mesh filter and the image to the mesh renderer material.

    There's a tutorial for this here:
    http://unity3d.com/learn/tutorials/modules/beginner/graphics/mesh-renderers-and-filters
     
  8. oskarszulc

    oskarszulc

    Joined:
    Dec 6, 2013
    Posts:
    9
    Thanks for your reply!
    Yeah, that's right. But when i have the mesh assigned to filter paired with renderer how do i use it in Skin2d? it still expects me to show him the pure mesh (but with required properties for setting up a texture), not mesh inside a gameobject. Or am i missing something there?

    I'm talking about this error after feeding Skin2D with generated mesh:
    "SkinnedMeshRenderer requires a mesh with skinning or blendshape information."

    how does the mesh + texture in gameobject apply to this?
     
    Last edited: May 12, 2014
  9. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    Skin2D has its own mesh filter. Just assign the mesh to it and follow the steps in Tutorial 4.
     
  10. oskarszulc

    oskarszulc

    Joined:
    Dec 6, 2013
    Posts:
    9
    yup, and here we come again to the very issue i was trying to explain the whole time: assigning the generated mesh to the skin2d's mesh filter causes the "SkinnedMeshRenderer requires a mesh with skinning or blendshape information." error to appear and assigning material or skeleton doesn't have any impact.
     
  11. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    I mention this in the tutorial. Just ignore the error messages and continue the skinning process. Once you've created a skeleton and generated the weights, the errors should disappear.
     
  12. oskarszulc

    oskarszulc

    Joined:
    Dec 6, 2013
    Posts:
    9
    Ok, i was somehow convinced that this was an error that shouldn't be ignored. Thanks a lot, it works now!
     
  13. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    That's good to hear.
    I know, that the error messages are confusing. It's the price I had to pay for having skinned meshes at all.
     
  14. Arder-Blackard

    Arder-Blackard

    Joined:
    May 17, 2014
    Posts:
    2
    Hello! First of all, thank you very much for such tremendous work!
    I've got just a small question. I just started to work with S&B and after trying to build a simple skeleton, I've noticed that the values in some bones Transform component and their Length properties are changed from time to time by themselves. It happens only when moving the mouse pointer over the scene editor. This doesn't seem to be the expected behaviour. Are there any ways to deal with this problem?
    Thank you in advance.
     
  15. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    It certainly shouldn't do this. Usually the cause is a faulty IK setup. But as per usual I can't say anything definitive without a sample scene, where the problem occurs. Could you provide one?
     
  16. Arder-Blackard

    Arder-Blackard

    Joined:
    May 17, 2014
    Posts:
    2
    I found the very easy way to reproduce this behaviour (no sample needed, no IK, even a single bone is enough). Imagine, we would like to setup bone parameters not via mouse drag but using Inspector properties:
    1. Select any bone
    2. Input desired value in the field Length (I used 35)
    3. Input desired value in the field Rotation (I used 90)
    4. Keep the bone selected and move mouse over the Scene Editor.
    Here it is - the values start to change constantly

    I've debugged the scripts a bit and the root of problem seems to be in the next calculations that happen during BoneEditor.OnSceneGUI() calls:


    void OnSceneGUI() {
    ...
    if (bone.editMode) {
    Event current = Event.current;
    if (bone.enabled !current.control) {
    EditorGUI.BeginChangeCheck();
    Vector3 v = Handles.FreeMoveHandle(bone.Head, Quaternion.identity, 0.1f, Vector3.zero, Handles.RectangleCap);
    Undo.RecordObject(bone, "Change bone");
    bone.length = Vector2.Distance(v, bone.transform.position);
    bone.transform.up = (v - bone.transform.position).normalized;
    ...​

    Here v is calculated using bone.length (through bone.Head and Handles.FreeMoveHandle, and later bone.length is calculated back from the value of v. For some reason the described sequence of steps make this update loop unstable in such way that both values keep changing each other over and over.

    Hope it may help you to reproduce the issue.
     
  17. Joe Wee

    Joe Wee

    Joined:
    May 28, 2014
    Posts:
    1
    qestion about the script (why the character's animator must off to run the flip function)

    Hei~ something to ask~ why when i put the script on the character ~the character's animator is disabled , i can flip the character while walking but why the animator doesnt work?
     
  18. findujanvier

    findujanvier

    Joined:
    May 9, 2014
    Posts:
    15
    Hmm, I found out this project has been rejected for months. Anyway thanks for awesome tool.
     
  19. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    I'm not sure what your problem is. Could you provide a sample project?

    The Unity team doesn't like open source. That's why they rejected it.
     
  20. 3CI

    3CI

    Joined:
    Feb 19, 2014
    Posts:
    20
    First of all two thumbs up to you guys, you are all gifted by an amazing talent and please do inform me if you are in KL Malaysia beers and fries are on me, but still hoping I can afford realbanbury's wishlist :D

    I do have a noob question and would like to ask for an apology about this, I am trying to create my very first project and its a virtual pet type and wanted to check if someone here was able to create a scenario were in they can change the sprite image on a specifric part of the bone like for example I wanted to change the bracelet on the characs right hand hence i need to change the sprite that is attached into the hand bone (named Hand.R)

    hoping to hear from expert guys here and thank you so much in advance
     
  21. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    That's quite easy and the main advantage of using skeleton based animation.
    Every gameobject has a Transform property. And a Transform has a parent property. In your case the parent of a sprite would be a bone. If you set the parent property to null, you remove the sprite from the bone. Next you have to create a gameobject with your new sprite. Set the parent of this new object to the bone. Copy local position, rotation and scale from the old sprite to the new sprite. Now you can delete the old sprite.
    Alternately you can change the sprite in the SpriteRenderer component.
    Personally I'd prefer the first solution, because it allows the use of prefabs.

    http://docs.unity3d.com/ScriptReference/Transform-parent.html
    http://docs.unity3d.com/ScriptReference/SpriteRenderer-sprite.html

    I hope this helps.
     
    theANMATOR2b likes this.
  22. 3CI

    3CI

    Joined:
    Feb 19, 2014
    Posts:
    20
    hi realbanburry, the explanation is exquisite however and i would like to ask for an apology, i am not that good in programming, would it be ok for you to check my code here:

    using UnityEngine;
    using System.Collections;
    using System.Collections.Generic;

    public class test : MonoBehaviour {

    public Sprite sprite;

    // Use this for initialization
    void Start () {

    GameObject go = new GameObject("Test");
    SpriteRenderer renderer = go.AddComponent<SpriteRenderer>();
    renderer.sprite = sprite;

    go.transform.parent = this.transform;

    }

    // Update is called once per frame
    void Update () {

    }

    }

    then I attached this script to the bone
     
    Last edited: Jun 18, 2014
  23. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    Well, it's a good start. But honestly, you should learn the basics of programming Unity, before writing a game.
    Unity has a lot of good tutorials and sample projects.

    https://unity3d.com/learn/tutorials/modules
    http://unity3d.com/learn/tutorials/projects

    That's how I learned Unity. It's not that difficult. You just have to take your time with it.
     
  24. 3CI

    3CI

    Joined:
    Feb 19, 2014
    Posts:
    20
    This is highly noted TheRealBanBury, I hope you guys wont get annoyed if I keep on asking questions, more power to you and hey Im pretty serious with the fries and beer here in KL and in Gods time I do hope I can give you one of your wish list more power sir
     
  25. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    I will always try to answer questions, as long as they are about a specific problem.
    Good luck with your game.
     
  26. king_

    king_

    Joined:
    Mar 21, 2014
    Posts:
    5
    a small question...
    how can i apply physics component to the game objects(rigidbody2D,Collider)?
    i tried adding these physics component to sprites, and also bones...and when i play the game the character just falls down going through other collider...!
    and if i remove every physics component from the bones/sprites the character still falls down as a rigidbody
     
  27. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    As it says at the top of this thread, if you don't provide a sample project, then I can't help you.
     
  28. king_

    king_

    Joined:
    Mar 21, 2014
    Posts:
    5
    ok my bad...everything is ok right now...
    but how to flip the character along x-axis(turning right to left), if i change the skeleton's transform.localscale.x into -1 the whole skeleton goes mad(dances:))
    ==============================================
    thank you for this most helpful project of yours
     
  29. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    Mirroring doesn't work. But rotation does, as long as you don't use lights. If you need lights, you need to flip the normals. See somewhere above in this thread.
     
  30. Echolaitoc

    Echolaitoc

    Joined:
    May 26, 2013
    Posts:
    5
    Hi Everyone,
    first of all: Thank you TheRealBanbury for this amazing unity package.
    I've been fiddling around and will use this for my upcoming project.
    I have some problems with sorting my game objects on the z-axis when sorting the sprites of a single skeleton with order in layers of the sprite renderer.
    While trying to come up with a solution I saw the bones have a zOrder property that doesn't seem to be used anywhere. Is that something that will be used in the future?
     
  31. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    Currently I have no plans for this. I can't even remember why I put it there, to be honest :confused:. The way to do this, is to animate the z-axis of the parts. If you're using a single sprite with mesh deformation, then I'm afraid that's not possible. You would need to cut the sprite apart (and the skeleton). There can only be one deformable sprite per skeleton. But it's perfectly possible to use multiple skeletons for a character.

    And thanks for using Sprites And Bones.
     
  32. Echolaitoc

    Echolaitoc

    Joined:
    May 26, 2013
    Posts:
    5
    Thanks for the quick reply :)
     
  33. bangquangvn

    bangquangvn

    Joined:
    Aug 19, 2013
    Posts:
    5
    Hi, can anyone tell me how to make the mesh of Sintel character in Blender ?
     
  34. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
  35. playemgames

    playemgames

    Joined:
    Apr 30, 2009
    Posts:
    438
    Hey Banbury after a long time away working on other stuff with my game, I'm back! I finished up the Unity PSD Importer to a much more usable state, I'll start a new thread with it most likely tomorrow. I'm going to try to work on Unity Sprites and Bones now and go through the list of enhancements to see what I can add. The first thing I am going to try to tackle is FFD, or at least an easier way to set up skinning and deforming.

    I was playing around with the multiple skins that Denvil had set up and there are some quirks to it, I want to see if I can make it more of a control point based way to deform than just skinning through the generated mesh. This is pretty much the killer feature I need streamlined, as I have hundreds of layers I'm working with and setting up and skinning meshes for them is an absolute pain at the moment. I really like the way Stickman does it, you put control points along the areas you want to deform and behind the scenes it creates the mesh from those points.

    Kinda thinking out loud here as well but I think the Sprites.DataUtility might be able to spit out the current mesh to make the edit:

    http://docs.unity3d.com/ScriptReference/Sprites.DataUtility.GetSpriteIndices.html

    http://docs.unity3d.com/ScriptReference/Sprites.DataUtility.GetSpriteMesh.html

    I'll give it a whirl this week when I get the chance.
     
  36. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    I noticed the surge of activity on the PSD importer. :)
    It would be nice, if you could work out a better solution for the mesh deforming. The math for FFD was too much for me.
    The Sprites.DataUtility is an interesting find. But this must be a new class, or I'm blinder than I thought. I really could have used those functions when creating the sprite meshes.
    I've noticed that some of the worst shortcomings of Unity have been addressed recently by the developers. Maybe someone has read my blog :D.
    Currently I'm rather busy with another project, but if you get the ball rolling, I might join the fun sooner or later.
     
  37. playemgames

    playemgames

    Joined:
    Apr 30, 2009
    Posts:
    438
    Yeah I think those are new functions, I had not seen them before either until I started sniffing around for ways to do deformation and mesh creation better. I'll get the ball rolling this week! Looking forward to coding with you again man!
     
  38. KinxilTheHarpist

    KinxilTheHarpist

    Joined:
    Jun 30, 2014
    Posts:
    11
    Great job of this Asset !

    I got some problems with the control of my character. The way I created it is similar to the Orc but for some reason I've a big problem with the Hip.

    With your Orc prefab, if you move for example the left arm helper, only this left arm can move. But when I move the left arm of my character, the whole body move randomly around the others helpers (which are fixed). Main issue is likely that the hip is moving while it should not.

    I created my hip as the parent of any others bones.

    The method I used :
    Created the new skeleton
    Created the bones one after anothers
    Added 4 helpers and linked them to each hand/feets
    Added each needed sprite and made them child of each associated bone.

    The model move well, the only problem is the hip moving instead of staying still.

    Any idea ?
     
  39. playemgames

    playemgames

    Joined:
    Apr 30, 2009
    Posts:
    438
    KinxilTheHarpist, include a project for the file as TheRealBanbury has said in the first post otherwise we cannot help you.
     
  40. KinxilTheHarpist

    KinxilTheHarpist

    Joined:
    Jun 30, 2014
    Posts:
    11
  41. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    I haven't had a look at your project, but you probably forgot to limit the length of the IK chain. By default IK influences the whole bone chain up to the root. You can limit this by changing the chain length property on the IK component. The Orc's arms use a value of 2, because there are two bones.
     
  42. nasos_333

    nasos_333

    Joined:
    Feb 13, 2013
    Posts:
    13,286
    Very interesting tool, i will try it

    I have been using Smoothmoves as main 2D platform, and looking for what else could be used, Puppet2D is another one i have bought but have not used yet.

    Does the tool create texture atlases ?
     
  43. playemgames

    playemgames

    Joined:
    Apr 30, 2009
    Posts:
    438
  44. nasos_333

    nasos_333

    Joined:
    Feb 13, 2013
    Posts:
    13,286
  45. bangquangvn

    bangquangvn

    Joined:
    Aug 19, 2013
    Posts:
    5
  46. playemgames

    playemgames

    Joined:
    Apr 30, 2009
    Posts:
    438
    Actually I am revamping the way skinned meshes are done, and have multiple skinned meshes on a skeleton working pretty good. I'll be posting my code to my fork soon, maybe this will help ease the creation of skinned meshes for everyone.
     
  47. playemgames

    playemgames

    Joined:
    Apr 30, 2009
    Posts:
    438
    K I'm almost there with adding some new features including making skins easier with no error messages (actually I have this done!) and creating a mesh from a polygon collider. However the problem I have with creating a mesh from the polygon collider is getting the UV's properly to map to the texture. I'm not quite sure of the math on how to get it, here's some screenshots of what I am doing:

    upload_2014-7-2_20-7-52.png

    I can take a sprite and then add a PolygonCollider2D and edit it as I like, then I have a script that runs to make the mesh. When I add the mesh to the Skin2D script and recalculate the weights and weight paint them to the skeleton it looks like this:

    upload_2014-7-2_20-22-7.png

    Here is the code I am trying to do to create the mesh, I must have something wrong with grabbing the uvs this way.

    Code (CSharp):
    1. using UnityEngine;
    2. using System.Collections;
    3. using System.Collections.Generic;
    4. using System.Linq;
    5.  
    6. public class PolygonMesh {
    7.  
    8.     public PolygonCollider2D polygonCollider;
    9.  
    10.     public void CreatePolygonMesh()
    11.     {
    12.         if (polygonCollider != null)
    13.         {
    14.             Vector2[] vertices2D = polygonCollider.points;
    15.  
    16.             // Use the triangulator to get indices for creating triangles
    17.             int[] indices = Triangulator.Triangulate(vertices2D);
    18.  
    19.             // Create the Vector3 vertices
    20.             Vector3[] vertices = new Vector3[vertices2D.Length];
    21.             for (int i=0; i<vertices.Length; i++) {
    22.                 vertices[i] = new Vector3(vertices2D[i].x, vertices2D[i].y, 0);
    23.             }
    24.  
    25.             // Create the mesh
    26.             Mesh mesh = new Mesh();
    27.             mesh.vertices = vertices;
    28.             mesh.triangles = indices;
    29.             Vector2[] uvs = new Vector2[vertices.Length];
    30.             Bounds bounds = polygonCollider.bounds;
    31.             int n = 0;
    32.             while (n < uvs.Length) {
    33.                 uvs[n] = new Vector2(vertices[n].x / bounds.size.x, vertices[n].z / bounds.size.x);
    34.                 n++;
    35.             }
    36.             mesh.uv = uvs;
    37.             mesh.RecalculateNormals();
    38.             mesh.RecalculateBounds();
    39.             ScriptableObjectUtility.CreateAsset(mesh);
    40.         }
    41.     }
    42. }
    I'm not sure how to grab the uvs using the polygon collider, if you have any ideas Banbury let me know.

    In the meantime I got multiple skins to work with ease now. You can just click on the sprite you want to make into a skin, and go to Window>Sprites>Skin2D and it will automagically create the mesh and the skin for you with no errors. You still have to weight paint it for it to show up (I was trying to get it to automatically paint it to the parent bone, but I am not sure how that flows right now so it doesn't seem to work).

    upload_2014-7-2_20-35-0.png

    Soon as I finish this I may write a new class for control points specifically for deformation, this way it can look a little cleaner than having a bunch of bones moving around.
     
  48. TheRealBanbury

    TheRealBanbury

    Joined:
    Dec 15, 2013
    Posts:
    248
    Calculating UV coordinates isn't one of my favourite acitivities, either.
    UV coordinates have to be between 0 and 1 with the coordiante center in the upper left corner. The coordinate center of your mesh is probably somewhere in the middle. So you have to translate your UVs by that amount.
    Also I don't understand, why you divide the z coordinate of the vertex by the width of the bounding box (line 33). Shouldn't this be the y axis divided by the height?
    Otherwise great job with the mesh creation. Users seem to have a lot of problems with that. So everything, that makes it easier and less error prone is very welcome.
     
  49. TheValar

    TheValar

    Joined:
    Nov 12, 2012
    Posts:
    760
    So you need to created a UV mapped mesh from a Unity sprite using the vertices of a polygoncollider2D right? Assuming I understand the problem correctly I think I can help you out with that. I made an algorithm that basically does that for this little project http://forum.unity3d.com/threads/dynamic-2d-destruction.235005/

    It may need to be modified a bit because it was doing a bunch of extra stuff with the Triangle.net library but it should do what you want once the fat gets trimmed off. It will even handle if the sprite is rotated or scaled.
     
  50. playemgames

    playemgames

    Joined:
    Apr 30, 2009
    Posts:
    438
    Thanks Banbury I had just used a snippet from the documentation on how to grab the uvs I didn't catch that about the z! Hopefully this will help a lot more people with making skinned meshes. I'll work on the deform control point stuff today to see if that will make things a bit easier as well.