Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. We have updated the language to the Editor Terms based on feedback from our employees and community. Learn more.
    Dismiss Notice

Draw Unity GL under UI

Discussion in 'UI Toolkit' started by micdolinski, Jun 18, 2020.

  1. micdolinski

    micdolinski

    Joined:
    Feb 16, 2019
    Posts:
    4
    Hello,

    I can't figure out how, or even if, it is possible to draw something under UI elements using GL API. Say there will be some lines, triangles and I'd like some text over it.
    As a background I am trying to build simple plotting app, Unity GL API makes possible drawing thousands of lines with reasonable FPS.

    Here's a dummy image example:
    upload_2020-6-18_16-20-27.png
     
  2. stan-osipov

    stan-osipov

    Unity Technologies

    Joined:
    Feb 24, 2020
    Posts:
    31
  3. uMathieu

    uMathieu

    Unity Technologies

    Joined:
    Jun 6, 2017
    Posts:
    386
    Using the onGenerateUIContent delegate, you can generate geometry that will be used later when rendering. This has the benefit of allowing batches and reducing drawcalls.

    Documentation is a bit lacking at the moment, but here is a sample:
    Code (CSharp):
    1. class SolidQuad : VisualElement
    2.         {
    3.             public SolidQuad() { generateVisualContent += OnGenerateVisualContent; }
    4.  
    5.             static readonly Vertex[] k_Vertices = new Vertex[4];
    6.             static readonly ushort[] k_Indices = { 0, 1, 2, 2, 3, 0 };
    7.  
    8.             void OnGenerateVisualContent(MeshGenerationContext mgc)
    9.             {
    10.                 Rect r = contentRect;
    11.                 if (r.width < 0.01f || r.height < 0.01f)
    12.                     return; // Skip rendering when too small.
    13.  
    14.                 Color color = resolvedStyle.color;
    15.                 k_Vertices[0].tint = Color.black;
    16.                 k_Vertices[1].tint = Color.black;
    17.                 k_Vertices[2].tint = color;
    18.                 k_Vertices[3].tint = color;
    19.  
    20.                 float left = 0;
    21.                 float right = r.width;
    22.                 float top = 0;
    23.                 float bottom = r.height;
    24.  
    25.                 k_Vertices[0].position = new Vector3(left, bottom, Vertex.nearZ);
    26.                 k_Vertices[1].position = new Vector3(left, top, Vertex.nearZ);
    27.                 k_Vertices[2].position = new Vector3(right, top, Vertex.nearZ);
    28.                 k_Vertices[3].position = new Vector3(right, bottom, Vertex.nearZ);
    29.  
    30.                 MeshWriteData mwd = mgc.Allocate(k_Vertices.Length, k_Indices.Length);
    31.                 mwd.SetAllVertices(k_Vertices);
    32.                 mwd.SetAllIndices(k_Indices);
    33.             }
    34.         }
     
  4. pawelduda

    pawelduda

    Joined:
    Feb 1, 2019
    Posts:
    45
    @uMathieu I tried using this method but with a Label. But this way I see only the gradient, I don't see the text. Is there a way around it?
     
  5. uMathieu

    uMathieu

    Unity Technologies

    Joined:
    Jun 6, 2017
    Posts:
    386
    Nexer8 likes this.
  6. pawelduda

    pawelduda

    Joined:
    Feb 1, 2019
    Posts:
    45
    @uMathieu Ok, thx for reply. We decided to alter delegates order during construction:

    Code (CSharp):
    1. var oldDelegates = generateVisualContent.GetInvocationList();
    2. generateVisualContent += OnGenerateVisualContent;
    3. foreach (var oldDelegate in oldDelegates) {
    4.   generateVisualContent -= (Action<MeshGenerationContext>) oldDelegate;
    5.   generateVisualContent += (Action<MeshGenerationContext>) oldDelegate;
    6. }
     
    Nexer8 likes this.