团结 - 触发输入子弹弹跳

本文关键字:子弹 输入 团结 | 更新日期: 2023-09-27 18:34:10

我对简单的弹道学有一些问题。由于我是编码新手,我浪费了 2 天的搜索时间,所以我决定问一个问题。我的项目符号.cs脚本有问题,代码工作正常,除了弹跳部分。我使用 OnTriggerEnter 是因为子弹会穿透不同的材料,但会在特定角度下反弹,所以我只使用对撞机作为触发器。我知道可以使用OnCollisionEnter来确定正常并使用Vector3.Reflect。但是,如果对撞机不被设置为扳机,子弹就会从永远不会穿透墙壁的地方反弹。只需要底部弹跳部分的帮助。

public Rigidbody rb;
private float vel;
private float kEnergy;
private bool AP = false;
private bool HP = false;
private bool ricochet = false;
// Use this for initialization
void Start () {
    vel = 738f;
    kEnergy = 2108f;
    //HP == false;
    Destroy (gameObject, 10);
    rb = GetComponent<Rigidbody> ();
    rb.velocity = transform.forward * vel;
    Quaternion bulletRotaion = transform.rotation;
    Debug.Log (bulletRotaion.eulerAngles);
}
// Update is called once per frame
void Update () {
    float curVelocity = rb.velocity.magnitude;
    if (curVelocity <= 0)
    {
        curVelocity = 0f;
    }
}
void OnTriggerEnter (Collider c)
{
    if (c.tag == "Wall") {
        Quaternion localOffset = transform.rotation;
        float impactAngleX = c.gameObject.GetComponent <MaterialDensity> ().angleX;
        float impactAngleY = c.gameObject.GetComponent <MaterialDensity> ().angleY;
        float impactAngleZ = c.gameObject.GetComponent <MaterialDensity> ().angleZ;
        float angleX = localOffset.eulerAngles.x;
        float angleY = localOffset.eulerAngles.y;
        float angleZ = localOffset.eulerAngles.z;
        float density = c.gameObject.GetComponent <MaterialDensity> ().materialDensity;
        float ricochetX = (angleX + impactAngleX);
        if (ricochetX > 360) 
        {
            ricochetX = (ricochetX - 360);
        }
        if (ricochetX < 0) 
        {
            ricochetX = (ricochetX + 360);
        }
        float ricochetY = (angleY + impactAngleY);
        if (ricochetY > 360) 
        {
            ricochetY = (ricochetY - 360);
        }
        if (ricochetY < 0) 
        {
            ricochetY = (ricochetY + 360);
        }
        float ricochetZ = (angleZ + impactAngleZ);
        if (ricochetZ > 360) 
        {
            ricochetZ = (ricochetZ - 360);
        }
        if (ricochetZ < 0) 
        {
            ricochetZ = (ricochetZ + 360);
        }
        if ((ricochetX > 60 && ricochetX < 300) || (ricochetY > 60 && ricochetY < 300) || (ricochetZ > 60 && ricochetZ < 300)) {
            ricochet = true;
            //Debug.Log (ricochet);
        } 
        if ((ricochetX < 60 && ricochetX > 300) || (ricochetY < 60 && ricochetY > 300) || (ricochetZ < 60 && ricochetZ > 300)) {
            ricochet = false;
            //Debug.Log (ricochet);
        }
        Debug.Log (ricochet);
        Debug.Log (ricochetX);
        Debug.Log (ricochetY);
        Debug.Log (ricochetZ);
        if (AP) 
        {
            density *= 0.9f;
        }
        if (HP) 
        {
            density *= 3f;
        }
        //float vel = gameObject.GetComponent<GunNew>().velocity;
        float curVelocity = rb.velocity.magnitude;
        float velocityMod = curVelocity / vel;
        float densityMod = density / velocityMod;
        float curEnergy = (kEnergy * velocityMod);
        float energyMod = (curEnergy * velocityMod);
        rb = GetComponent<Rigidbody> ();
        //Quaternion localOffset = transform.rotation;
        float randomX = Random.Range (0.03f, 0f);
        float randomY = Random.Range (0.03f, -0.03f);
        if (randomX == 0) 
        {
            randomX = 0.01f;
        }
        if (randomY == 0) 
        {
            randomY = 0.01f;
        }
        localOffset.x += randomX;
        localOffset.y += randomY;
        if (curVelocity > densityMod && !ricochet) {
            rb.rotation = localOffset;
            rb.velocity = transform.forward * ((curVelocity - (curVelocity * (randomX + randomY))) - densityMod);
            //Debug.Log (curVelocity);
            //Debug.Log (energyMod);
        } 
        if (curVelocity > densityMod && ricochet)
        {
            Vector3 objAngle = new Vector3 (impactAngleX, impactAngleY, impactAngleZ);
            Vector3 bulletAngle = rb.rotation.eulerAngles;
            Debug.Log (objAngle);
        }
        if (curVelocity <= densityMod)
        {
            //Debug.Log (curVelocity);
            //Debug.Log (energyMod);
            Destroy (gameObject);
        }
    }
}

第二个代码是来自墙的代码。

public float materialDensity = 100f;
public float angleX;
public float angleY;
public float angleZ;
//Quaternion localOffset = transform.rotation;
// Use this for initialization
public void Start () 
{
    GetComponent<Rigidbody> ();
    Quaternion localOffset = transform.rotation;
    float angleX = localOffset.eulerAngles.x;
    float angleY = localOffset.eulerAngles.y;
    float angleZ = localOffset.eulerAngles.z;
    //Debug.Log (localOffset.eulerAngles.x);
}
// Update is called once per frame
void Update () {
}

团结 - 触发输入子弹弹跳

首先,我会在你的游戏中为会弹跳的东西和不会弹跳的东西做一个分层。

然后,当您测试与子弹的碰撞时,您只能检查与弹跳层的碰撞。这将提高性能,并使编码更加简单。

从那里,您可以依靠 Unity 的物理特性来执行自己的弹跳,或者如果您想自己计算它,您可以进行光线投射并使用光线投射的法线,如上所述。

if(Physics.Raycast (shootRay, out shootHit, range, ricochetMask)) {...