Exemplo n.º 1
0
        bool Mesh2Obstacle()
        {
            if (mesh.vertexCount == 0 || mesh.triangles.Length == 0)
            {
                LogMgr.LogError("Convert Error");
                return(false);
            }
            BeginSample("Mesh2Obstacle");
            //old
            Vector3[] vectorVertices = mesh.vertices;
            int[]     triangles      = mesh.triangles;

            //create new
            KInt3[] vertices = new KInt3[mesh.vertexCount];

            Dictionary <KInt3, int> hashedVerts = new Dictionary <KInt3, int> (mesh.vertexCount);

            int[] newVertices = new int[vertices.Length];

            //从模型坐标系转换到世界坐标系
            for (int i = 0; i < vertices.Length; i++)
            {
                vertices [i] = (KInt3)MeshMatrix.MultiplyPoint3x4(vectorVertices [i]);
                ShowProgress("从模型坐标系转换到世界坐标系", (float)i / vertices.Length);
            }
            //旧顶点在新顶点中的索引
            int newVerIdx = 0;

            for (int i = 0; i < vertices.Length; i++)
            {
                //当hash 顶点集合不包含这个顶点的时候,把这个点加入进去,去除共点
                if (!hashedVerts.ContainsKey(vertices [i]))
                {
                    newVertices [newVerIdx] = i;
                    hashedVerts.Add(vertices [i], newVerIdx);
                    newVerIdx++;
                }
                ShowProgress("构建映射", (float)i / vertices.Length);
            }

            for (int x = 0; x < triangles.Length; x++)
            {
                //把老的顶点索引映射到新的顶点索引上
                KInt3 vertex = vertices [triangles [x]];

                triangles [x] = hashedVerts [vertex];
                ShowProgress("三角映射", (float)x / triangles.Length);
            }

            KInt3[] totalIntVertices = vertices;
            vertices = new KInt3[newVerIdx];
            for (int i = 0; i < newVerIdx; i++)
            {
                vertices [i] = totalIntVertices [newVertices [i]];
                ShowProgress("顶点索引转换", (float)i / newVerIdx);
            }
            //顶点创建结束
#if UNITY_EDITOR
            this.ObsVertices = vertices;
#endif
            if (triangles.Length % 3 != 0)
            {
                LogMgr.LogErrorFormat("triangle lenth error :{0}", triangles.Length);
            }

            //创建三角
            ObsTriangles = new NavmeshTriangle[triangles.Length / 3];

            for (int i = 0; i < ObsTriangles.Length; i++)
            {
                NavmeshTriangle tri = new NavmeshTriangle();
                ObsTriangles [i] = tri;
#if UNITY_EDITOR
                //init
                tri.uid = i;
#endif
                //
                tri.v0 = triangles [i * 3];
                tri.v1 = triangles [i * 3 + 1];
                tri.v2 = triangles [i * 3 + 2];

                if (RVOMath.IsClockwiseXZ(vertices [tri.v0], vertices [tri.v1], vertices [tri.v2]) == false)
                {
                    int tmp = tri.v0;
                    tri.v0 = tri.v2;
                    tri.v2 = tmp;
                }

                //finish position
                tri.v03 = vertices [tri.v0];
                tri.v13 = vertices [tri.v1];
                tri.v23 = vertices [tri.v2];

                tri.v03xz = new KInt2(tri.v03.x, tri.v03.z);
                tri.v13xz = new KInt2(tri.v13.x, tri.v13.z);
                tri.v23xz = new KInt2(tri.v23.x, tri.v23.z);

                tri.averagePos = (tri.v03 + tri.v13 + tri.v23) / 3;

                if (this.ExactMode >= ExactType.TWO)
                {
                    tri.xzPos = new KInt2(tri.averagePos.x, tri.averagePos.z);

                    if (point2triangle.ContainsKey(tri.xzPos))
                    {
                        point2triangle [tri.xzPos].Add(tri);
                    }
                    else
                    {
                        point2triangle [tri.xzPos] = new List <NavmeshTriangle> ();
                        point2triangle [tri.xzPos].Add(tri);
                    }
                }

                ShowProgress("构建三角形", (float)i / ObsTriangles.Length);
            }

            Dictionary <KInt2, NavmeshTriangle> sides = new Dictionary <KInt2, NavmeshTriangle> (triangles.Length * 3);

            //创建三角形的边
            for (int i = 0, j = 0; i < triangles.Length; j += 1, i += 3)
            {
                sides [KInt2.ToInt2(triangles [i + 0], triangles [i + 1])] = ObsTriangles [j];
                sides [KInt2.ToInt2(triangles [i + 1], triangles [i + 2])] = ObsTriangles [j];
                sides [KInt2.ToInt2(triangles [i + 2], triangles [i + 0])] = ObsTriangles [j];
            }

            HashSet <NavmeshTriangle> connections = new HashSet <NavmeshTriangle> ();

            for (int i = 0, j = 0; i < triangles.Length; j += 1, i += 3)
            {
                connections.Clear();

                NavmeshTriangle node = ObsTriangles [j];

                for (int q = 0; q < 3; q++)
                {
                    NavmeshTriangle other;
                    //如果是mesh中的边,则加入
                    if (sides.TryGetValue(KInt2.ToInt2(triangles [i + ((q + 1) % 3)], triangles [i + q]), out other))
                    {
                        connections.Add(other);
                    }
                }
                //拷贝当前的一份连接点,而不是赋值引用过去
                node.connections = new List <NavmeshTriangle> ();
                node.connections.AddRange(connections);

                node.CreateSharedInfo();
                ShowProgress("构建连接点", (float)i / (triangles.Length / 3));
            }
            ClearProgressBar();
            EndSample();

            return(true);
        }