예제 #1
0
    public static Mesh GeneratePlane(PlaneGenerationData data)
    {
        StringBuilder nameBuilder = new StringBuilder("Procedural Plane [", 28);

        nameBuilder.Append(data.length);
        nameBuilder.Append("x");
        nameBuilder.Append(data.width);
        nameBuilder.Append("][");
        nameBuilder.Append(data.verticesPerLength);
        nameBuilder.Append(",");
        nameBuilder.Append(data.verticesPerWidth);
        nameBuilder.Append("]");

        Vector3[] vertices = new Vector3[data.verticesPerLength * data.verticesPerWidth];
        Vector2[] uv       = new Vector2[vertices.Length];
        Vector4[] tangents = new Vector4[vertices.Length];
        Vector4   tangent  = new Vector4(1f, 0f, 0f, -1f);

        switch (data.direction)
        {
        case PlaneGenerationData.Direction.XY: tangent = new Vector4(1f, 0f, 0f, -1f); break;

        case PlaneGenerationData.Direction.XZ: tangent = new Vector4(1f, 0f, 0f, -1f); break;

        case PlaneGenerationData.Direction.YZ: tangent = new Vector4(0f, 0f, 1f, -1f); break;

        default: tangent = Vector4.zero; break;
        }

        for (int i = 0, w = 0; w < data.verticesPerWidth; w++)
        {
            for (int l = 0; l < data.verticesPerLength; l++, i++)
            {
                float u = l / (float)(data.verticesPerLength - 1);
                float v = w / (float)(data.verticesPerWidth - 1);
                float x = -data.length / 2f + data.length * u;
                float y = -data.width / 2f + data.width * v;

                Vector3 position;
                switch (data.direction)
                {
                case PlaneGenerationData.Direction.XY: position = new Vector3(x, y, 0f); break;

                case PlaneGenerationData.Direction.XZ: position = new Vector3(x, 0f, y); break;

                case PlaneGenerationData.Direction.YZ: position = new Vector3(0f, y, x); break;

                default: position = Vector3.zero; break;
                }

                vertices[i] = position;
                uv[i]       = new Vector2(u, v);
                tangents[i] = tangent;
            }
        }

        int[] triangles = new int[(data.verticesPerLength - 1) * (data.verticesPerWidth - 1) * 6];
        for (int vi = 0, ti = 0, w = 0; w < data.verticesPerWidth - 1; w++, vi++)
        {
            for (int l = 0; l < data.verticesPerLength - 1; l++, vi++, ti += 6)
            {
                triangles[ti]     = vi;
                triangles[ti + 3] = triangles[ti + 2] = vi + 1;
                triangles[ti + 4] = triangles[ti + 1] = vi + data.verticesPerLength;
                triangles[ti + 5] = vi + data.verticesPerLength + 1;
            }
        }

        Mesh mesh = new Mesh {
            name      = nameBuilder.ToString(),
            vertices  = vertices,
            triangles = triangles,
            uv        = uv
        };

        mesh.RecalculateNormals();

        mesh.tangents = tangents;

        return(mesh);
    }
예제 #2
0
    private void OnPlaneGenerationGUI()
    {
        planeGenerationData = planeGenerationData ?? new PlaneGenerationData();

        planeGenerationData.direction = (PlaneGenerationData.Direction)UG.EnumPopup("平面方向", planeGenerationData.direction);

        UG.BeginHorizontal();

        planeGenerationData.length = UG.DelayedFloatField("长", planeGenerationData.length);
        planeGenerationData.width  = UG.DelayedFloatField("宽", planeGenerationData.width);

        UG.EndHorizontal();

        UG.BeginHorizontal();

        planeGenerationData.verticesPerLength = UG.DelayedIntField("长顶点数", planeGenerationData.verticesPerLength);
        planeGenerationData.verticesPerWidth  = UG.DelayedIntField("宽顶点数", planeGenerationData.verticesPerWidth);

        UG.EndHorizontal();

        bool   legal        = true;
        string errorMessage = String.Empty;

        if (defaultMaterial == null)
        {
            legal         = false;
            errorMessage += "默认材质不能为空";
        }

        if (planeGenerationData.length <= 0)
        {
            legal         = false;
            errorMessage += "平面长必须大于0\n";
        }

        if (planeGenerationData.width <= 0)
        {
            legal         = false;
            errorMessage += "平面宽必须大于0\n";
        }

        if (planeGenerationData.verticesPerLength <= 0)
        {
            legal         = false;
            errorMessage += "平面长顶点数必须大于0\n";
        }

        if (planeGenerationData.verticesPerWidth <= 0)
        {
            legal         = false;
            errorMessage += "平面宽顶点数必须大于0\n";
        }

        if (legal)
        {
            if (GUILayout.Button("生成"))
            {
                MeshTool.InstantiatePlane(planeGenerationData, defaultMaterial);
            }
        }
        else
        {
            UG.HelpBox(errorMessage, MessageType.Error);
        }
    }
예제 #3
0
 public static GameObject InstantiatePlane(PlaneGenerationData data, Material material) => InstantiateMeshGameObject(GeneratePlane(data), material);