I’m attempting to use the Mathf.Clamp() function to restrict the movement of a user controlled object. But for some reason, it doesn’t seem to have any effect.
All the examples that I have come across seem to be in Javascript, rather than my preffered C#, so I’m open to the possibility it could be a variable type issue of some sort.
Can any of you kind folks see the issue?
using UnityEngine;
using System.Collections;
public class MoveXY : MonoBehaviour {
public Transform target;
public float speedHorizontal = 10.0F;
public float speedVertical = 10.0F;
void Start () {
if(!target)
return;
}
void Update () {
float translation = Input.GetAxis("Vertical") * speedVertical;
translation = translation * Time.deltaTime;
float translation2 = Input.GetAxis("Horizontal") * speedHorizontal;
translation2 = translation2 * Time.deltaTime;
target.transform.Translate(0.0F, translation, 0.0F);
target.transform.Translate(Mathf.Clamp(translation2, -2.0F, 2.0F), 0.0F, 0.0F);
}
}
Mathf.Clamp always works as expected. Your code is limiting the speed. If you mean to limit the position, transform.Translate isn’t what you want, since that’s relative movement, not absolute.
I note that you’re clamping the displacement of the object (its per-frame movement), not its absolute position. If you want to constrain its x position, translate it without clamping, then do target.transform.position.x = Mathf.Clamp(target.transform.position.x, -2, 2)
afterwards.
public static Vector3 ClampVector3(Vector3 vec, Vector3 min, vector3 max)
{
return Vector3.Min(max,Vector3.Max(min,vec));
}
This function will clamp a vector3 within the box defined by min and max. If you just want to clamp only one axis you have to do it that way:
Vector3 pos = target.position;
pos.x = Mathf.Clamp(pos.x, 2.0f, -2.0f);
target.position = pos;
I had a script which clamped x and y using transform.position to move my player - this worked fine.
I tried to use the Translate method, and clamp the X and Y values in C# but did not work.
Annoying since using Translate() makes my object transform a lot smoother than using transform.position = new Vector(x,y,z) - this is too precise.
In order to use Translate() with clamps I had to write the code in Javascript (which worked) so that is one of your options. However I forgot I had a C# script that I found which results in smooth transformations that uses transform.position = new Vector 3 so here it is:
using System.Collections;
public class DragScript : MonoBehaviour
{
[SerializeField]
float _horizontalLimit = 2.5f, _verticalLimit = 2.5f, dragSpeed = 0.01f;
Transform cachedTransform;
Vector3 startingPos;
void Start ()
{
//Make reference to transform
cachedTransform = transform;
//Save starting position
startingPos = cachedTransform.position;
}
void Update ()
{
if (Input.touchCount > 0) {
Vector2 deltaPosition = Input.GetTouch (0).deltaPosition;
//Switch through touch events
switch (Input.GetTouch (0).phase) {
case TouchPhase.Began:
break;
case TouchPhase.Moved:
DragObject (deltaPosition);
break;
case TouchPhase.Ended:
break;
}
}
}
void DragObject (Vector2 deltaPosition)
{
cachedTransform.position = new Vector3 (Mathf.Clamp ((deltaPosition.x * dragSpeed) + cachedTransform.position.x,
startingPos.x - _horizontalLimit, startingPos.x + _horizontalLimit),
Mathf.Clamp ((deltaPosition.y * dragSpeed) + cachedTransform.position.y, startingPos.y - _verticalLimit, startingPos.y + _verticalLimit),
cachedTransform.position.z);
}
}