Camera.ScreenToWorldPoint
Vector3 ScreenToWorldPoint(Vector3 position);
將屏幕坐標轉換為世界坐標。
如何轉換?假如給定一個所謂的屏幕坐標(x,y,z),如何將其轉換為世界坐標?
首先,我們要理解攝像機是如何渲染物體的:
攝像機對游戲世界的渲染范圍是一個平截頭體,渲染邊界是一個矩形,用與near clippingplane或者far clippingplane平行的平面截取這個平截頭體,可以獲得無數個平行的矩形面,也就是我們看到的屏幕矩形。離攝像機越遠,矩形越大,離攝像機越近,矩形越小。所以,同樣大小的物體,隨着離攝像機越來越遠,相對於對應屏幕矩形就越來越小,所看起來就越來越小。
在屏幕上,某個像素點相對於屏幕矩形的位置,可以對應於游戲世界中的點相對於某個截面的位置,關鍵在於這個點在哪個截面上,也就是說,關鍵在於這個截面離攝像機有多遠!
在ScreenToWorldPoint這個方法中,參數是一個三維坐標,而實際上,屏幕坐標只能是二維坐標。參數中的z坐標的作用就是:用來表示上述平面離攝像機的距離。
也就是說,給定一個坐標(X,Y,Z),
首先截取一個垂直於攝像機Z軸的,距離為Z的平面P,這樣不管X,Y怎么變化,返回的點都只能在這個平面上;
然后,X,Y表示像素坐標,根據(X,Y)相對於屏幕的位置,得到游戲世界中的點相對於截面P的位置,我們也就將屏幕坐標轉換為了世界坐標。
官網文檔中的說法:
Camera.ScreenToWorldPoint
Vector3 ScreenToWorldPoint(Vector3 position);
Description
Transforms position from screen space into world space.
Screenspace is defined in pixels. The bottom-left of the screen is (0,0); the right-top is (pixelWidth,pixelHeight). The z position is in world units from the camera.
using UnityEngine; using System.Collections; public class Example : MonoBehaviour { void OnDrawGizmosSelected() { Vector3 p = camera.ScreenToWorldPoint(new Vector3(100, 100, camera.nearClipPlane)); Gizmos.color = Color.yellow; Gizmos.DrawSphere(p, 0.1F); } }
博主測試:
在屏幕上創建一個cube,攝像機從上往下照 ,讓cube跟隨鼠標移動
using System.Collections; using System.Collections.Generic; using UnityEngine; public class MainCameraScript : MonoBehaviour { public int pixelWidth; public int pixelHeight; public Vector3 mousePosition; public Vector3 worldPosition; public GameObject cube; // Use this for initialization void Start () { } // Update is called once per frame void Update () { pixelWidth = this.GetComponent<Camera>().pixelWidth; pixelHeight = this.GetComponent<Camera>().pixelHeight; mousePosition = Input.mousePosition; mousePosition.z = this.GetComponent<Camera>().farClipPlane; worldPosition = this.GetComponent<Camera>().ScreenToWorldPoint(mousePosition); cube.GetComponent<Transform>().position = worldPosition; } }