/ Tips

Rotating a Bone Along Its Normal - Unity Tip

Occasionally in Blender, a bone needs to be rotated around its local y-axis for a mesh to deform correctly when the bone moves "inwards", or rotates around an axis perpendicular to its normal. This most commonly becomes a necessity when skinning fingers for a humanoid mesh, but it can happen elsewhere too. Take the ailerons of this plane model:

Screen-Shot-2018-05-13-at-3.25.28-AM

To compensate for the diahedral of the plane's wings, the bone is rolled by three degrees so that the normal of the bone matches the angle of the wing, and the aileron folds upwards and downwards correctly.

Screen-Shot-2018-05-13-at-3.33.28-AM

Without the three degrees of roll on the bone, the ailerons fold unevenly (relative to the wing), as if the wing were completely flat.

Screen-Shot-2018-05-13-at-3.34.42-AM

It's easy to rotate perpendicular to the bone's normal in Blender, but how do you do that pragmatically in Unity without resorting to playing animations? If you simply modify the bone's rotation directly, the roll will not be taken into account.

To do this, you can use the "Rotate Around" method like so:

aileronBone.transform.RotateAround(aileronBone.transform.position, aileronBone.transform.right, aileronRotAmount);

Transform.RotateAround takes three arguments; a (Vector3) point in space, a (Vector3) axis that crosses through that point, and an arbitrary amount of degrees to rotate.

The roll amount for a bone in Blender becomes the transform.up vector of the bone when imported into Unity. Thus, transform.right is perpendicular to the normal, and we can use it to rotate along the normal.

Remember that Transform.RotateAround is cumulative, so if you want to set the rotation directly each time you call Transform.RotateAround, you'll want to store and reset the bone's local euler angles before each Transform.RotateAround.