Unity 3D 创建Mesh(一)

来源:互联网 发布:windows双系统怎么删除 编辑:程序博客网 时间:2024/03/29 17:47

Unity 3D 创建Mesh(一)


一、Unity 3D 创建面片(Mesh)

Mesh是一种网格,可以产生像地形那样震撼的效果,那么怎样创建Mesh呢?那就要知道Mesh包含什么!
Mesh(网格):顶点、三角形、段数。
如图所示:该网格该如何表示呢?
顶点(vertexes)16=4*4段数(segment)3*3三角形(triangles)18但是,三角形数目不是自己数,而是计算出来的。

二、创建Mesh属性

我们来创建一个长宽为100m*100m,高度为0m,段数为3*3的网格,如上图所示
/*  Mesh属性     *      长宽     *      段数     *      高度     */    private Vector2 size;//长度和宽度    private float height= 0;//高度    private Vector2 segment;//长度的段数和宽度的段数
/*  顶点属性     *      顶点     *      uv     *      三角形      */    private Vector3[] vertexes;//顶点数    private int[] triangles;//三角形索引


    /*计算顶点,存入顶点数组*/
    private void computeVertexes()    {        int sum = Mathf.FloorToInt((segment.x + 1) * (segment.y + 1));//顶点总数        float w = size.x / segment.x;//每一段的长度        float h = size.y / segment.y;         GetTriangles();//计算三角形索引顶点序列        int index = 0;        vertexes = new Vector3[sum];        for (int i = 0; i < segment.y + 1;i++ )        {            for (int j = 0; j < segment.x + 1; j++)            {                float tempHeight = 0;                vertexes[index] = new Vector3(j*w, 0, i*h);//计算完顶点                index++;            }        }    }
/*计算三角形的顶点索引*/
private int[] GetTriangles()    {        int sum = Mathf.FloorToInt(segment.x * segment.y * 6);//三角形顶点总数:假设是1*1的网格,会有2个顶点复用,因此是6个顶点。假设是2*2的网格,则是4个1*1的网格,即4*6即2*2*6!        triangles = new int[sum];        uint index = 0;        for (int i = 0; i < segment.y; i++)        {            for (int j = 0; j < segment.x; j++)            {                int role = Mathf.FloorToInt(segment.x) + 1;                int self = j + (i * role);                int next = j + ((i + 1) * role);                //顺时针
//第一个三角形                triangles[index] = self;                triangles[index + 1] = next + 1;                triangles[index + 2] = self + 1;
//第二个三角形                triangles[index + 3] = self;                triangles[index + 4] = next;                triangles[index + 5] = next + 1;                index += 6;            }        }        return triangles;    }
到此:顶点、三角形计算完成!接下来是渲染。

三、渲染网格

在Unity 3D中,一个GameObject只有一个transform组件。我们在程序中,声明一个GameObject变量,通过添加MeshFilter来增加Mesh属性,通过MeshRenderer渲染出来,在MeshRenderer中,我们使用默认材质球。
    private GameObject mMesh;    private Material mMaterial;
mMesh = new GameObject();        mMesh.name = "CreateMesh";
</pre><pre code_snippet_id="655703" snippet_file_name="blog_20150429_12_2096575" name="code" class="cpp">    private void DrawMesh()    {        Mesh mesh = mMesh.AddComponent<MeshFilter>().mesh;//网格        mMesh.AddComponent<MeshRenderer>();//网格渲染器        mMaterial = new Material(Shader.Find("Diffuse"));//材质        mMesh.GetComponent<Renderer>().material = mMaterial;        /*设置mesh*/        mesh.Clear();//更新        mesh.vertices = vertexes;        //mesh.uv         mesh.triangles = triangles;        mesh.RecalculateNormals();        mesh.RecalculateBounds();    }

四、完整代码(有点不一样,扩充了点,拖在摄像机下面即可)

using UnityEngine;using System.Collections;/*仅仅创建Mesh * * */public class CreatMesh : MonoBehaviour {    private GameObject mMesh;    private Material mMaterial;    /*  Mesh属性     *      长宽     *      段数     *      高度     *      高度差     */    private Vector2 size;//长度和宽度    private float minHeight = -10;//最小高度    private float maxHeight = 10;//最大高度    private Vector2 segment;//长度的段数和宽度的段数    private float unitH;//最小高度和最大高度只差,值为正    /*  顶点属性     *      顶点     *      uv     *      三角形      */    private Vector3[] vertexes;//顶点数    private Vector2 uvs;//uvs坐标    private int[] triangles;//三角形索引void Start () {        creatMesh(100, 100, 3, 3, -10, 10);}    private void creatMesh(float width, float height, uint segmentX, uint segmentY,int min, int max)    {        size = new Vector2(width, height);        maxHeight = max;        minHeight = min;        unitH = maxHeight - minHeight;        segment = new Vector2(segmentX, segmentY);        if (mMesh != null)        {            Destroy(mMesh);        }        mMesh = new GameObject();        mMesh.name = "CreateMesh";        computeVertexes();        DrawMesh();    }    private void computeVertexes()    {        int sum = Mathf.FloorToInt((segment.x + 1) * (segment.y + 1));//顶点总数        float w = size.x / segment.x;//每一段的长度        float h = size.y / segment.y;         GetTriangles();        int index = 0;        vertexes = new Vector3[sum];        for (int i = 0; i < segment.y + 1;i++ )        {            for (int j = 0; j < segment.x + 1; j++)            {                float tempHeight = 0;                vertexes[index] = new Vector3(j*w, 0, i*h);                index++;            }        }    }    private void DrawMesh()    {        Mesh mesh = mMesh.AddComponent<MeshFilter>().mesh;//网格        mMesh.AddComponent<MeshRenderer>();//网格渲染器        mMaterial = new Material(Shader.Find("Diffuse"));//材质        mMesh.GetComponent<Renderer>().material = mMaterial;        /*设置mesh*/        mesh.Clear();//更新        mesh.vertices = vertexes;        //mesh.uv         mesh.triangles = triangles;        mesh.RecalculateNormals();        mesh.RecalculateBounds();    }    private int[] GetTriangles()    {        int sum = Mathf.FloorToInt(segment.x * segment.y * 6);//三角形顶点总数        triangles = new int[sum];        uint index = 0;        for (int i = 0; i < segment.y; i++)        {            for (int j = 0; j < segment.x; j++)            {                int role = Mathf.FloorToInt(segment.x) + 1;                int self = j + (i * role);                int next = j + ((i + 1) * role);                //顺时针                triangles[index] = self;                triangles[index + 1] = next + 1;                triangles[index + 2] = self + 1;                triangles[index + 3] = self;                triangles[index + 4] = next;                triangles[index + 5] = next + 1;                index += 6;            }        }        return triangles;    }}




0 0