Mesh网格

参考文档:猫神

mesh是图形硬件用来绘制复杂事物的的框架。它至少包含一个顶点集合(这些顶点是三维空间中的一些坐标,)以及连接这些点的一组三角形(最基本的2D形状)。这些三角形集合在一起就构成任何mesh所代表的表面形状

如果你想用一个GameObject展示一个3D的模型,那么它必须要两个components才可以。第一个是mesh filter,它决定了你想展示那个mesh(形状);第二个是mesh renderer,它决定了你应该如何渲染mesh(上色),比如使用什么材质球,是否接受阴影或者投影等等。

绘制一张玻璃片

绘制顶点

通过顶点画三角面

上贴图

using System.Collections;
using UnityEngine;

[RequireComponent(typeof(MeshFilter)), RequireComponent(typeof(MeshRenderer))]
public class MeshGrid : MonoBehaviour
{
    Grid<int> grid;
    int xSize=8,ySize=4;
    Mesh mesh;

    // Start is called before the first frame update
    void Start()
    {
        grid = new Grid<int>(xSize, ySize, 10, new Vector3(0, 0));
        StartCoroutine(GenerateVertices());
    }

    private IEnumerator GenerateVertices()
    {
        WaitForSeconds wait = new WaitForSeconds(0.1f);
        mesh = GetComponent<MeshFilter>().mesh;

        Vector2[] uv = new Vector2[grid.GetVertices().Length];
        Vector4[] tangents = new Vector4[grid.GetVertices().Length];
        Vector4 tangent = new Vector4(1f, 0f, 0f, -1f);
        for (int i = 0; i < xSize+1; i++)
        {
            for( int j = 0; j < ySize+1; j++)
            {
                grid.SetVertices(i + j * (xSize + 1), grid.GetWorldPos(i, j));
                uv[i + j * (xSize + 1)] = new Vector2((float)i / xSize, (float)j / ySize);
                tangents[i + j * (xSize + 1)] = tangent;
            }
        }
        mesh.vertices = grid.GetVertices();
        mesh.uv = uv;
        mesh.tangents = tangents;
        int[] triangles = new int[6 * xSize * ySize];
        for(int y = 0, vi = 0, ti = 0; y < ySize; y++, vi++)
        {
            for (int x = 0; x < xSize; x++, ti += 6, vi++)
            {
                triangles[ti] = vi;
                triangles[3 + ti] = triangles[2 + ti] = vi + 1;
                triangles[4 + ti] = triangles[1 + ti] = vi + xSize + 1;
                triangles[5 + ti] = vi + xSize + 2;
                mesh.triangles = triangles;
                mesh.RecalculateNormals();
                yield return wait;
            }
        }
    }



    private void OnDrawGizmosSelected()
    {
        if(grid == null) return;
        Gizmos.color = Color.black;
        for(int i = 0; i < grid.GetVertices().Length; i++)
        {
            Gizmos.DrawSphere(grid.GetVertices()[i], 1f);
        }
        
    }
}

让mesh有凹凸感

法线贴图是一种纹理贴图,用于存储每个像素处的法线信息。通过使用切线空间,法线贴图可以提供更精细的表面细节,使模型看起来更加真实。例如,法线贴图可以模拟细微的凹凸感,而不需要增加几何复杂度。

其原理基于改变表面法线的方向,从而影响光照计算的结果。通过法线去计算光照的入射方向和强度,从而影响最终的颜色和亮度。

// 在法线贴图中使用,只需要这么设置就可以实现这种效果

Vector4[] tangents = new Vector4[grid.GetVertices().Length];
Vector4 tangent = new Vector4(1f, 0f, 0f, -1f);

tangents[所有的顶点下标] = tangent;

 mesh.tangents = tangents;

Rounded Cube

边缘角度被设计为圆环的性质的立方体