Actually I assume you’re doing this for third person movement, so I’ll tell you how I solve this problem:
First we have a camera that is separate from the player. We have an orbiter script or whatever camera follower you want. Then we have a child of the camera called “CenterCam”–in scripting we will set this to always be at the players position. But because it is a child of the camera it will always have the camera’s rotation.
Then we place a child under CenterCam called CenterChild. For our next part of the script we map input (or whatever direction you want to be relative) to the local position of Center Child. Since center child also has the rotation of the camera and is always locally centered on the target, the resulting position compared to CenterCam is the direction you want to move. Should look something like this:
Now you can take the position of the CenterChild and set that to be the “RotateTowards” target of the player. (Or you can just map that to input acceleration if you want him to strafe instead of turning. But for example purposes this is what I did)
var quat = Quaternion.identity;
if ((lookDir - transform.position) != Vector3.zero)
{
quat = Quaternion.LookRotation(lookDir - transform.position);
}
^Where lookDir is the position of CenterChild. Now we just have to tell the player to take that rotation either all the time, or just when we’re moving. (So he can stand still without rotating towards that position)
Now all that’s left is to Quaternion.Slerp into the correct rotation! Keep in mind that now he’ll always be facing the CenterChild position when moving, so just take that into account by remapping ANY movement into just relative forward movement. (He’s always facing CenterChild, so just always go forward)