【Unity UGUI】Unity UGUI源码分析 Mask和RectMask2D分析和性能对比

一.前言

在Unity UGUI的性能优化中经常能看见,使用RectMask2D替换Mask,因为Mask会产生额外的Drwcall,而RectMask2D不会产生额外的Drwcall。但是RectMask2D的性能一定比Mask好吗?

二.Mask源码分析

public class Mask : UIBehaviour, ICanvasRaycastFilter, IMaterialModifier

Mask代码在190行左右。
Mask本身不具有绘制属性不继承Graphic,必须依赖带有Graphic的组件,节点如果没有如Image Text等组件Mask无法添加。
ICanvasRaycastFilter是表明Mask是射线可以投射的目标,ScreenPointToWorldPointInRectangle就是根据摄像机的位置和屏幕位置创建射线,根据RectTransform创建Plane,调用Plane.Raycast检测PM2.5与射线是否相交。

public static bool ScreenPointToWorldPointInRectangle(
      RectTransform rect,
      Vector2 screenPoint,
      Camera cam,
      out Vector3 worldPoint)
    {
   
    
    
      worldPoint = (Vector3) Vector2.zero;
      Ray ray = RectTransformUtility.ScreenPointToRay(cam, screenPoint);
      Plane plane = new Plane(rect.rotation * Vector3.back, rect.position);
      float enter = 0.0f;
      if ((double) Vector3.Dot(Vector3.Normalize(rect.position - ray.origin), plane.normal) != 0.0 && !plane.Raycast(ray, out enter))
        return false;
      worldPoint = ray.GetPoint(enter);
      return true;
    }

IMaterialModifier,得到修改的材质,在Canvas重绘时,如果Material是dirty会调用此方法更新材质,Mask实现的重点在GetModifiedMaterial上

Material GetModifiedMaterial(Material baseMaterial)

MaskEnabled()在获取材质之前确保物体active,有graphic渲染组件
FindRootSortOverrideCanvas找到节点上面最近是overrideSorting覆盖排序的的Canvas

public virtual Material GetModifiedMaterial(Material baseMaterial)
{
   
    
    
    if (!MaskEnabled())//MaskEnabled() { return IsActive() && graphic != null; }
        return baseMaterial;

    var rootSortCanvas = MaskUtilities.FindRootSortOverrideCanvas(transform);
    var stencilDepth = MaskUtilities.GetStencilDepth(transform, rootSortCanvas);
    if (stencilDepth >= 8)
    {
   
    
    
        Debug.LogWarning("Attempting to use a stencil mask with depth > 8", gameObje

猜你喜欢

转载自blog.csdn.net/qq_58047420/article/details/139908956
今日推荐