Unity世界座標轉屏幕座標等關係——最白話,手把手教你做系列。

遇到問題

通過一個世界座標,在屏幕對應位置生成Ui。

記錄原因

在沒遇到這個問題之前也聽過類似的需求,想法也很簡單,就是有個方法Camera.main.WorldToScreenPoint();世界座標轉屏幕座標,然後克隆物體並賦值。
如圖示方法
在這裏插入圖片描述然而,在實際操作的時候卻發現,無論怎麼操作,都無法達到所需要的效果。這就讓我對自己的雲代碼能力產生了懷疑。
之後我通過對比輸出的屏幕座標和我需要顯示的物體位置不斷對比,發現我對這幾種概念完全懵了。屏幕座標?世界座標?視口座標?

重點

通過查詢很多材料。我意識到原來Unity中有四種座標系
1 .World Space(世界座標):三維空間座標,Vector3。
2.Screen Space(屏幕座標):以像素來定義的,以屏幕的左下角爲(0,0)點,右上角爲(Screen.width,Screen.height),Z的位置是以相機的世界單位來衡量的。
3.ViewPort Space(視口座標):視口座標是標準的和相對於相機的。相機的左下角爲(0,0)點,右上角爲(1,1)點,Z的位置是以相機的世界單位來衡量的。
4.UGUI界面的座標系:與錨點有關,錨點所在位置即爲(0,0)。
那麼問題就出來了。
我們的需求是通過一個世界座標,在屏幕對應位置生成Ui。所以我主觀的認爲這個屏幕對應位置即爲屏幕座標。然而事實上在3D的場景中屏幕顯示的位置就是物體所在的位置。那麼,這個屏幕的對應位置應該Ui的座標。所以需求其實應該是通過一個世界座標,在Ui的對應位置上生成一個Ui。
那麼問題就好解決了。以下是我用到的方法作爲參考,參數都有說明。

/// <summary>
    /// 世界座標轉屏幕座標
    /// </summary>
    /// <param name="pos"></param>
    public void WorldToScreen(Vector3 pos)
    {
        //克隆物體
        GameObject obj = Instantiate(Resources.Load("prefabs/Wts_Icon")) as GameObject; 
        //獲取屏幕座標
        Vector3 pt = Camera.main.WorldToScreenPoint(Cube.transform.position);
        //獲取在(參數1)Canvas下(參數2)屏幕座標對應(參數3)攝像機下的(參數3)Ui座標
        Vector2 v;
        RectTransformUtility.ScreenPointToLocalPointInRectangle(m_canvas.transform as RectTransform, pt, m_cam, out v);     
        //給物體位置賦值並設置父物體
        obj.transform.position = v;
        obj.transform.SetParent(m_canvas.transform, false);     
    }

這種也是做血條跟隨之類需求的實現方式之一。
最後點一下obj.transform.SetParent(m_canvas.transform, false);這個方法不能用obj.transform.SetParent(m_canvas.transform);代替,也不能隨意改動執行順序,也是坑之一。因爲你生成的物體是在3D場景裏,直接放在父物體下會發生位置和大小的變化,改動順序也是一樣。

以上。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章