1、思路:

  (1)信息数据:需要展示属性信息

  (2)信息的展示:负责显示UI属性信息

  (3)UI的跟随:负责实现UI对人物的跟随

  (4)UI的管理:负责对UI进行创建于回收,游戏中需要用到UI的地方都是与该脚本的交互。

2、将需要用到的UI资源打到一个图集中,以免出现大量人物的时候图集穿插造成不良的影响。

3、创建一个头顶UI预设,当道对应的目录下面:

为了测试的方便,在Resources下面也放一个做好的UI预设:

需要注意的是,做的这个预设是不带Panel的,因为希望可以把游戏展示的所有人物头顶UI信息放到同一个Panel下管理。

4、创建一个Panel,用来管理头顶的UI信息:

5、UI跟随脚本:

using UnityEngine;

/// <summary>
/// 2DUI跟随3D物体
/// </summary>
public class UIFollow3DPosition : MonoBehaviour
{
public Transform targetTrans; //2DUI需要跟随的3D目标
public Camera targetCa; //照射的3D目标的摄像机
public Vector3 offsetPos; //2DUI需要在3D目标点的基础上做出的偏移量
public float dis; //3D目标点与摄像机之间的距离,为了实现:3D目标点摄像机机发生变化的时候2DUI也跟随发生变化
public float ratio; //2DUI的缩放比例 [HideInInspector]
public bool isAutoScale = false; //控制2DUI是否发生缩放 public const float FarDistance = 40f; //3D目标点与摄像机的最大距离
public const float NearDistance = 6.5f; //3D目标点与摄像机的最小距离
public static Vector3 MaxScale = Vector3.one;
public static Vector3 MinScale = new Vector3(0.5f, 0.5f, 0.5f); private Camera uiCa; //NGUI摄像机
Transform selfTrans; //2DUI,因为该脚本是挂在2DUI上的
GameObject selfObj; //2DUI
Vector3 screenPos; //2DUI的屏幕坐标
Vector3 curPos; //2DUI的世界坐标
Vector3 backPos = new Vector3(, , ); public Transform cachedTransform
{
get
{
if (trans == null)
trans = transform;
return trans;
}
}
private Transform trans; void Awake()
{
selfTrans = transform;
selfObj = gameObject;
uiCa = UICamera.first.cachedCamera;
}
public void QuickUpdate()
{
LateUpdate();
}
void LateUpdate()
{
if (targetTrans != null && targetCa != null)
{
screenPos = targetCa.WorldToScreenPoint(targetTrans.position + offsetPos);
if(screenPos.z < )
{
selfTrans.localPosition = backPos;
}
else
{
curPos = uiCa.ScreenToWorldPoint(screenPos);
curPos.z = ;
selfTrans.position = curPos;
}
if(isAutoScale)
{
dis = Vector3.Distance(targetTrans.position, targetCa.transform.position);
ratio = Mathf.Clamp01((dis - NearDistance) / (FarDistance - NearDistance));
cachedTransform.localScale = Vector3.Lerp(MaxScale, MinScale, ratio);
}
}
}
}

6、数据及展示的实现:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using UnityEngine; namespace Module.UI
{
//头顶显示需要用到的是数据
public class CharacterTopParam
{
public int level;
public string name; public CharacterTopParam(int level, string name)
{
this.level = level;
this.name = name;
}
} public class UI_Character_TopUI : MonoBehaviour
{
[SerializeField]
UILabel lblInfo; GameObject obj = null;
public GameObject cachedGameObjec
{
get
{
if (null == obj)
obj = gameObject;
return obj;
}
} UIFollow3DPosition followPos = null;
public UIFollow3DPosition FollowPos
{
get
{
if (null == followPos)
{
followPos = cachedGameObjec.GetComponent<UIFollow3DPosition>();
followPos.isAutoScale = true;
}
return followPos;
}
} public void Show(CharacterTopParam param)
{
if (null != param)
{
lblInfo.text = string.Format("LV.{0} Name.{1}", param.level, param.name);
cachedGameObjec.SetActive(true);
}
} public void Hide()
{
cachedGameObjec.SetActive(false);
} }
}

7、将以上两个脚本挂载到做好的UI预设上,并进行相应的设置:

8、UI管理脚本的实现:

using System.Collections;
using System.Collections.Generic;
using UnityEngine; namespace Module.UI
{
public class BillboardUIManager
{
static BillboardUIManager billboardMgr = null;
public static BillboardUIManager BillboardMgr
{
get
{
if (null == billboardMgr)
billboardMgr = new BillboardUIManager();
return billboardMgr;
}
} Transform childParent; public BillboardUIManager()
{
GameObject go = GameObject.Find("UI Root/BillboardPanel");
childParent = NGUITools.AddChild(go).transform;
} public void Destroy()
{
GameObject.Destroy(childParent.gameObject);
} public void SetParentRootActive(bool active)
{
childParent.gameObject.SetActive(active);
} Queue<UI_Character_TopUI> queueCharacterTopUI = new Queue<UI_Character_TopUI>();
public UI_Character_TopUI GetCharacterTopUI(Transform target, Camera cam)
{
UI_Character_TopUI topUI = null;
if (queueCharacterTopUI.Count <= )
{
Object go = Resources.Load("ui_character_top");
if (go)
{
GameObject prefab = GameObject.Instantiate(go) as GameObject;
prefab.transform.parent = childParent;
prefab.transform.localPosition = Vector3.zero;
prefab.transform.localRotation = Quaternion.identity;
prefab.transform.localScale = Vector3.one;
NGUITools.SetLayer(prefab, childParent.gameObject.layer);
topUI = prefab.GetComponent<UI_Character_TopUI>();
}
}
else
{
topUI = queueCharacterTopUI.Dequeue();
} topUI.FollowPos.targetTrans = target;
topUI.FollowPos.targetCa = cam;
topUI.FollowPos.offsetPos = new Vector3(, , ); return topUI;
} void RecycleCharacterUI(UI_Character_TopUI topUI)
{
if (null != topUI)
{
topUI.Hide();
queueCharacterTopUI.Enqueue(topUI);
}
}
}
}

9,以上就是全部的核心逻辑,下面是调用逻辑:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using Module.UI; public class CubeCtrl : MonoBehaviour
{
[SerializeField]
Camera targetCam; float speed = 20.0f; Transform trans = null;
public Transform Trans
{
get
{
if (null == trans)
trans = transform;
return trans;
}
} //Show UI Info
UI_Character_TopUI characterTopUI = null;
public UI_Character_TopUI CharacterTopUI
{
get
{
if (null == characterTopUI)
characterTopUI = BillboardUIManager.BillboardMgr.GetCharacterTopUI(Trans, targetCam);
return characterTopUI;
}
} void Start()
{
Trans.transform.rotation = Quaternion.identity;
CharacterTopParam param = new CharacterTopParam(, "我是方的");
CharacterTopUI.Show(param);
} void Update()
{
if (Input.GetKey(KeyCode.A))
{
Trans.Translate(-Time.deltaTime * speed, , );
}
else if (Input.GetKey(KeyCode.D))
{
Trans.Translate(Time.deltaTime * speed, , );
}
else if (Input.GetKey(KeyCode.W))
{
Trans.Translate(, , Time.deltaTime * speed);
}
else if (Input.GetKey(KeyCode.S))
{
Trans.Translate(, , -Time.deltaTime * speed);
}
}
}

10、项目运行前后的效果对比图:

         

11、项目运行时候的结构:

Unity + NGUI 实现人物头顶UI的信息展示的更多相关文章

  1. Unity NGUI 网络斗地主 -界面制作

    Unity NGUI 网络斗地主 -界面制作 源文件在群(63438968群共享!) @灰太龙 这一节说一下NGUI的界面摆放,并且教会大家使用NGUI的自适应功能! 在这里感谢@Gamer,是他给我 ...

  2. Unity NGUI实现Tabview

    unity版本:4.5.1 NGUI版本:3.5 参考链接:http://blog.csdn.net/g__dragon/article/details/17242969,作者:CSDN G_Drag ...

  3. BMFont中文字体图集制作的方法~(for unity ngui)

    BMFont中文字体图集制作的方法~(for unity ngui) 好吧~似乎这个问题困扰了很多人,游戏开始中文化是个不错的事儿啊,这里我就做下说明,如何制作中文字体图集~ 这里的字库图集的制作更多 ...

  4. Unity NGUI 粒子的排序

    Unity NGUI系统中是没有对粒子进行排序的,如: 怎么解决这个问题呢? 思路是把粒子的渲染层级,相对于UI组件的层级进行一个偏移. 解决后的效果如下: 代码如下: using System.Co ...

  5. unity NGUI点击消息不传入到场景中去

    unity NGUI点击消息不传入到场景中去 1.今天遇到的问题是点击NGUI的按钮,场景中也相应了这个消息 解决的办法是在场景中需要互动的时候,也就是在update中进行判断 是否是点击了NGUI按 ...

  6. Unity NGUI 网络斗地主 -发牌 脚本交互

    Unity NGUI 网络斗地主 -发牌 脚本交互 @By 灰太龙 Unity4.2.1f4 NGUI 3.0.4 本篇说的问题是脚本与控件的交互! 现在对界面进行了改进,先看副图! 1.制作发牌效果 ...

  7. Unity NGUI 网络斗地主 -制作图集 Atlas

    Unity NGUI 网络斗地主 -制作图集 Atlas by @杨海龙 开发环境   Win7+Unity4.2.1f4+NGUI 3.0.4版本 这一节告诉大家如何制作(图集)Atlas! 1.首 ...

  8. Unity NGUI 3.0.4版本 制作网络版斗地主

    Unity NGUI 3.0.4版本 @by 灰太龙  开发环境 Win7旗舰版 Unity 4.2.1f4 本文就写个开门篇,告诉大家怎么用NGUI,第一步导入NGUI 3.0.4版本! 1.启动U ...

  9. Unity里的人物驱动/换装备/换武器/换衣服/卡通重定位(转)

    Unity里的人物驱动/换装备/换武器/换衣服/动画重定位 刚学的过程被这个问题困扰最多. 首先,基本的,大家都知道驱动人物需要骨架.绑骨的Mesh和动画(这三个要是不知道的话就得考虑看看计算机图形学 ...

随机推荐

  1. Scrapy是什么

    1.Scrapy是蜘蛛爬虫框架,我们用蜘蛛来获取互联网上的各种信息,然后再对这些信息进行数据分析处理. 2.Scrapy的组成 引擎:处理整个系统的数据流处理,出发事务 调度器: 接受引擎发过来的请求 ...

  2. mysql事务(一)——redo log与undo log

    数据事务 即支持ACID四大特性. A:atomicity          原子性——事务中所有操作要么全部执行成功,要么全部执行失败,回滚到初始状态 C:consistency     一致性—— ...

  3. python之路----黏包的解决方案

    黏包的解决方案 远程执行命令 # server 下发命令 给client import socket sk = socket.socket() sk.bind(('127.0.0.1',8080)) ...

  4. python之路----面向对象进阶一

    一.isinstance和issubclass isinstance(obj,cls)检查是否obj是否是类 cls 的对象 class Foo(object): pass obj = Foo() i ...

  5. 开源|如何使用CNN将视频从2D到3D进行自动转换(附源代码)

    http://www.sohu.com/a/128924237_642762 全球人工智能 文章来源:GitHub 作者:Eric Junyuan Xie 它是如何运行的? 在运行代码之前,请先根据官 ...

  6. Python Web学习笔记之Python多线程基础

    多线程理解 多线程是多个任务同时运行的一种方式.比如一个循环中,每个循环看做一个任务,我们希望第一次循环运行还没结束时,就可以开始第二次循环,用这种方式来节省时间. python中这种同时运行的目的是 ...

  7. 20145105 《Java程序设计》实验三总结

    实验三 一.       实验内容 结对修改实验一代码,重点学习重构 二.       实验步骤 下载结伴同学的实验一代码 初始代码 进行整数.小数和负数的多组数据测试,发现一个运行错误的例子 分析后 ...

  8. 20145127《java程序设计》第六周学习总结

    教材学习内容总结 第十章 输入与输出 文件的读写 网络上传数据的基础 10.1 InputStream与OutputStream 流(Stream)是对「输入输出」的抽象,注意「输入输出」是相对程序而 ...

  9. SVC(STM32)

    这两个都是 system level service,有什么区别呢?…… 手册上说 SVC 这个指令是同步的,而 PendSV 是异步的,请问是什么意思呢?…… 高手路过尽请留言啊

  10. Python3基础 map+lambda 将指定系列元素乘2

             Python : 3.7.0          OS : Ubuntu 18.04.1 LTS         IDE : PyCharm 2018.2.4       Conda ...