using System.Collections; using System.Collections.Generic; using UnityEngine; //網格創建差不多分這幾步: 1,確認頂點 2,確認頂點順序 3,確認法線,uv... public class MeshStudy : MonoBehaviour { public float sideLength = 2; public float angleDegree = 100; private static readonly int ANGLE_DEGREE_PRECISION = 1000; private static readonly int SIDE_LENGTH_PRECISION = 1000; private MeshFilter _meshFilter; private TriangleMeshCreator creator = new TriangleMeshCreator(); //在編輯器中執行 [ExecuteInEditMode] private void Awake() { _meshFilter = GetComponent<MeshFilter>(); } private void Update() { _meshFilter.mesh = creator.CreateMesh(sideLength,angleDegree); } //在沒選中的時候 畫出的網格設置為灰色 void OnDrawGizmos() { Gizmos.color = Color.gray; DrawMesh(); } void OnDrawGizmosSelected() { Gizmos.color = Color.green; DrawMesh(); } void DrawMesh() { Mesh mesh = creator.CreateMesh(sideLength,angleDegree); int[] tris = mesh.triangles; //繪制三角形 網格信息是從本地坐標獲取的 若在正確的世界位置顯示需求轉換到世界坐標系 Gizmos.DrawLine(Transform2World(mesh.vertices[0]), Transform2World(mesh.vertices[1])); Gizmos.DrawLine(Transform2World(mesh.vertices[1]), Transform2World(mesh.vertices[2])); Gizmos.DrawLine(Transform2World(mesh.vertices[2]), Transform2World(mesh.vertices[0])); } private Vector3 Transform2World(Vector3 src) { return transform.TransformPoint(src); } private class TriangleMeshCreator { private float _sideLength; private float _angleDegree; private Mesh _cacheMesh; public Mesh CreateMesh(float sideLength, float angleDegree) { if (checkDiff(sideLength, angleDegree)) { Mesh newMesh = Create(sideLength,angleDegree); if (newMesh != null) { _cacheMesh = newMesh; this._sideLength = sideLength; this._angleDegree = angleDegree; } } return _cacheMesh; } //三角形邊長和弧長 private Mesh Create(float sideLength, float angleDegree) { Mesh mesh = new Mesh(); Vector3[] verticles = new Vector3[3]; //圓的周長為2ΠR 所以弧長 = (n°/360)*2ΠR (簡化后: L = n°ΠR/180) //從弧度轉化到角度 float angle = Mathf.Deg2Rad * angleDegree; float halfAngle = angle / 2; float cosA = Mathf.Cos(halfAngle); float sinA = Mathf.Sin(halfAngle); //隨便畫一個三角形 verticles[0] = Vector3.zero; verticles[1] = new Vector3(cosA * sideLength, 0, sinA * sideLength); verticles[2] = new Vector3(cosA * sideLength, 0, -sinA * sideLength); //輸入網格的頂點和頂點順序 int[] triangles = new int[3] { 0, 1, 2 }; mesh.vertices = verticles; mesh.triangles = triangles; //設置uv頂點信息 Vector2[] uvs = new Vector2[verticles.Length]; //設置如下貼圖中就避開了數字 說明uv的對角線坐標分別對應 (0,0) 和 (1,1) uvs[0] = new Vector2(0, 0.5f); uvs[1] = new Vector2(0.5f, 0.5f); uvs[2] = new Vector2(0.6f, 0); //uvs[0] = new Vector2(0, 0.5f); //uvs[1] = Vector2.one; //uvs[2] = Vector2.right; mesh.uv = uvs; return mesh; } //檢測是否滿足構成條件 private bool checkDiff(float sideLength, float angleDegree) { return (int)((sideLength - this._sideLength) * SIDE_LENGTH_PRECISION) != 0 || (int)((angleDegree - this._angleDegree) * ANGLE_DEGREE_PRECISION) != 0; } } }