[C#] Vector3.RotateTowards Parameters Are Confusing

In the game I’m currently making the camera follows the enemy to always have vision on them. I’ve looked around and found the function of Vector3.RotateTowards, and it’s just what I needed. I began to read up on it to figure out what I could about it, so the first place I go is the Unity Scripting API page.

Needless to say, I was instantly overwhelmed. They brought out vocabulary like “maxRadiansDelta”, “Magnitude”, and “Current” which I didn’t understand at all. All I knew about magnitude was that it’s the number of units between two coordinates. Can someone help explain the parameters and process they went through on the page?

Also, when I put this into my game, the camera is extremely jerky when I move my character, it isn’t smooth at all. I feel like if I understood what was going on, I’d understand how to fix this bug

1 Like

This function is quite simple once you see what it’s doing. It’s not what you want for this purpose, by the way, but let’s understand it anyway.

A vector can represent a direction, right? For example, Vector3.right is (1,0,0), and it represents a direction straight in the +X direction. Vector3(0,1,1) would represent a vector straight up. OK so far?

Now, what RotateTowards does is give you a new vector that’s part way between one vector (your “current direction”) and another (the “target direction”). How far towards the target should it be? All the way? Half way? 10 degrees? 30 degrees? Pi/4 radians?

That’s what maxRadiansDelta is for. It’s the maximum number of radians this function will move from the current direction to the target direction. I assume here you understand the difference between radians and degrees (but if not, just say so). So, pass in how many radians you’re willing to move in this time step, and RotateTowards won’t rotate more than that. (It may rotate less than that, if the current direction is already closer than that to the target).

Normally you represent a direction with unit (magnitude=1) vectors. But if for some reason your vectors have different magnitudes, RotateTowards can also interpolate the magnitudes. The maxMagnitudeDelta parameter controls how far (at most) the magnitude will change.

So, hopefully you understand now what this function does. But a vector alone can’t represent an orientation, so it’s not what you want to make the camera look at something. For that you want Quaternion.RotateTowards instead.

Cheers,

  • Joe
8 Likes

Thanks a lot, you’ve helped clear up most of my questions, appreciated a bunch

Quick question, is Vector3.RotateTowards essentially making a Vector3 suitable for Quaternion.RotateTowards, and then is executed from there? I have a loose knowledge on Quaternions but I think they mainly deal with rotations, right?

Also, what would I want to use for this purpose?

No, Vector3.RotateTowards really has nothing to do with Quaternion.RotateTowards. A vector represents a position or a direction. A quaternion represents an orientation or a rotation.

I’ll sketch out for you how to approach making an object always face another object (by smoothly turning towards it).

  • Use Quaternion.LookRotation to figure out the rotation that looks directly at the target.
  • Use Quaternion.RotateTowards to move your current rotation closer to this target rotation (from step 1) on each frame.
  • …There’s no step 3. :slight_smile:
2 Likes

Oh I see. I was aware that Vector3’s were mainly used for coordinates, however I thought they were often also used to represent 3 individual values, the X, Y, and Z, which rotations also use, however they’re not utilized the same way. Hence the reason why I thought that Vector3.RotateTowards would “setup” the Vector3 to be optimal for Quaternion.RotateTowards so that way they can translate that Vector3’s vectors and turn them into a Quaternion

Really wish the Scripting API pages would be a little more explanatory, especially for something that’s meant to help new people, hahaha. But thanks, with my newfound knowledge thanks to you, I might be able to tackle this problem alone. Thanks for your help!

Ah, I see. Yes, in fact you can represent a rotation as separate rotations around the X, Y, and Z axes; this is called “Euler angles.” And yeah, I guess we do occasionally store Euler angles in a Vector3 for convenience. Euler angles are easy for us humans to grasp, but they have many mathematical problems; see the accepted answer here for example. So, basically, you should use Euler angles as little as possible, and only for things like initialization or maybe readout for debugging purposes. Never attempt to do things like interpolation with them!

Quaternions suffer from none of the mathematical problems. They’re what you want to use for composing rotations, interpolating between two rotations, etc.

Good luck,

  • Joe
3 Likes