Unity Canvas相关知识学习
文章目录
- Unity Canvas相关知识学习
- 1. Canvas:
- 1.1 Render Mode
- 1.2 多个Canvas的显示顺序
- 2.Canvas Scaler:屏幕分辨率自适应
- 2.1 UI Scale Mode
- 3. EventSystem
- 4. Standalone Input Module
- 5. Graphic Raycaster:图形射线投射器
1. Canvas:
UI元素的容器,合批最小单位,2D模式,3D模式。
1.1 Render Mode
UI 在屏幕上或作为 3D 空间对象进行渲染的方式。
1)Screen Space - Overlay:在此模式下,画布会进行缩放来适应屏幕,然后直接渲染而不参考场景或摄像机(即使场景中根本没有摄像机,也会渲染 UI)。如果更改屏幕的大小或分辨率,则 UI 将自动重新缩放进行适应。UI 将绘制在所有其他图形(例如摄像机视图)上。
- Canvas总是在绘制完其它物体后,最后进行绘制,所以Canvas会覆盖在所有物体之上。
- Canvas的大小和位置无法通过手动设置, 大小只能和屏幕大小一致, 位置总是处于屏幕正中间。
- 根据CanvasScaler组件的设置, 最终确定Canvas的大小,如果没有CanvasScaler,此时Canvas的一个像素等于一个Units。
- 此模式的Canvas节点下的3D物体不会显示。
2)Screen Space - Camera:在此模式下,UI画布会固定在渲染相机前方。通过调整 Plane Distance 来改变画布与相机的距离。此时画布始终会重新缩放来准确适应摄像机视锥体。如果更改屏幕的大小或分辨率或更改摄像机视锥体,则 UI 将自动重新缩放进行适应。场景中比 UI 平面更靠近摄像机的所有 3D 对象都将在 UI 前面渲染,而平面后的对象将被遮挡。
3)World Space:此模式将 UI 视为场景中的平面对象进行渲染。但是,与 Screen Space - Camera 模式不同,该平面不需要面对摄像机,可以任意定向。画布的大小可以使用矩形变换来设置,但画布在屏幕上的大小将取决于摄像机的视角和距离。其他场景对象可以位于画布后面、穿透画布或位于画布前面。
1.2 多个Canvas的显示顺序
- 渲染模式为 Screen Space - Overlay 的始终在最前面。
- SortingLayer越大的显示越靠前。
- SortingLayer相同,SortOrder越大的显示越靠前。
- SortingLayer和SortOrder都相同,Z坐标越小的(距离相机越近)的越靠前。
- Z坐标,SortingLayer和SortOrder都相同,受在Hierarchy窗口中的层级关系影响,层级越靠下显示越靠前。
2.Canvas Scaler:屏幕分辨率自适应
用于控制 Canvas 画布中 UI 元素的整体缩放和像素密度。此缩放会影响画布下的所有内容。
2.1 UI Scale Mode
确定画布中的 UI 元素的缩放方式。
1) Screen Space 模式下
Constant Pixel Size:无论屏幕大小如何,UI 元素都保持相同像素大小。
Scale Factor:按此系数缩放画布中的所有 UI 元素。
Reference Pixels Per Unit:canvas中每一个单位对应的像素数,通常100像素对应Unity中的一个单位。
Scale With Screen Size:根据某个缩放因子,等比缩放画布,Canvas下的UI元素也会受到影响。
Reference Resolution:UI 布局的设计分辨率。如果屏幕分辨率(实际设备分辨率)较大,则 UI 会放大,如果较小,则 UI 会缩小。
Screen Match Mode:屏幕适配模式
- Match Width or Height:以宽度、高度或二者的线性插值作为参考来缩放画布区域。
- Expand:扩展模式,选择宽高比中较小的缩放因子进行缩放。可以显示全部UI,画布中多出来的空白像素用固定颜色填充。
- Shrink:裁剪模式,选择宽高比中较大的缩放因子进行缩放。会有一部分UI被裁剪。
Match:以宽度比、高度比或二者的线性插值作为参考进行缩放。
Reference Pixels Per Unit:每单位像素数。
Constant Physical Size:无论屏幕大小和分辨率如何,UI 元素都保持相同的物理大小。
用于解决不同设备上(DPI不同)同一个UI大小不同的问题。
Physical Unit: 用于指定位置和大小的物理单位。
Fallback Screen DPI:在屏幕 DPI 未知时采用的 DPI。
Default Sprite DPI:用于精灵的每英寸像素,使其“Pixels Per Unit”设置与“Reference Pixels Per Unit”设置匹配。
Reference Pixels Per Unit:如果精灵具有此“Pixels Per Unit”设置,则其 DPI 将与“Default Sprite DPI”设置匹配。
2) World Space 模式下
Dynamic Pixels Per Unit: 用于 UI 中动态创建的位图(如文本)的每单位像素量。
Reference Pixels Per Unit: 每单位像素数。
3. EventSystem
- 负责Tick整个事件系统。
- 负责管理所有的输入事件,并将其分派给正确的GameObject。
- 一个场景中只能有一个EventSystem组件,创建UI时如果没有EventSystem则自动创建一个。
在 Editor 中 EventSystem 对象的 Inspector 窗口可以查看:当前选中对象(Selected),以及鼠标左右键的输入信息(Pointer -1 和 Pointer -2)等信息。
4. Standalone Input Module
- 继承 BaseInputModule。
- 由EventSystem 管理和驱动 。
- 处理不同类型的输入(例如鼠标、触摸屏等)并生成对应的事件 。
InputModule 主要在 Process() 函数中处理用户输入事件。
以 touch 为例:Process主要的工作就是维护 PointerEventData 的数据(点击位置,当前位置,点击时间、上一帧的 delta值等),同时根据 PointerEventData 发出事件(Click、Drag)。
5. Graphic Raycaster:图形射线投射器
- 如果UI需要接受点击事件,需要在UI所在的 Canvas 上添加 GraphicRaycaster 组件。
- 所有可交互UI元素都继承自 UIBehaviour 并勾选 Raycast Target,才能够接收和处理相应类型的输入事件。
- 检测时获取当前射线击中的所有物体,统一进行排序,选择排序后的第一个对象作为射线检测的结果。
- 依赖 RectTranform 的矩形框来进行射线检测, 不需要摄像机。
- 根据Canvas的层级和UI的深度depth进行排序。
// EventSystem.cs
public void RaycastAll(PointerEventData eventData, List<RaycastResult> raycastResults)// s_RaycastComparer 排序方法
private static int RaycastComparer(RaycastResult lhs, RaycastResult rhs)// GraphicRaycaster.cs
public override void Raycast(PointerEventData eventData, List<RaycastResult> resultAppendList)
UGUI事件系统原理:
流程:事件输入–>射线投射–>事件分发
InputModule 获取用户的操作数据,Raycaster 则找到目标对象并通知 EventSystem,最后由EventSystem 发送事件让目标对象进行响应,处理对应的事件。
Unity提供了一系列事件处理接口,它们继承自 IEventSystemHandler 。每次分发事件时查询目标对象上实现了
IEventSystemHandler 接口的所有组件, 然后向这些组件进行消息分发。
UGUI支持的事件:https://docs.unity.cn/cn/current/Manual/SupportedEvents.html
核心源码:ExecuteEvents.cs