您当前的位置: 首页 >  游戏

野奔在山外的猫

暂无认证

  • 4浏览

    0关注

    85博文

    0收益

  • 0浏览

    0点赞

    0打赏

    0留言

私信
关注
热门博文

【Unity 笔记】适合小型游戏的UI框架

野奔在山外的猫 发布时间:2021-05-29 17:06:14 ,浏览量:4

程序语言:C# 开发平台:Visual Studio 2019 游戏引擎:Unity 版本:2019.4.6f1 【2017版本以上均可】

一、什么是UI?

答:UI设计(或称界面设计)是指对软件的人机交互、操作逻辑、界面美观的整体设计。  

二、了解小型游戏的UI框架

在这里插入图片描述

  • UIWindow:封装UI界面的访问方式
  • UIEventListener:事件响应监听器
  • UIController:UI行为的管理
  • UIManager:管理UI的初始状态及提供查询指定UI的方法等

三、UIEventListener 事件监听

UI交互行为作为重要的环节,常以多样化操作提高用户交互体验,而如何选择响应方式,如按下时反馈、松手时反馈等,需要开发者手动调整。因而便利化代码操作以更灵活处理多种交互行为:

using UnityEngine;
using UnityEngine.EventSystems;

namespace UI.Framework
{
    public delegate void PointerHandler(PointerEventData data);

    /// 
    /// UI 事件监听器
    /// 
    public class UIEventListener : MonoBehaviour, IPointerClickHandler, IPointerEnterHandler, IPointerExitHandler, IPointerDownHandler, IPointerUpHandler
    {
        public event PointerHandler Click;
        public event PointerHandler Enter;
        public event PointerHandler Exit;
        public event PointerHandler Down;
        public event PointerHandler Up;

        /// 
        /// 点击
        /// 
        /// 
        public void OnPointerClick(PointerEventData eventData)
        {
            Click?.Invoke(eventData);
        }

        /// 
        /// 点下
        /// 
        /// 
        public void OnPointerDown(PointerEventData eventData)
        {
            Down?.Invoke(eventData);
        }

        /// 
        /// 进入
        /// 
        /// 
        public void OnPointerEnter(PointerEventData eventData)
        {
            Enter?.Invoke(eventData);
        }

        /// 
        /// 离开
        /// 
        /// 
        public void OnPointerExit(PointerEventData eventData)
        {
            Exit?.Invoke(eventData);
        }

        /// 
        /// 松键
        /// 
        /// 
        public void OnPointerUp(PointerEventData eventData)
        {
            Up?.Invoke(eventData);
        }
    }
}`
3.1 引用命名空间
using UnityEngine;
using UnityEngine.EventSystems;
  • UnityEngine:Unity提供的扩展程序,此处引用为继承MonoBehaviour允许挂载到场景物体上
  • UnityEngine.EventSystem:Unity事件系统,此处为实现其提供的多种交互接口,以灵活化交互方式的使用
3.2 事件行为的声明
public event PointerHandler Click;
public event PointerHandler Enter;
public event PointerHandler Exit;
public event PointerHandler Down;
public event PointerHandler Up;
  • event
3.3 接口实现

使用接口实现操作方法,如下为使用点击事件接口实现点击事件行为。

public void OnPointerClick(PointerEventData eventData)
{
     Click?.Invoke(eventData);
}
  • OnPointerClick():由IPointClickHandler提供的实现方法,指点击行为的方法均为此
  • Click:指点击行为事件
  • Click?.Invoke(eventData):判断当前点击行为,如果是执行点击的对应事件

四、UIWindow 视图交互行为

挂载于UI窗口。用于提供给UI窗口的显隐方式,如[立即显隐],[延迟显隐],[渐变显隐]等。

using System.Collections;
using UnityEngine;
using Tool;

namespace UI.Framework
{
    /// 
    /// UI 窗口显隐效果【挂载于指定显隐窗口上】
    /// 
    [RequireComponent(typeof(CanvasGroup))]
    public class UIWindow : MonoBehaviour
    {
        //CanvasGroup提供透明度更变显隐(性能上最优)
        private CanvasGroup group;

        protected void Awake()
        {
            group = GetComponent();
        }

        //立即显隐
        private void SetVisibleInstantly(bool state)
        {
            group.alpha = state ? 1 : 0;
            group.blocksRaycasts = state;
        }

        /// 
        /// 设置可见性
        /// 
        /// 是否可见
        /// 延迟时间,默认为0
        public void SetVisible(bool state, float delay = 0)
        {
            StartCoroutine(SetVisibleDelay(state, delay));
        }

        /// 
        /// 延时显隐
        /// 
        /// 是否可见
        /// 延迟时间
        /// 
        private IEnumerator SetVisibleDelay(bool state, float delay)
        {
            yield return new WaitForSeconds(delay);
            SetVisibleInstantly(state);
        }

        /// 
        /// 获取监听器
        /// 
        /// 
        /// 
        public UIEventListener GetListener(string childName)
        {
            Transform childTF = transform.FindChildTF(childName);
            if (childTF == null) return null;
            UIEventListener listener = childTF.GetComponent();
            if (listener == null) listener = childTF.gameObject.AddComponent();
            return listener;
        }
    }
}
4.1 引用命名空间
using System.Collections;
using UnityEngine;
using Tool;
  • System.Colletion:Biu La Biu La~
  • UnityEngine:同3.1描述
  • Tool:第三方工具,由作者自己准备的工具包,后续会说及此工具包内容
4.2 需求组件
[RequireComponent(typeof(CanvasGroup))]
  • 当脚本所挂载的物体上查无该组件对象时,控制台会提示需要添加该组件。如图示为CanvaGroup组件
  • 我们也可使用[AddComponent(typeof(CanvasGroup))],当物体没有该组件直接添加该组件
4.3 CanvasGroup 画布组
private CanvasGroup group;
  • 常见的UI交互,即UI的显隐,在游戏多未激活或禁用、创建或销毁。对小型主界面的游戏,不需要过于复杂的交互行为逻辑,我们选择CanvasGroup组件改变 0~1 透明度来实现UI的隐藏。
  • 使用CanvasGroup组件仅从更变显隐状态上比SetActive()的性能开支更优。
4.4 组件的获取
protected void Awake()
{
     group = GetComponent();
}
  • 使用组件的功能,必然少不了对组件对象的获取
4.5 Canvas显隐行为
private void SetVisibleInstantly(bool state)
{
     group.alpha = state ? 1 : 0;
     group.blocksRaycasts = state;
}
  • SetVisibleInstantly():即时显隐,我们通过改变画布的alpha透明度实现这以行为。
  • blockRagtCastes:决定该CanvasGroup组件是否接口射线检测 射线检测来自于我们的鼠标Click等行为
private IEnumerator SetVisibleDelay(bool state, float delay)
{
     yield return new WaitForSeconds(delay);
     SetVisibleInstantly(state);
}
  • 需求总是复杂多样,唉,我想要延迟执行UI的显隐。
  • IEnumerator:协程,允许程序暂缓一时间后执行。 这里是延时调用SetVisibleInstantly()方法
public void SetVisible(bool state, float delay = 0)
{
     StartCoroutine(SetVisibleDelay(state, delay));
}
  • SetVisible():封装 直接显隐 与 延时显隐 的方法 记忆方法名,调用总是麻烦的,就不能使用一个函数方法实现多种效果。
  • 你也可以使用方法 重载 来实现。
4.6 事件监听者
public UIEventListener GetListener(string childName)
{
     Transform childTF = transform.FindChildTF(childName);
     if (childTF == null) return null;
     UIEventListener listener = childTF.GetComponent();
     if (listener == null) listener = childTF.gameObject.AddComponent();
     
     return listener;
}
  • 作为UI行为的事件监听器,他需要监听来自UIController的消息通知,来进一步实现要求的显隐方法。
  • transfrom.FindChild():来自于using Tool(自己准备的工具类命名空间)。其目的是查询当前脚本上挂载的物体上的 事件监听组件。 Unity仅为我们提供查询等方法,但并未根据具体实际需求提供更多的方法。如何灵活的使用这些方法并封装成一个便利工具是开发者必备的小技能。
  • childTF == null:说明场景内并无命名 childName参数 的UI对象。 我们也可以适当添加方法在控制台Debug告诉我们并无此对象。
  • listener == null:即查找到的UI对象上,发现脚没有 事件监听组件。给它添加一个就完事了。
  • return listener:我们最终只为获取 事件监听组件对象,返回它。  
五、UIManager 视图映射与索引

用于管理所有UI状态的综合管理器,主要用于控制进入游戏后呈现的UI状态。即隐藏主菜单外的所有UI界面。

using System.Collections.Generic;
using Tool;
using UnityEngine;

namespace UI.Framework
{
    /// 
    /// UI 管理器
    /// 
    public class UIManager : GetInstance
    {
        // 例如:游戏一开始隐藏所有UI


        private Dictionary cache;

        /// 
        /// 保护级 防父类覆盖
        /// 
        protected override void Init()
        {
            base.Init();

            cache = new Dictionary();
            //查询 UIWindow组件 的物体
            UIWindow[] ui = FindObjectsOfType();
            //设置 隐藏
            for (int i = 0; i             
关注
打赏
1659777066
查看更多评论
0.0489s