微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

Raycast2D 只击中对撞机的一侧

如何解决Raycast2D 只击中对撞机的一侧

我想确保高速移动的各种物体不能穿过墙壁或其他物体。我的思考过程是通过 Raycast 检查两个运动时刻之间是否发生了碰撞。

所以脚本应该记住之前的位置并通过 Raycast 检查之前和当前位置之间的碰撞。

如果发生碰撞,应将物体定位在会合点并沿先前位置的方向稍微移动。

我的问题是在地图外工作,而不是在地图内工作。如果我从内到外,我可以穿墙。从外到内都没有。

很明显,我对使用光线投射的应用程序有一些误解。

MapLayout with Walls

    using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class ObsticalControll : MonoBehavIoUr
{

    private Vector3 positionBefore;
    public LayerMask collisionLayer = 9;
    private Vector3 lastHit = new Vector3(0,-20);
    // Start is called before the first frame update
    void Start()
    {
        positionBefore = transform.position;


    }

    private void OnDrawGizmos()
    {
        Gizmos.DrawCube(lastHit,new Vector3(.2f,.2f,.2f));
    }

    // Update is called once per frame
    void Update()
    {
        Vector3 curruentMovement = transform.position;
        Vector2 dVector = (Vector2)transform.position - (Vector2)positionBefore;
        float distance = Vector2.distance((Vector2)positionBefore,(Vector2)curruentMovement);
        RaycastHit2D[] hits = Physics2D.RaycastAll((Vector2)positionBefore,dVector,distance,collisionLayer);

        if(hits.Length > 0)
        {
            Debug.Log(hits.Length);
            for (int i = hits.Length -1 ; i >= 0 ; i--)
            {
                RaycastHit2D hit = hits[i];
                if (hit.collider != null)
                {
                    Debug.Log("hit");
                    lastHit.x = hit.point.x;
                    lastHit.y = hit.point.y;      
                    Vector3 resetPos = new Vector3(hit.point.x,hit.point.y,transform.position.z) + positionBefore.normalized * 0.1f;
                    transform.position = new Vector3(resetPos.x,resetPos.y,transform.position.z);
                }
            }
                
           
        }



        positionBefore = transform.position;
    }
}

解决方法

Unity 内置了一个更好的方法来处理这个问题。 假设高速移动的物体具有刚体(在您的情况下为 2d),您可以将其碰撞检测设置为连续而不是离散。

enter image description here

这将有助于高速碰撞的碰撞,假设它高速移动并且墙壁没有移动。

如果由于某种原因您无法将其应用于您的场景,我会尝试帮助解决光线投射。

,

然而,我仍然想知道我的 raycast 脚本的碰撞行为。如果你想通过光线投射计算镜头或类似的东西,那肯定会很有趣

好的,所以您最初的想法是检查是否发生了碰撞,通过检查其当前位置和先前位置。并检查它们之间是否有任何东西,这意味着发生了碰撞。然后你会把它传送回它应该击中的地方。

一个更好的方法是检查游戏对象在下一帧中的位置,通过在它前面进行光线投射,以及它将行进的距离。如果它确实击中了某些东西,这意味着在下一帧内,它就会与它发生碰撞。所以你可以在碰撞命中点停止它,并得到它命中的东西。 (这意味着您不必将其传送回来,因此不会有一个帧通过然后返回)

几乎相同的想法,但稍微简单一些。

问题是,如果在下一帧中另一个物体也出现在它们之间,它就无法解释这一点。这就是刚体.movePosition 发光的地方,并且使用 OnCollisionEnter 您可以检测到它何时以及正确碰撞了什么。以及无需将其传送回来

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。