# Limit position rigidbody

How can I limit the position of a rigidbody, between two values ​​if I use this code:

public Vector3 dir;

Rigidbody rb;

void Awake()
{
rb = GetComponent<Rigidbody>();
}

void FixedUpdate()
{
rb.velocity = new Vector3(0f, 0f, 6f);

}


If I use Vector3.Clamp then the object will shake

• This body appears to be able to move in 3 dimensions. Do you want to limit it to within an axis-aligned rectangular prism in worldspace, or some other shape of volume? And are there any other physics interactions acting on this body, such as collisions from other objects? – DMGregory Mar 25 '20 at 14:28
• Do you happen to have some kind of "play area" and are looking for some way to prevent objects from leaving it? – Philipp Mar 25 '20 at 16:04
• @DMGregory, In world space along the x axis. Yes, I have a play area. – Aimon Z. Mar 25 '20 at 18:01
• And can this object move on any other axes? Should we permit/preserve motion on those axes? – DMGregory Mar 25 '20 at 18:03
• @DMGregory, Yes, on other axes the object can move – Aimon Z. Mar 25 '20 at 18:04

# Your problem is the use of FixedUpdate() for position clamping. You are correct to apply the forces in FixedUpdate() but clamping the position should be done in Update() or LateUpdate().

public Vector3 dir;
public Vector3 min;
public Vector3 max;

Rigidbody rb;

void Awake()
{
rb = GetComponent<Rigidbody>();
}

void FixedUpdate()
{
rb.velocity = new Vector3(0f, 0f, 6f);

}

void Update()
{
transform.position = new Vector3(
Mathf.Clamp(transform.position.x, min.x, max.x),
Mathf.Clamp(transform.position.y, min.y, max.y),
Mathf.Clamp(transform.position.z, min.z, max.z));
}


FixedUpdate() is frame-rate independent, which means that there are frames happening in between those calculations. The GameObject's position however is recalculated for every frame. The reason you are seeing shaking when clamping in FixedUpdate() is that there is a force on the object that would cause it to move, causing the position in each frame to be calculated as the distance moved from the last frame, but then you are clamping it at a different rate than the framerate so it returns to the clamped value every few frames.

• I don't recommend mixing physics and non-physics (transform) manipulation on a single object. This will disable interpolation on the rigidbody, which can make your movement look juddery, and can teleport the object into obstacles, leading to tunnelling or other incorrect collision resolution. – DMGregory Mar 26 '20 at 10:38

We can also use physics itself to do the clamping, at the end of each FixedUpdate:

// Project where our velocity will take us by the end of the frame.
Vector3 positionAtEndOfStep = rb.position + rb.velocity * Time.deltaTime;

// Limit that projected position to within our allowed bounds.
positionAtEndOfStep.x = Mathf.Clamp(positionAtEndOfStep.x, min, max);

// Compute a velocity that will take us to this clamped position instead.
Vector3 neededVelocity = (positionAtEndOfStep - rb.position)/Time.deltaTime;

// You can also calculate this as the needed velocity change/acceleration,