- Home /
Quick Question About Limiting a Rotation.
Hey guys! I'm not the best person when it comes to rotations, sorry. I have a problem. I have a flashlight attached to my first person controller. This flashlight is not static, it follows the mouse. I want to limit the rotation of the flashlight so that it doesn't go too far off the screen. Here is the code to make the flashlight follow the mouse:
Vector3 v3Pos = Input.mousePosition;
v3Pos.z = moveArea;
v3Pos = Camera.main.ScreenToWorldPoint(v3Pos);
transform.LookAt(v3Pos);
And here is the code for my flashlight script:
Mathf.Clamp(transform.rotation.x, -20f , 20f);
Mathf.Clamp(transform.rotation.y, -30f , 30f);
The code to limit the rotation does not work. Please fix it and thanks a lot! :)
Can anyone help? It will be greatly appreciated :)
Try using Euler angels. WHen you do transform.rotation.x, you are getting the rotation of x in quaternions, which is between -1 and 1 not sure on the values but essentially it is small
Can you show me an example? I have never used Euler angles before
Ooh. I really like the new design for the script reference. $$anonymous$$uch cleaner.
Answer by robertbu · Mar 25, 2013 at 02:15 AM
"transform.rotation" as you used above is a Quaternion. A Quaternion is a 4D construct, and generally you don't address the individual properties such as x,y,z and w. From the script reference:
[Quaternions] are based on complex numbers and are not easy to understand intuitively. Thus you almost never access or modify individual Quaternion components (x,y,z,w);
You can get euler angles from a rotation, and as a shorthand, directly from the Transform. For example, you can read:
Vector3 v3Pos = transform.euler;
But are are issues with euler angles as well. First, for any physical rotation there are multiple euler rotations. So an object was spun around on the x axis by 180 degrees, you would expect a euler angle of (180,0,0), but the euler angle read back from the Transform might be instead (0,180,180) which represents the same rotation.
Second, you should not set individual components of a euler angle. You need to set all the as the same time by assigning a Vector3. From the script reference:
Do not set one of the eulerAngles axis separately (eg. eulerAngles.x = 10; ) since this will lead to drift and undesired rotations. When setting them to a new value set them all at once.
So limiting rotation is not a simple thing. There are complex scripts written to normalize and clamp rotations, but there are also other ways of looking at some problems that make a solution easy.
One idea for your situation you might only set the position if the mouse is within a certain area of the screen. The following code (untested) limits the LookAt to a radius of 1/2 of the screen height. You can adjust the radius by adjusting the calculation for "max_pixel_radius".
using UnityEngine;
using System.Collections;
public class Bug16 : MonoBehaviour {
float max_pixel_radius = Screen.height / 4.0f;
Vector2 v2Center = new Vector2(Screen.width / 2.0f, Screen.height / 2.0f);
void Update () {
float fT = ((Vector2)Input.mousePosition - v2Center).magnitude;
if (fT <= max_pixel_radius) {
Vector3 v3Pos = Input.mousePosition;
v3Pos.z = moveArea;
v3Pos = Camera.main.ScreenToWorldPoint(v3Pos);
transform.LookAt(v3Pos);
}
}
}
Very interesting! Works well but needs a few adjustments. I really like the way you handled that piece of code. I think it's very well executed and I will give you best answer. Thanks
Your answer
Follow this Question
Related Questions
gesture rotation clamp 2 Answers
I need help with clamping a rotation towards the mouse position 2 Answers
player flicks when mouse is near the player 1 Answer
Clamp Rotation Problem 1 Answer
How to limit the rotation of an object?? 2 Answers