记下来存档备忘一下世界坐标转为画布坐标。
因为游戏中可能用到多个摄像机,管场景的、管画布的。
所以基本思路是:
- 世界坐标转为场景相机的视口坐标
- 视口坐标与画布尺寸做计算得到屏幕坐标。
二话不说,直接上代码:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class MainTest : MonoBehaviour {
public RectTransform rectCanvas; //画布节点
public Camera worldCamera; //场景相机
public Camera uiCamera; //画布相机
public Transform cube; //测试用的场景对象
public UnityEngine.UI.Image image; //测试用UI图标
private GUIStyle style;
void Start()
{
style = new GUIStyle();
style.fontSize = 24;
style.normal.background = new Texture2D(300,100);
style.normal.textColor = new Color(0.3f,0.3f,0.5f,1f);
}
void OnGUI()
{
//计算场景坐标到画布坐标
if (GUILayout.Button("世界坐标转为画布坐标", style))
{
Vector2 canvasSize = rectCanvas.sizeDelta;
Vector3 viewPortPos3d = worldCamera.WorldToViewportPoint(cube.position);
Vector2 viewPortRelative = new Vector2(viewPortPos3d.x - 0.5f, viewPortPos3d.y - 0.5f);
Vector2 cubeScreenPos = new Vector2(viewPortRelative.x * canvasSize.x, viewPortRelative.y * canvasSize.y);
Debug.LogError("ScrrenSize="+canvasSize
+",cube.position="+cube.position
+",viewPortPos3d="+viewPortPos3d+",screenPos="+cubeScreenPos+",newPos="+viewPortRelative);
image.rectTransform.anchoredPosition = cubeScreenPos;
}
GUILayout.Label("\n");
if (GUILayout.Button("随机修改cube坐标", style))
{
float rate = 5f;
Vector3 newPos = cube.position + new Vector3(UnityEngine.Random.Range(-rate, rate), UnityEngine.Random.Range(-rate, rate), 0);
cube.position = newPos;
}
}
}
最后,补充一点,虽然其他计算方法也很多,但是如果场景相机 和画布相机 的坐标角度什么的不重合的情况下 两个相机同时计算方便的多。
如下图是运行预览:
最后附上资源包地址,哈哈哈我的github:
https://github.com/yuhezhangyanru/UGUIComponents/tree/master/WorldPositiontoScrrenPositionTool