Unity3D游戏开发unity3D技术分享征服Unity3d

简易 Unity3D UI 框架

2017-05-19  本文已影响539人  YLME

看见一篇介绍 Unity3D UI 框架编写的文章,并且给出了示例代码。然后去了解了一下。讲道理,示例代码蛮乱的,不知道有一些是不是直接从项目代码拷贝然后简单修改,对于一个简单的框架来说,有很多不必要的混乱逻辑。而且我又喜欢粉色,所以就重新编写了,话不多说先上运行图示。具体代码点这里

运行图示

想了解更多信息具体查看代码。这篇博客主要谈一谈 UI 框架基本的需求。UI 框架有很多实现方式,比如多个界面共用一个摄像机渲染还是单个界面单个摄像机渲染,但是基本的需求是一致的。掌握了基本的需求,才能适应不同项目策划百变的需求。最后需求分析基于手游,界面基于 NGUI

基本情景

UIOper

游戏玩法一般分为 UI 玩法和核心玩法。假设核心玩法是战斗。UI 玩法与核心相互交织连接,比如打开装备界面锻炼装备,这样战斗时就更厉害,还比如打开聊天界面与好友聊天,一起组队打 Boss 。上图是常见的操作之一,总结为两句话:界面之间跳转,界面与战斗跳转,这是最基本的需求情景。

了解了基本情景后来探索更多的细节吧。

界面渲染

渲染是最现实的问题,毕竟界面要先能被看见。新创建一个 Camera 独立负责界面渲染,和主场景和战斗场景渲染独立开来。对于这个只渲染 UI 的 Camera 设置 Camera.cullingMask 指定渲染的 Layer,避免冗余渲染,同样界面(GameObject)的 Layer 也要设置为值才能被显示 。这样当调节战斗场景和主场景摄像机渲染时,UI 不会受到影响,相应的修改 UI Camera 的选项时,也不会影响非 UI 的渲染。

界面跳转与界面层级(depth,深度值)

界面跳转与界面层级是相互关联的。比如某个导航按钮打开一个新的界面,但新的界面层级比较低,这样在重叠区域导航按钮就会遮挡新打开的界面,这不符合实际需求,因此需要合理的管理界面层级,防止出现错误的遮挡。界面跳转涉及多个界面,界面层级涉及到渲染次序进而影响显示顺序,NGUI 中可以用 depth 控制渲染次序,UGUI 又是另一种方式控制渲染次序,这里使用 NGUI 深度值进行描述,目的都是一样的,就是控制渲染秩序。

当游戏界面足够的简单,UI 管理就更简单。如下所示。比如仅仅创建两个 UIPanel,ToolPanel 深度值更大,显示优先级更高,PlayPanel 优先级低一些,用来展示玩法,由于游戏界面很简单,此时完全可以把所有界面都创建好,如 UI1 和 UI2 。比如需要显示 UI2 时,设置 UI1 为 Inactive 然后设置 UI2 为 Active 。通过这种方式,你就可以完成一个超简单的 UI 框架,当然它的功能备受限制,但是对于简单的小游戏来说,也足够了。

UIRoot
    PlayPanel
        UI1
        UI2
    ToolPanel
        Tool

然而很多时候游戏会涉及很多界面。这样就得考虑更灵活的实现方式。

UIRoot
    Panel1
        Panel2
        Panel3

当然若不在乎冗余的 UIRoot 组件,或者想个别界面采用特俗的缩放方式,也可以每个节目单独一个 UIRoot 组件。如下。

UIRoot1
    Panel
UIRoot2
       Panel
UIRoot3
       Panel

这些都是基本的 UI 框架需求。这些需求可以根据项目情况或简单或复杂实现。相信读到这里,你内心也有了一些自己的想法了,是吧。

再进一步,资源,内存,效率

开发

到这一步一个框架就开发出来使用了。在实际项目需求中可能会为了便利性,进一步增加一些通用功能。下面列举一些项目中会实际处理的事情。

下面是前面提到的我重新实现的小框架的例子。例子很简单,就是显示一个界面。在 Awake 中进行初始化处理即可。之后便可以调用 WndMgr.inst.ShowWindow(WndId.shop); 来显示界面。

using UnityEngine;
using TinyWnd;

public class ShopWnd : Wnd
{
    protected override void OnAwake()
    {
        _wndId = WndId.shop;
        _colliderMode = WndColliderMode.transparent;
        _closeClickBg = true;
        _unifiedClose = true;
    }
}

提一点,组件中 AwakeStart 执行顺序,大家都知道。要注意的地方是 AwakeStart 不一定是在同一帧执行。当调用 AddComponent 添加新的组件时,初始化完毕后 Awake 会被调用,而 Start 未被调用。因此组件的一些初始化处理放在 Awake 函数中会更加合适。这样的话,动态添加这个组件后就可以使用了,而不用担心一些初始化操作未被执行。


我的博客地址 https://my.oschina.net/iirecord/blog

上一篇 下一篇

猜你喜欢

热点阅读