hey everyone i m in a project where i have to limit rotation of my ,targetItem( a gameobject) to some digress say 180 to 350 degree.i am able to do some portion of it using math.clamp when i go towards 180 everything works fine but when i go beyond 350 degree it sets value of my targetItem to 180. how can i fix this problem so that ,when i try to go beyond 350 it shuld not reset my value to 180 and stay at 350 degree
here is my code
if(hit.transform.name=="stear" )
{
var MinClamp = 180;
var MaxClamp = 350;
if(Input.GetTouch(i).phase == TouchPhase.Moved)
{
targetItem.transform.Rotate(0, theTouch.deltaPosition.x * rotationRate,0,Space.World);
targetItem.transform.rotation.eulerAngles = new Vector3( 0, Mathf.Clamp(targetItem.transform.rotation.eulerAngles.y,MinClamp,MaxClamp),0);
print(targetItem.transform.rotation.eulerAngles.y);
}
}
for more detail u can see the log and projet in youtube link given
project live in action in youtube
public static float ClampAngle(float angle, float min, float max)
{
angle = Mathf.Repeat(angle, 360);
min = Mathf.Repeat(min, 360);
max = Mathf.Repeat(max, 360);
bool inverse = false;
var tmin = min;
var tangle = angle;
if(min > 180)
{
inverse = !inverse;
tmin -= 180;
}
if(angle > 180)
{
inverse = !inverse;
tangle -= 180;
}
var result = !inverse ? tangle > tmin : tangle < tmin;
if(!result)
angle = min;
inverse = false;
tangle = angle;
var tmax = max;
if(angle > 180)
{
inverse = !inverse;
tangle -= 180;
}
if(max > 180)
{
inverse = !inverse;
tmax -= 180;
}
result = !inverse ? tangle < tmax : tangle > tmax;
if(!result)
angle = max;
return angle;
}
Reading transform.eulerAngles is always a bad idea: it’s actually transform.rotation converted to a 3-axes (Euler) representation; since there are several XYZ combinations that correspond to a single rotation, Unity may (and often will) return the “wrong” one (a valid XYZ combination, but not the one you expect).
When you must rotate something to precise angles or inside precise limits, the best alternative is to save the angle in a member variable (declared outside any function) and “rotate” it mathematically, then assign the angle to transform.eulerAngles (writing to eulerAngles works fine). Your code could become something like this:
// declare this variable outside any function:
private var angle: Vector3 = Vector3.zero;
...
if (hit.transform.name=="stear" )
{
if(Input.GetTouch(i).phase == TouchPhase.Moved)
{
// "rotate" angle.y mathematically:
angle.y += theTouch.deltaPosition.x * rotationRate;
// clamp it to the desired limits:
angle.y = Mathf.Clamp(angle.y, 180, 350);
// update target actual rotation:
targetItem.transform.eulerAngles = angle;
}
}