天天看點

[Unity3D]射線碰撞檢測+LayerMask的使用

射線:射線是3D世界中一個點向一個方向發射的一條無終點的線,在發射軌迹中與其他物體發生碰撞時,它将停止發射 。

用途:在unity中射線應用範圍比較廣, 多用于碰撞檢測(如:子彈飛行是否擊中目标)、角色移動 等。

相關API:

1、Ray Camera.main.ScreenPointToRay(Vector3 pos)   傳回一條射線Ray從錄影機到螢幕指定一個點

2、Ray Camera.main.ViewportPointToRay(Vector3 pos)  傳回一條射線Ray從錄影機到視口(視口之外無效)指定一個點

3、Ray 射線類 

4、RaycastHit 光線投射碰撞資訊

5、bool Physics.Raycast(Vector3 origin, Vector3 direction, float distance, int layerMask)

    當光線投射與任何碰撞器交叉時為真,否則為假。

    bool Physics.Raycast(Ray ray, Vector3 direction, RaycastHit out hit, float distance, int layerMask)

    在場景中投下可與所有碰撞器碰撞的一條光線,并傳回碰撞的細節資訊()。

    bool Physics.Raycast(Ray ray, float distance, int layerMask)

    bool Physics.Raycast(Vector3 origin, Vector3 direction, RaycastHit out hit,float distance, int layerMask)

    注意:如果從一個球型體的内部到外部用光線投射,傳回為假。

    參數了解:

  origin : 在世界坐标中射線的起始點

  direction: 射線的方向

  distance: 射線的長度

  hit: 使用c#中out關鍵字傳入一個空的碰撞資訊類,然後碰撞後指派。可以得到碰撞物體的transform,rigidbody,point等資訊。 

  layerMask: 隻標明Layermask層内的碰撞器,其它層内碰撞器忽略。 選擇性的碰撞

6、RaycastHit[] RaycastAll(Ray ray, float distance, int layerMask)

   投射一條光線并傳回所有碰撞,也就是投射光線并傳回一個RaycastHit[]結構體。

列子如下:

using UnityEngine;

using System.Collections;

public class RayTest : MonoBehaviour {

    // Use this for initialization

    void Start ()

    {

        mainCrma = Camera.main;

    }

    private Camera mainCrma;

    private RaycastHit objhit;

    private Ray _ray;

    void Update () 

        if (Input.GetMouseButtonDown(0)) 

        {

            _ray=mainCrma.ScreenPointToRay(Input.mousePosition);//從錄影機發出一條射線,到點選的坐标

            Debug.DrawLine(_ray.origin,objhit.point,Color.red,2);//顯示一條射線,隻有在scene視圖中才能看到

            if (Physics.Raycast (_ray, out objhit, 100)) 

            {

                GameObject gameObj = objhit.collider.gameObject;

                Debug.Log("Hit objname:"+gameObj.name+"Hit objlayer:"+gameObj.layer);

            }

        }

[Unity3D]射線碰撞檢測+LayerMask的使用

layerMask參數:  

Raycast (ray : Ray, out hitInfo : RaycastHit, distance : float = Mathf.Infinity, layerMask : int = kDefaultRaycastLayers)

其實很簡單:1 << 10  打開第10的層。

~(1 << 10) 打開除了第10之外的層。

~(1 << 0) 打開所有的層。

(1 << 10) | (1 << 8) 打開第10和第8的層。

public class LayerMaskTest : MonoBehaviour {

    void Start () 

        mask = 1<<( LayerMask.NameToLayer("cube"));//執行個體化mask到cube這個自定義的層級之上。

    //private LayerMask mask 1<<10;

    private LayerMask mask;

            Debug.DrawLine(_ray.origin,objhit.point,Color.red,2);//劃出射線,隻有在scene視圖中才能看到

            if (Physics.Raycast (_ray,out objhit, 100, mask.value))

                Debug.Log("Hit objname:"+gameObj.name+"--Hit objlayerName:"+LayerMask.LayerToName (10));

}

 建立2個cube,一個layer設定為:cube  一個layer設定為:Default

運作如下:

[Unity3D]射線碰撞檢測+LayerMask的使用

繼續閱讀