How to draw line smooth in unity (c# base coding problem)

末鹿安然 提交于 2021-01-29 17:23:51

问题


I want to draw line from unityUI. (i dont want to use Line Renderer in unity).

So I figured out the coding below, but my problem is the line sizes are not constant.

public class MyUILineRenderer : Graphic
{
    public Vector2[] pointPos;
    public float[] angles;
    public MyUIGridRenderer gridRenderer;

    public Vector2Int gridSize = new Vector2Int(1, 1);
    public float lineThickness = 0.5f;
    public float width;
    public float height;
    public float unitWidth;
    public float unitHeight;

    public float angleHelp;
    public bool calAngle;

    public Color[] colors;

    protected override void OnPopulateMesh(VertexHelper vh)
    {
        vh.Clear();
        width = rectTransform.rect.width;
        height = rectTransform.rect.height;

        unitWidth = width / (float)gridSize.x;
        unitHeight = height / (float)gridSize.y;
        if (calAngle)
        {
            angles = new float[pointPos.Length];
        }

        if (pointPos.Length < 2)
        {
            return;
        }

        float angle = 0;

        for (int i = 0; i < pointPos.Length; i++)
        {
            Vector2 point = pointPos[i];

            if (i < pointPos.Length - 1)
            {
                if (calAngle)
                {
                    angle = angles[i] = -GetAngle(pointPos[i], pointPos[i + 1]) + angleHelp;
                }
                else
                {
                    angle = angles[i];
                }
            }
            DrawLine(vh, point, angle);
        }

        int count = pointPos.Length * 2 - 2;
        for (int i = 0; i < count; i += 2)
        {
            vh.AddTriangle(i + 0, i + 1, i + 3);
            vh.AddTriangle(i + 0, i + 2, i + 3);
        }
    }

    public float GetAngle(Vector2 currentPos, Vector2 targetPos) {
        return (float)(Mathf.Atan2(targetPos.y - currentPos.y, targetPos.x - currentPos.x) * (180 / Mathf.PI));
    }

    private void DrawLine(VertexHelper vh, Vector2 point, float angle)
    {
        UIVertex vertex = UIVertex.simpleVert;
        vertex.color = colors[0];

        vertex.position = Quaternion.Euler(0, 0, angle) * new Vector3(-lineThickness, 0);
        vertex.position += new Vector3(unitWidth * point.x, unitHeight * point.y);
        vh.AddVert(vertex);

        vertex.color = colors[1];
        vertex.position = Quaternion.Euler(0, 0, angle) * new Vector3(lineThickness, 0);
        vertex.position += new Vector3(unitWidth * point.x, unitHeight * point.y);
        vh.AddVert(vertex);
    }
}

and when i draw in unity like this

https://ibb.co/0MS63Ly

As you guys can see that line thickness is not constant.

How could i make line like picture below?

https://ibb.co/JdhRxqH


回答1:


In case it's useful, find this adapted script from the docs to draw lines.

using UnityEngine;

public class Example : MonoBehaviour
{
    // Draws a line from "startVertex" var to the curent mouse position.
    public Material mat;
    Vector3 startVertex;
    Vector3 mousePos;

    void Start()
    {
        startVertex = Vector3.zero;
    }

    void Update()
    {
        mousePos = Input.mousePosition;
        // Press space to update startVertex
        if (Input.GetKeyDown(KeyCode.Space))
        {
            startVertex = new Vector3(mousePos.x / Screen.width, mousePos.y / Screen.height, 0);
        }
    }

    void OnPostRender()
    {
        if (!mat)
        {
            Debug.LogError("Please Assign a material on the inspector");
            return;
        }
        GL.PushMatrix();
        mat.SetPass(0);
        GL.LoadOrtho();

        GL.Begin(GL.LINES);
        GL.Color(Color.red);
        //GL.Vertex(startVertex);
        //GL.Vertex(new Vector3(mousePos.x / Screen.width, mousePos.y / Screen.height, 0));
        
        GL.Vertex(new Vector3(0, 0, 0));
        GL.Vertex(new Vector3(0.3f, 0.3f, 0f));

        GL.Vertex(new Vector3(0.3f, 0.3f, 0f));
        GL.Vertex(new Vector3(0.3f, 0.5f, 0f));

        GL.Vertex(new Vector3(0.3f, 0.5f, 0f));
        GL.Vertex(new Vector3(0.7f, 0.5f, 0f));

        GL.End();

        GL.PopMatrix();
    }
}

Check how you need to insert every pair of points in screen coordinates. Be aware that Unity calls OnPostRender on MonoBehaviours that are attached to the same GameObject as an enabled Camera component, so there is where you would need to attach this script for it to work.

Find screenShot of the red lines:

In case you might need to draw points from the scene in the world space, you can obtain The Size of the Frustum at a Given Distance from the Camera to transform the points you need to the screen space.



来源:https://stackoverflow.com/questions/65539598/how-to-draw-line-smooth-in-unity-c-base-coding-problem

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!