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

Blender FBX export -> wrong bone rotation relative to its amature

Discussion in 'Asset Importing & Exporting' started by Smaples, Oct 29, 2013.

  1. Smaples

    Smaples

    Joined:
    Oct 29, 2013
    Posts:
    12
    When I export bones from Blender via the fbx exporter the bones got wrong local rotation relative to their amature within unity. I searched very long for a fix but nothing works. Does anybody has a solution for this, so that the mesh, its amature and its bones get the same orientation in local coordiantion-system?
     
    Last edited: Oct 30, 2013
    harryjc and CloudyVR like this.
  2. halley

    halley

    Joined:
    Aug 26, 2013
    Posts:
    2,364
    There is a fundamental difference between Blender and Unity's coordinate system, which incidentally is the same fundamental difference between Microsoft DirectX and OpenGL. You can't fix this distinction with a simple "rotate ninety degrees" because no combination of rotations will align the two systems.

    http://msdn.microsoft.com/en-us/library/windows/desktop/bb204853(v=vs.85).aspx

    Blender and OpenGL use a "right handed" coordinate system. They follow centuries of mathematics tradition that came from observing the natural world. For example, electrical flow and magnetism are described in textbooks assuming the user will work with the right hand rule.

    Ultimately, Microsoft wanted to differentiate themselves from the competition and set some standards, so they chose to go with a left-handed system for Direct3D (an early part of the DirectX suite). It was an arbitrary decision with deep impact, as you see here. It broke with all the traditions of OpenGL, SGI, and even traditional mathematics in general. However, it had the intended effect: game developers who wanted to sell for Microsoft platforms found it to be enough of a pain to support both left- and right-handed math, that they stopped trying to make games that were cross-platform compatible. If you know latin, you'll understand why I call this a sinister plot on behalf of Microsoft.

    Unity decided to focus on Microsoft's standards first: DirectX and .NET and C# are all Microsoft's gifts designed to sow incompatibility in the marketplace. Over and over, developers have had to write, test and put up with workarounds to offer 90% compatibility with the rest of the right-handed world. Now that iOS and Android are prevalent and profitable right-handed platforms, Unity has worked to overcome much of this by doing core conversions of a number of things when converting from right-handed assets. This hides a lot of the issues but can't erase them all.

    If you mirror any ONE axis (e.g., scale by -1,0,0 or 0,-1,0, or 0,0,-1), you have converted the base coordinates from left-handed to right-handed systems. However, the vertex order of polygons has also been reversed by this, so all the surface normals are flipped. All text that appears on textures has to be flipped around. Also, all Quaternion and 4x4 Matrix math ends up rotating differently. It's a major headache.



    Short answer: you will always see some axis changes when looking at Blender and Unity.
     
  3. Smaples

    Smaples

    Joined:
    Oct 29, 2013
    Posts:
    12
    Many thanks for your investigation and the informations. But I do not agree with all of the points. Basically it is possible to convert from the "left hand system" to the "right hand system". And of couse the FBX export does it with some objects correctly. But "and that is the main Problem" not for all objects (meshes and bones) in the same maner. But let me explain/clarify my problem in the next post with pictures
     
    Last edited: Oct 30, 2013
  4. Smaples

    Smaples

    Joined:
    Oct 29, 2013
    Posts:
    12
    1. I did an export from blender 2.69 to Unity 4.2
    2. I created a cube and a bone as parent.
    3. I saved the scene as untitled.blend in an asset folder of Unity
    • In Picture 1. you see the "local axis" of the cube within blender.
    • In Picture 2. you can see the imported cube in Unty and note that Unity creates a top level parent (empty object) with the name of the Blender file (untitled). And you will also see that the axis are different compared to the Blender Cube of Picture 1.
    • In Picture 3. you can see the cube-mesh within Unity. And you can see that it has diffrent axis to the Blender cube "and more confusing" different to the empty object "untitled" of picture 2. And from my point of view this is the first bug. Both objects should have the same axis.
    • But not enough! Analog to the above explanation compare the Pictures 4., 5., 6. You will find that every Unity Object has a different orientation where the objects in blender have the same local orientation. Only the Armature and the Cube-Mesh are the same in Unity. This is a bug and not a problem of mathematical transformation. Every object should have the same local orientation related to the "global".
    The main problem comes with scirpting when you have to effect bones. E. g. when you want to attach a "lookAt-funktion" to a "head bone".


    $wrongbonerotation.jpg
     
  5. halley

    halley

    Joined:
    Aug 26, 2013
    Posts:
    2,364
    I understand what you're saying. They're both due to the choices Unity has done to patch over the left-handed vs right-handed system, as well as Blender's choice of "Z is up" and Unity's choice of "Z is forward".

    For discussion, label your images (A, B, C) on the top row, (D, E, F) on the bottom row.

    In A to B, the converter makes a container Empty and orients it so Y is up, and then in B to C they oriented the child cube so the cube's top (the character's head) is at the top in Unity's Y-is-up world scheme.

    In D to E, you see the same local coords for the armature as for the cube. This should not be a surprise.

    However, the F picture shows a different decision that Unity has made, and I agree with you wholeheartedly that it was a very strange decision.

    Blender generally considers the bone stick to be along the bone's Z axis by default. Unity generally considers the bone stick to be along the bone's -X axis by default. It's a pain. I agree with you that it blows the whole concept of "Look At" out of the water. (Especially since Blender can do a "track to" constraint on any axis direction, but Unity gives no such options for LookAt().) It's not a bug, it's just another annoying artifact of handedness conversions. They apparently decided it was the easiest way to marry the quaternion math that drives deformations, with the other conversions they're doing to ensure your characters and text don't look backwards.
     
    davidrochin likes this.
  6. Smaples

    Smaples

    Joined:
    Oct 29, 2013
    Posts:
    12
    As I read anywhere in the net Unity uses the FBX-Exporter-Script of the Blender to which the .blend files of the OS are associated. So for sure the different rotation is a bug but not from Unity rather from the Blender-FBX-Exporter. So from my point of view there are two possibilities.

    1. The Blender-FBX-Exporter has to be fixed so it correspond to the Unty universe/world and rotate every object in the same maner.
    2. Unity develops an own Importer based on the blender file (.blend) without detour over the Blender-FBX-Exporter.


    I recommend the second, because Blender is not a commercial Software and its indeed a nice to have of its development. Furthermore Blender is open source other than Unity Pro. So Unity can read the .blend files but not vice versa I guess but please correct me. And we will not worry about the Blender-FBX-Exporter anymore.
     
    Last edited: Oct 30, 2013
  7. halley

    halley

    Joined:
    Aug 26, 2013
    Posts:
    2,364
    Unity should NOT try to read the .blend file directly; the format of a .blend changes with every build of Blender (not just every major version but every compile can introduce new data in the files). Export scripts inside Blender is the way to go here.

    The Blender FBX exporter works for other purposes as-is. I'm pretty sure it's doing the right thing for any right-hand-rule application: export the bones as-is. If you want to make a separate exporter for Unity, go ahead, since it's just an open-source python script. If you think Unity should include it, post your fixed version on the Asset Store and see what people think. All the Mecanim stuff seems to be happy with bones pointing -X axis, so I think it's fighting a losing battle, in my opinion.
     
  8. Smaples

    Smaples

    Joined:
    Oct 29, 2013
    Posts:
    12
    Blender is freeware and I can not expact more as it is. Unity Pro is commercial and I can expect those kind of elementary functionalty from it. And its not necessary to provide an import for every new Blender build but for a stable version. And Unity may also change its data system so this is not an argument.

    Maybe I will create an exporter but its not my focus rather then to create indie-games.

    Anyway I m just at the beginning with Unity and its the evaluation phase. And what blockades will find more when I go on with it. Maybe its not my game-engine or Blender not my 3D creation tool. I will see but thanks for you paricipation.
     
  9. Smaples

    Smaples

    Joined:
    Oct 29, 2013
    Posts:
    12
    Blender is freeware and I can not expact more as it is. Unity Pro is commercial and I can expect those kind of elementary functionalty from it. And its not necessary to provide an import for every new Blender build but for a stable version. And Unity may also change its data system so this is not an argument.

    Maybe I will create an exporter but its not my focus rather then to create indie-games.

    Anyway I m just at the beginning with Unity and its the evaluation phase. And what blockades will find more when I go on with it. Maybe its not my game-engine or Blender not my 3D creation tool. I will see but thanks for you participation.
     
  10. Cygon4

    Cygon4

    Joined:
    Sep 17, 2012
    Posts:
    382
    I think that reading .blend files is quite reasonable:

    A. Blender has an excellent track record of backwards and forwards compatibility. They've gone through major redesigns, yet I can still open an animated model I created in Blender 2.69 RC3 with Blender 2.49b. The small subset of data that Unity is interested in is way below the baseline and if someone would have added a .blend importer to Unity 2.0, it would still be working fine today.

    B. There is an Open Source library that reads .blend files: AssImp. Its license should be fine for inclusion in Unity.

    C. It would be way faster than what Unity does now (launch Blender a dozen times to export each animation clip separately). I have models that take several minutes to import because of this.
     
  11. shaderbytes

    shaderbytes

    Joined:
    Nov 11, 2010
    Posts:
    900
    In blender :

    Rotate your model -90 deg on the x axix , then ctrl A and apply rotation

    now do exactly the same for the armature.

    then when exporting the fbx .. do not set it to unity coord .. rather to blenders y-forward z-up

    import into unity and there should be no rotation problems

    edit:

    make sure you have set blenders rotation to use the pivot point of the model/armature when doing the rotation.. not the median center
     
    Last edited: Oct 31, 2013
  12. Smaples

    Smaples

    Joined:
    Oct 29, 2013
    Posts:
    12
    @Cygon: Tried it but no success until now. But will investigate a little bit more time in the next days with it.
    @shaderbytes: With your tip it looks really better so the object and the armature have the same rotation but the bone itself does not.

    I did some tests with the exporter and what I could figure out is:

    • In Blender 2.69 select the bone
    • Go in to edit mode (TAB)
    • Open the properties (Nkey) and make a roll about 90 deg
    • Leave the edit mode select all objects including the bones
    • Oben the FBX exporter and set the forward axis to "-Y" and up-axis to "X"

    When you do this, the bone and the object have the same rotation except the empty armature object. But the armature is only an empty which I do not really need.

    I will go on with some tests if this works for animations. But what a horror to create a setup like this. And I do not think its appclicable to already created animations.
     
    Last edited: Nov 1, 2013
  13. arielcorrea

    arielcorrea

    Joined:
    Feb 21, 2019
    Posts:
    14
    For those, like me, who stumbled on this thread. Here is a possible solution (or workaround):
     
    SergeyIwanski and Knarhoi like this.
  14. bidjo666

    bidjo666

    Joined:
    Mar 24, 2018
    Posts:
    3
    In FBX export settings select Armatures
    Primary Bone Axis select Z Axis
    Secondary Bone Axis select -X Axis
     
    Recluse, Reahreic and lukeiszed like this.
  15. topitsky

    topitsky

    Joined:
    Jan 12, 2016
    Posts:
    100
    Thanks! This fixed the bone rotation problem
     
  16. GGodis

    GGodis

    Joined:
    Apr 9, 2019
    Posts:
    2
    Really important to note that while this helps to fix the armature bone orientations, it will likely mess up the transformations for the animated (boneless) meshes that might be attached as a child to some specific bone. For example, if you have a mesh of a "cup" that is attached to the character's wrist bone - on export to FBX changing those "Primary Bone" and "Secondary Bone" might mess up cup's transformations! (Tested with the current version of Blender 2.91.0)
     
  17. Siccity

    Siccity

    Joined:
    Dec 7, 2013
    Posts:
    255
    If you're using Blender you're going to be eternally gimped by the FBX format, as it is designed in a way that is mostly incompatible with Blender. It is a miracle that it works at all.

    My solution is to use the new opensource glTF format instead of FBX. glTF enforces a single coordinate system, which means exporters and importers alike don't need to support every concievable configuration; they only need to support one. I've been using this format for a few different projects now, and all models, bones and everything import exactly as they're supposed to.
    Unfortunately Unity is hesitant to provide official support for this format, so you will have to look up importer plugins for unity. I hope that with enough traction, Unity will have to support it officially.