Box Casting for aligning an object to a surface

Hello everyone, I am attempting to align an object to the surface using a “Box Cast”, the problem I am having is that, The is positioned and that it is rotated to align with the surface, But when rotated it just is a bit away from the ground, Of course it makes sense because the box cast is straight and isn’t rotated so it returns the highest hit, I would like it to be perfectly aligned to the ground oriented as well, Any help/suggestion is appreciated.

here is the code that doesn’t work best.

using UnityEngine;

public class BoxCastTest : MonoBehaviour
{
    public Vector3 boxSize = new Vector3(1, 1, 1);
    public Vector3 boxCastDirection;

    public float maxDistance = 5f;

    public LayerMask layerMask;

    public GameObject boxObject;

    private void Start()
    {
        boxCastDirection = -transform.up;
    }

    void Update()
    {
        PerformBoxCastAndAlign();
    }

    void PerformBoxCastAndAlign()
    {
        if (boxObject == null)
        {
            Debug.LogError("Box object is not assigned!");
            return;
        }

        RaycastHit hit;

        if (Physics.BoxCast(transform.position, boxSize / 2, boxCastDirection, out hit, transform.rotation, maxDistance, layerMask))
        {
            // Calculate the target rotation
            Quaternion targetRotation = Quaternion.FromToRotation(transform.up, hit.normal) * transform.rotation;

            // Align rotation
            boxObject.transform.rotation = targetRotation;

            // Set the size of the box object
            boxObject.transform.localScale = boxSize;

            // Position
            boxObject.transform.position = transform.position + boxCastDirection * hit.distance;
        }
    }

    void OnDrawGizmos()
    {
        // Draw the box cast for debugging purposes
        Gizmos.color = Color.red;
        Gizmos.DrawWireCube(transform.position + boxCastDirection * maxDistance, boxSize);
    }
}

Anybody Has An idea on how to achieve this?, Still waiting,

If you want to use boxcasts to align an object to a slope, you have to do a lot of math to correct for the hitpoint offset in correspondance to the slope angle. mathematically that’s quite complex because it involves so many edge cases. it actually involves so many edge cases that even math alone can’t fix it, due to missing information of the corresponding surface. which means: you will need some form of raycast or spherecast in addition to handle those specific edge cases. overall this can get quite difficult to implement, so for your case i recommend that you use a raycast from the center of your object to acquire the correct position and rotation from the surface instead of a boxcast.

3 Likes

So box cast returns a hit point? should I perform a ray or sphere cast from that point + a height offset?, but then I am not sure how to calculate the target position and rotation for it., Anyway thanks!, I guess a lot of trial and error would be required.

If you shoot a simple raycast from the center of your object towards a “normalizedRaycastDirectionVector”, you will get a hitpoint. from that hitpoint, subtract normalizedRaycastDirectionVector * objectHeight * 0.5f to get your new center position. to compute the new rotation use hit.normal. if you use Quaternion.FromToRotation you will have to multiply the result to your current rotation (instead of setting it, like you did in your code, which technically should be wrong, however i don’t know your use-case specifically so…). In general it will be a lot of trial and error until you get a working solution :slight_smile:

1 Like

I will update the thread once I get my results.:grinning: thanks for your help!

I thought about your problem again and you should probably use a SphereCast instead of a Raycast. use your objects height * 0.5f as your radius. To compute the new position, use ray.origin + ray.direction * hit.distance

The reason: with the raycast you still have to account for the slope angle for how much you push your object up to have absolute precission, which in edge-cases (very steep angles) can lead to issues. with SphereCasts where the radius ~= objectheight you won’t run into these edge cases :wink:

Thanks!, let’s see what I get.:soon: