使用Raycast同时移动两个播放器对象

时间:2018-07-26 23:15:33

标签: unity3d controls game-physics raycasting

我们已经设置了播放器控制器脚本并正在为单个播放器对象工作,但是当我们要添加第二个播放器对象时,就会遇到麻烦。我知道我们可能会使用LayerMask来使RayCast忽略播放器对象,但是当发生这种情况时,两个对象都将尝试移入同一空间并引起问题。我为此感到难过。

播放器控制器脚本:

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

public class PlayerController : MonoBehaviour
{
    public float speed;
    bool isMoving;
    float distance;
    Vector3 endPos;
    public Text parText;
    private int par;
    public static int moves;
    bool upDetect;
    bool downDetect;
    bool rightDetect;
    bool leftDetect;
    Vector3 upLine;
    Vector3 downLine;
    Vector3 leftLine;
    Vector3 rightLine;
    public bool actionCheck;
    Vector3 actionLine;

    void Start()
    {
        isMoving = false;
        par = Counter.levelPar;
        endPos = transform.position;
        //setPar();
    }

    private void FixedUpdate()
    {
        upLine = new Vector3(transform.position.x, transform.position.y, transform.position.z + 0.1f);
        upDetect = Physics.Linecast(transform.position, upLine);
        Debug.DrawLine(transform.position, upLine);

        downLine = new Vector3(transform.position.x, transform.position.y, transform.position.z - 0.1f);
        downDetect = Physics.Linecast(transform.position, downLine);
        Debug.DrawLine(transform.position, downLine);

        leftLine = new Vector3(transform.position.x - 0.1f, transform.position.y, transform.position.z);
        leftDetect = Physics.Linecast(transform.position, leftLine);
        Debug.DrawLine(transform.position, leftLine);

        rightLine = new Vector3(transform.position.x + 0.1f, transform.position.y, transform.position.z);
        rightDetect = Physics.Linecast(transform.position, rightLine);
        Debug.DrawLine(transform.position, rightLine);

       // actionLine = new Vector3(transform.position.x, transform.position.y - 1, transform.position.z);
       // actionCheck = Physics.Linecast(transform.position, actionLine);
       // Debug.DrawLine(transform.position, actionLine);

        if (Input.GetKey("left") && isMoving == false && leftDetect == false)
        {
            isMoving = true;
            RaycastHit hit;
            Ray leftRay = new Ray(transform.position, Vector3.left);
            if (Physics.Raycast(leftRay, out hit))
            {
                if (hit.collider != null)
                {
                    endPos = new Vector3(hit.collider.transform.position.x + 1, endPos.y, endPos.z);
                }
            }
            //countMove();
        }

        if (Input.GetKey("right") && isMoving == false && rightDetect == false)
        {
            isMoving = true;
            RaycastHit hit;
            Ray rightRay = new Ray(transform.position, Vector3.right);
            if (Physics.Raycast(rightRay, out hit))
            {
                if (hit.collider != null)
                {
                    endPos = new Vector3(hit.collider.transform.position.x - 1, endPos.y, endPos.z);
                }
            }
            //countMove();
        }

        if (Input.GetKey("up") && isMoving == false && upDetect == false)
        {
            isMoving = true;
            RaycastHit hit;
            Ray upRay = new Ray(transform.position, Vector3.forward);
            if (Physics.Raycast(upRay, out hit))
            {
                if (hit.collider != null)
                {
                    endPos = new Vector3(endPos.x, endPos.y, hit.collider.transform.position.z - 1);
                }
            }
            //countMove();
        }

        if (Input.GetKey("down") && isMoving == false && downDetect == false)
        {
            isMoving = true;
            RaycastHit hit;
            Ray downRay = new Ray(transform.position, -Vector3.forward);
            if (Physics.Raycast(downRay, out hit))
            {
                if (hit.collider != null)
                {
                    endPos = new Vector3(endPos.x, endPos.y, hit.collider.transform.position.z + 1);
                }
            }
            //countMove();
        }



        distance = Vector3.Distance(transform.position, endPos);
        //Debug.Log(distance);
        //Debug.Log(rightDetect);
        //Debug.Log(leftDetect);
        //Debug.Log(upDetect);
        //Debug.Log(downDetect);

        if (distance < 0.01)
        {
            distance = 0;
        }

        if (distance > 0)
        {
            transform.position = Vector3.Lerp(
                transform.position, endPos,
                Time.deltaTime * speed / distance);
            transform.rotation = Quaternion.identity;
        }
        else
        {
            isMoving = false;
            endPos = transform.position;
        }

        //setPar();

    }

    /*void countMove()
    {
        moves++;

        if (par > 0)
        {
            par--;
        }
    }

    void setPar()
    {
        parText.text = "Par: " + par.ToString();
    }*/

}

1 个答案:

答案 0 :(得分:1)

弄清楚了。我必须使用Raycast命中来找出它命中了什么物体。如果对象具有“ Player”标签,则它将转到该对象的PlayerController脚本并获取其结束pos的值。然后,我只需要调整endPos变量即可补偿多余的空间。这是我的代码。

PlayerController:

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

public class PlayerController : MonoBehaviour
{
    public float speed;
    bool isMoving;
    public float distance;
    public Vector3 endPos;
    public Text parText;
    private int par;
    public static int moves;
    bool upDetect;
    bool downDetect;
    bool rightDetect;
    bool leftDetect;
    Vector3 upLine;
    Vector3 downLine;
    Vector3 leftLine;
    Vector3 rightLine;
    Vector3 actionLine;
    Rigidbody rb;

    void Start()
    {

        isMoving = false;
        par = Counter.levelPar;
        endPos = transform.position;
        rb = GetComponent<Rigidbody>();

        //setPar();
    }

    private void FixedUpdate()
    {
        upLine = new Vector3(transform.position.x, transform.position.y, transform.position.z + 1);
        upDetect = Physics.Linecast(transform.position, upLine);
        Debug.DrawLine(transform.position, upLine);

        downLine = new Vector3(transform.position.x, transform.position.y, transform.position.z - 1);
        downDetect = Physics.Linecast(transform.position, downLine);
        Debug.DrawLine(transform.position, downLine);

        leftLine = new Vector3(transform.position.x - 1, transform.position.y, transform.position.z);
        leftDetect = Physics.Linecast(transform.position, leftLine);
        Debug.DrawLine(transform.position, leftLine);

        rightLine = new Vector3(transform.position.x + 1, transform.position.y, transform.position.z);
        rightDetect = Physics.Linecast(transform.position, rightLine);
        Debug.DrawLine(transform.position, rightLine);

       // actionLine = new Vector3(transform.position.x, transform.position.y - 1, transform.position.z);
       // actionCheck = Physics.Linecast(transform.position, actionLine);
       // Debug.DrawLine(transform.position, actionLine);

        if (Input.GetKey("left") && isMoving == false && leftDetect == false)
        {
            isMoving = true;
            RaycastHit hit;
            Ray leftRay = new Ray(transform.position, Vector3.left);
            if (Physics.Raycast(leftRay, out hit))
            {
                if (hit.collider != null && hit.collider.tag != "Player")
                {
                    endPos = new Vector3(hit.collider.transform.position.x + 1, endPos.y, endPos.z);
                }

                if (hit.collider.tag == "Player")
                {
                    GameObject oPlayer = hit.collider.gameObject;
                    endPos = GetOtherEndPos(oPlayer);
                    endPos = new Vector3(endPos.x + 1, endPos.y, endPos.z);
                }
            }
            //countMove();
        }

        if (Input.GetKey("right") && isMoving == false && rightDetect == false)
        {
            isMoving = true;
            RaycastHit hit;
            Ray rightRay = new Ray(transform.position, Vector3.right);
            if (Physics.Raycast(rightRay, out hit))
            {
                if (hit.collider != null && hit.collider.tag != "Player")
                {
                    endPos = new Vector3(hit.collider.transform.position.x - 1, endPos.y, endPos.z);
                }

                if (hit.collider.tag == "Player")
                {
                    GameObject oPlayer = hit.collider.gameObject;
                    endPos = GetOtherEndPos(oPlayer);
                    endPos = new Vector3(endPos.x - 1, endPos.y, endPos.z);
                }
            }
            //countMove();
        }

        if (Input.GetKey("up") && isMoving == false && upDetect == false)
        {
            isMoving = true;
            RaycastHit hit;
            Ray upRay = new Ray(transform.position, Vector3.forward);
            if (Physics.Raycast(upRay, out hit))
            {
                if (hit.collider != null && hit.collider.tag != "Player")
                {
                    endPos = new Vector3(endPos.x, endPos.y, hit.collider.transform.position.z - 1);
                }

                if (hit.collider.tag == "Player")
                {
                    GameObject oPlayer = hit.collider.gameObject;
                    endPos = GetOtherEndPos(oPlayer);
                    endPos = new Vector3(endPos.x , endPos.y, endPos.z - 1);
                }
            }
            //countMove();
        }

        if (Input.GetKey("down") && isMoving == false && downDetect == false)
        {
            isMoving = true;
            RaycastHit hit;
            Ray downRay = new Ray(transform.position, -Vector3.forward);
            if (Physics.Raycast(downRay, out hit))
            {
                if (hit.collider != null && hit.collider.tag != "Player")
                {
                    endPos = new Vector3(endPos.x, endPos.y, hit.collider.transform.position.z + 1);
                }

                if (hit.collider.tag == "Player")
                {
                    GameObject oPlayer = hit.collider.gameObject;
                    endPos = GetOtherEndPos(oPlayer);
                    endPos = new Vector3(endPos.x, endPos.y, endPos.z + 1);
                }
            }
            //countMove();
        }

        distance = Vector3.Distance(transform.position, endPos);
        //Debug.Log(distance);
        //Debug.Log("Name: " + this.name + " distance = " + distance + " vel = " + rb.velocity.magnitude + " isMoving: " + isMoving);
        //Debug.Log(rightDetect);
        //Debug.Log(leftDetect);
        //Debug.Log(upDetect);
        //Debug.Log(downDetect);
        //Debug.Log(isMoving);
        //Debug.Log("Velocity = " + rb.velocity.magnitude);

        if (distance < 0.1)
        {
            distance = 0;
        }

        if (distance > 0)
        {
            transform.position = Vector3.Lerp(
                transform.position, endPos,
                Time.deltaTime * speed / distance);
            transform.rotation = Quaternion.identity;
        }

        else
        {
            isMoving = false;
            endPos = transform.position;
        }

        //setPar();

    }

    Vector3 GetOtherEndPos(GameObject oPlayer)
    {
        PlayerController script = oPlayer.GetComponent<PlayerController>();
        return script.endPos;
    }

    /*void countMove()
    {
        moves++;

        if (par > 0)
        {
            par--;
        }
    }

    void setPar()
    {
        parText.text = "Par: " + par.ToString();
    }*/

}