1,基本数据结构
UIPanel
基本的UI容器单位,保存相关显示信息数据,主要更新通过LateUpdate来处理相关变化更新。主要数据包含:widgets,当前Panel的widgets;drawCalls当前Panel的渲染信息
UIWidgets
以List的形式记录在UIPanel,每次widgets列表发生变化时(即有添加删除操作,隐藏显示也会触发),必然导致整个Panel的重建。
UIGeometry
每个Widget中的图形信息,包含顶点,UV,以及颜色信息。其中verts时原始顶点信息,mRtpVerts是相对于Panel的顶点信息。
UIDrawCall
渲染相关信息,可通过打开文件中 SHOW_HIDDEN_OBJECTS的宏,在编辑器Hierarchy中看到实际生成的Mesh信息。以List的形式记录在UIPanel, 每一次DrawCall的重建,会从当前DC中的对应的Widgets中收集所有的mRtpVerts的信息,用于填充生成的Mesh。
2,重要方法
UIPanel::LateUpdate 根据静态变量mUpdateFrame来更新所有的Panel。
UIPanel::UpdateSelf 更新当前Panel相关信息。
UIPanel::UpdateWidgets 更新所有的Widget(通过调用UIWidget::UpdateTransform, UIWidget::UpdateVisibility, UIWidget::UpdateGeometry)。
UIPanel::FillAllDrawCalls 清除所有drawCall信息,重新根据所有的widgets来重建drawcall信息(重新填充顶点,重新创建material等),最重量级的操作。
UIPanel::FillDrawCall(UIDrawCall dc, bool needsCulling) 单独更新某个drawCall。
UIWidget::UpdateTransform 会更新当前panel的worldToLocal矩阵来计算当前widget的左下和右上两个顶点(mOldV0,mOldV1),每次当transform发生变化时,计算新的左下右上,如果距离的平方大于0.000001f时,修改mMoved变量为true,用于更新Geometry相关信息。
UIWidget::UpdateGeometry 当mMoved为true时,通过UIWidget::ApplyTransform来更新mRtpVerts的信息。
3,使用中注意的重点问题
UIPanel
每一帧会更新相关裁剪区域相关的信息, 更新每一个UIDrawCall中的信息(包含cachedTransform) ,以及更新所有的Widget信息。当Panel的Transform发生变化时,会影响到每一个widget的显示等相关信息。
当Panel的OnEnable调用时,会触发Rebuild操作,所以频繁隐藏显示某个界面最好的方法是将其位置移动到摄像机外或者切换相关layer避开UI摄像机。
当移除某个widget时,如果这个widget正好跟所在UIDrawCall的depthStart和depthEnd相等时,会可能影响UIDrawCall的合并,所以也会触发Rebuild,否则只会更新这个DC。
当添加某个widget时,如果这个widget能添加到某个UIDrawCall,会将这个DC设置为Dirty,只更新这个DC即可,如果不能,则会触发Rebuild。(FindDrawCall)
UIWidget
当某个widget的tranform发生变化的时候,如果这一帧不用重建整个panel,就会将widget对应的UIDrawCall设置为isDirty,然后在UIPanel的UpdateSelf中通过FillDrawCall更新当前UIDrawCall的mesh信息。
设置widget的Depth时,会先将widget从panel中移除,然后再次重新添加到panel中。
隐藏widget,改变材质,以及父节点发生变化时引起自己的panel发生变化时等操作(不同widget可能会有不同的触发原因,检查RemoveFromPanel调用的时机)会触发RemoveFromPanel的操作。
Shader中后面带数字的,是根据UIPanel中的clipCount裁剪的数量来选择的。
v.vertex记录的 中心点在屏幕的的widget是个坐标点的坐标,localposition的大小的一半。
_ClipRange的数据,xy记录裁剪位置的偏移(通过center + offset 计算得来),z记录了 1 / range的宽的一半,w记录了 1 / range的高的一半。中心点在正中间
_ClipArge的数据,xy记录的 range.zw / soft.xy 的数据 用于shader的计算