原文:http://gad.qq.com/article/detail/26562
UGUI在CPU上的性能开销高主要原因之一是Canvs对UI网格的重建,有很多情况会触发Canvas对网格的重建,例如Image,Text等UI元素的Enable及UI元素的长、宽或Color属性的变化等。
Canvas中UI Mesh顶点较多的话,则该项将会出现较高的CPU开销,在Unity的Profiler中则对应的是Canvas.SendWillRenderCanvases或Canvas.BuildBatch占用过多的时间。Canvas.BuildBatch主要功能是合并Canvas节点下所有UI元素的网格,合并后的网格会缓存起来,只有其下面的UI元素的网格发生改变时才会重新合并。UI元素的网格变化主要是Canvas.SendWillRenderCanvases调用时,rebuild了Layout或者graphic。
该函数的调用过程时序图如下:
1:该过程由CanvasUpdateRegistry监听Canvas的WillRenderCanvases(上图中1)而执行,主要是对前标记为dirty的layout和graphic执行rebuild。引起layout和graphic的dirty主要原因是因为Canvas树形结构下的UI元素发生了变化(例如增加删除UI对象,UI元素的顶点,rec尺寸改变等)调用了Graphic.SetDirty(实际上最终都会调用CanvasUpdateRegistry.RegisterCanvasElementForLayoutRebuild)。
2:在rebuild layout之前会对Layout rebuild queue中的元素依据它们在heiarchy中的层次深度进行排序(上图中的2),排列的结果是越靠近根的节点越会被优先处理。
3:rebuild layout(上图中的3),主要是执行ILayoutElement和ILayoutController接口中的方法来计算位置,Rect的大小等布局信息。
4:rebulid graphic(上图中的4),主要是调用UpdateGeometry重建网格的顶点数据(上图中5)以及调用UpdateMeterial更新CanvasRender的材质信息(上图中6)。