I am trying to set up a character which faces a particular forward direction and its up direction is direction is based on the normal of the mesh it's standing on.
So I do something like;
transform.up = raycastHitInfo.WorldNormal;
transform.forward = LookDirection;
The problem is that I can't seem to set both components simultaneously and get a desired result.
What I'm trying to do is set transform.right as a cross product between up and forward,
transform.right = Vector3.Cross(FloorNormal, ForwardLookDirection);
But the results I'm getting aren't very good for some surfaces which are angled at more than a single axis (see here: http://i.imgur.com/TQpYU.png)
Any ideas for how I can do what I'm trying to?
asked Jun 09 '12 at 02:12 PM
answered Jun 09 '12 at 02:16 PM
The two vectors you're cross-producting aren't necessarily at right angles, which will give you a skewed matrix. Try this:
This guarantees you an orthogonal matrix. But you'll get nasty snaps as you cross polygon boundaries (and the normal changes suddenly), so you may want to store this as a target matrix and seek the actual matrix towards it to smooth those transitions.
answered Jun 09 '12 at 02:58 PM
To elaborate on Jessy's fine reply, as you mentioned, you have to set
LookAt and LookRotation take a 2nd optional parm, as the up:
Another cute trick is you can compute the smallest rotation between two vectors and apply that to your current rotation. "face this way" ignores your current rotation, but "tilt from where I am now to this new facing" respects your current orientation:
answered Jun 09 '12 at 03:04 PM
Have you tried using Quaternion.LookRotation? http://unity3d.com/support/documentation/ScriptReference/Quaternion.LookRotation.html
You pass that method a direction the object will face with it's z-axis and an up-vector which will determine the rotation of the object around that direction. This will give you a Quaternion you can assign to transform.rotation.
So in your case that would look like this: