Unity里名字牌、血条等头顶挂件的实现

using UnityEngine;using System.Collections;public class Following : MonoBehaviour {public GameObject m_goFollowing = null;public float m_fOffset = 0;private Camera m_go3DCamera = null;private Camera m_go2DCamera = null;void Start(){m_go3DCamera = GameObject.FindWithTag("MainCamera").GetComponent<Camera>();m_go2DCamera = GameObject.Find("UI Root").transform.FindChild("Camera").GetComponent<Camera>();}void Update () {Vector3 vPos = TransPos(m_goFollowing.transform.position + new Vector3(0, m_fOffset, 0));gameObject.transform.position = new Vector3(vPos.x, vPos.y, 0); //get proper z, z = 0.0f simplygameObject.transform.rotation = m_go2DCamera.transform.rotation; //keep the same rotation with camera, so Parallel with camera}//Transform WorldPos in 3DCamera to new WorldPos in 2DCamera. They share the same ScreenPosVector3 TransPos(Vector3 worldpos){if (m_go3DCamera == null || m_go2DCamera == null){return Vector3.zero;}Vector3 screenPos = m_go3DCamera.WorldToScreenPoint(worldpos);Vector3 newWorldPos = m_go2DCamera.ScreenToWorldPoint(screenPos);return newWorldPos;}}

这其中的要点都写在注释里了。

游戏场景一般用3DCamera渲染,名字牌血条等属于UI,应该被UI相机渲染。头顶的名字牌血条要跟随着3D场景里的物体,关键是如何将3D相机空间里的位置映射到UI相机相机空间。中间的桥梁是屏幕位置,两个相机看到的头顶物件应该映射到同一个屏幕坐标。

同时,两个细节需要注意:

1. 为保证UI可见,通过UI相机变换得到的坐标深度要设置为合适的值,太远或太近会出视野范围。可以简单地设置为0。

2. 头顶物件要注意和UI相机保持平行,即头顶物件的rotation设置为UI相机的rotation。

实际应用中,,还有一些性能问题需要注意。

(1)减少DrawCall:

NGUI内置合并DrawCall机制,同一个Panel下,不被打断的depth区间段,使用同样的Material,这些Widget可以被合并为一个DrawCall。

具体而言,使用同样的Atlas的UISprite,挂在同一个UIPanel下的depth区间,此depth区间在此UIPanel下不被其他的Atlas使用。UILabel也针对每种字体分配一个Depth区间。 当然,前提是不影响功能需求。

以头顶的名字条NameBar、血条HPBar为例,NameBar.prefab, HPBar.prefab本身不要带有UIPanel,我们为头戴物件在NGUI-UIRoot下创建一个共同的UIPanel–HeadWearingPanel,所有实例化的NameBar、HPBar都挂在HeadWearingPanel下。

另外,NGUI3.8.0之前的版本,显示/隐藏UIWdget会导致所有UIDrawCall的销毁重建,对CPU负荷较大。如果用NGUI3.8.0之前的版本,建议不要直接用gameObejct.SetActive(false)来实现UI控件的隐藏,可以令transform.scale = Vector3.zero, 或者将欲隐藏的UI移到视野外。NGUI3.8.0的版本没有这个问题了。

(2)减少GC

对于要频繁创建销毁的UI,做一个资源池。避免频繁创建销毁对象带来的大量gc。

针对每种类型的Prefab创建一个Pool.删除NameBar、HPBar时,并不真正Destroy,将之隐藏即可。常见NameBar、HPBar时,先从Pool里查找是否有可用的NameBar、HPBar,若没有找到才真正实例化创建新对象。

微笑的去寻找一个不可能出现的你。

Unity里名字牌、血条等头顶挂件的实现

相关文章:

你感兴趣的文章:

标签云: