示例#1
0
        public OCMeshBuilder FromMesh(UnityEngine.Mesh mesh)
        {
            if (mesh == null)
            {
                return(this);
            }

            _vertices.AddRange(mesh.vertices);
            _colors.AddRange(mesh.colors);
            _normals.AddRange(mesh.normals);
            _uv.AddRange(mesh.uv);

            for (int i = 0; i < mesh.subMeshCount; ++i)
            {
                AddIndices(0, mesh.GetTriangles(i));
            }

            return(this);
        }
示例#2
0
        public static object Serialize_UnityMesh(object obj, System.Type type, OverloadLevelConvertSerializer serializer)
        {
            uint version = serializer.Version;

            UnityEngine.Mesh mesh = (UnityEngine.Mesh)obj;

            int flags;

            if (version <= 3)
            {
                // old version, we just had 'colors'
                flags = 1;
            }
            else
            {
                // new version, use a flags value to report what we have
                if (serializer.IsWriting)
                {
                    flags = 0;
                    if (mesh.colors != null && mesh.colors.Length > 0)
                    {
                        flags |= 1;
                    }
                    if (mesh.colors32 != null && mesh.colors32.Length > 0)
                    {
                        flags |= 2;
                    }
                    serializer.SerializeOut_int32(flags);
                }
                else
                {
                    flags = serializer.SerializeIn_int32();
                }
            }

            serializer.SerializeX(mesh, x => x.name);
            serializer.SerializeX(mesh, x => x.vertices);             // Note: vertices must come first since the other fields may check size invariants
            serializer.SerializeX(mesh, x => x.uv);
            serializer.SerializeX(mesh, x => x.uv2);
            serializer.SerializeX(mesh, x => x.uv3);
            serializer.SerializeX(mesh, x => x.normals);
            serializer.SerializeX(mesh, x => x.tangents);
            if ((flags & 1) != 0)
            {
                serializer.SerializeX(mesh, x => x.colors);
            }
            if ((flags & 2) != 0)
            {
                serializer.SerializeX(mesh, x => x.colors32);
            }
            if (version > 3)
            {
                serializer.SerializeX(mesh, x => x.boneWeights);
                serializer.SerializeX(mesh, x => x.bindposes);
            }

            if (serializer.IsWriting)
            {
                Int32 numSubmeshes = mesh.subMeshCount;
                serializer.SerializeOut_int32(numSubmeshes);

                for (Int32 i = 0; i < numSubmeshes; ++i)
                {
                    Int32[] tris = mesh.GetTriangles(i);
                    serializer.SerializeOut_array(typeof(Int32), tris);
                }
            }
            else
            {
                Int32 numSubmeshes = serializer.SerializeIn_int32();
                mesh.subMeshCount = numSubmeshes;

                for (Int32 i = 0; i < numSubmeshes; ++i)
                {
                    Int32[] tris = (Int32[])serializer.SerializeIn_array(typeof(Int32));
                    mesh.SetTriangles(tris, i);
                }
            }

            return(mesh);
        }
    private static void SetGeometryFromMesh(
        UnityEngine.Mesh mesh,
        AK.Wwise.AcousticTexture[] acousticTextures,
        float[] occlusionValues,
        UnityEngine.Transform transform,
        ulong geometryID,
        ulong associatedRoomID,
        bool enableDiffraction,
        bool enableDiffractionOnBoundaryEdges,
        string name = "")
    {
        var vertices = mesh.vertices;

        // Remove duplicate vertices
        var vertRemap   = new int[vertices.Length];
        var uniqueVerts = new System.Collections.Generic.List <UnityEngine.Vector3>();
        var vertDict    = new System.Collections.Generic.Dictionary <UnityEngine.Vector3, int>();

        for (var v = 0; v < vertices.Length; ++v)
        {
            int vertIdx = 0;
            if (!vertDict.TryGetValue(vertices[v], out vertIdx))
            {
                vertIdx = uniqueVerts.Count;
                uniqueVerts.Add(vertices[v]);
                vertDict.Add(vertices[v], vertIdx);
            }
            vertRemap[v] = vertIdx;
        }

        int vertexCount = uniqueVerts.Count;
        var vertexArray = new UnityEngine.Vector3[vertexCount];

        for (var v = 0; v < vertexCount; ++v)
        {
            var point = transform.TransformPoint(uniqueVerts[v]);
            vertexArray[v].x = point.x;
            vertexArray[v].y = point.y;
            vertexArray[v].z = point.z;
        }

        int surfaceCount = mesh.subMeshCount;

        var numTriangles = mesh.triangles.Length / 3;

        if ((mesh.triangles.Length % 3) != 0)
        {
            UnityEngine.Debug.LogFormat("SetGeometryFromMesh({0}): Wrong number of triangles", mesh.name);
        }

        using (var surfaceArray = new AkAcousticSurfaceArray(surfaceCount))
            using (var triangleArray = new AkTriangleArray(numTriangles))
            {
                int triangleArrayIdx = 0;

                for (var s = 0; s < surfaceCount; ++s)
                {
                    var surface       = surfaceArray[s];
                    var triangles     = mesh.GetTriangles(s);
                    var triangleCount = triangles.Length / 3;
                    if ((triangles.Length % 3) != 0)
                    {
                        UnityEngine.Debug.LogFormat("SetGeometryFromMesh({0}): Wrong number of triangles in submesh {1}", mesh.name, s);
                    }

                    AK.Wwise.AcousticTexture acousticTexture = null;
                    float occlusionValue = 1.0f;

                    if (s < acousticTextures.Length)
                    {
                        acousticTexture = acousticTextures[s];
                    }

                    if (s < occlusionValues.Length)
                    {
                        occlusionValue = occlusionValues[s];
                    }

                    surface.textureID = acousticTexture == null ? AK.Wwise.AcousticTexture.InvalidId : acousticTexture.Id;
                    surface.occlusion = occlusionValue;
                    surface.strName   = name + "_" + mesh.name + "_" + s;

                    for (var i = 0; i < triangleCount; ++i)
                    {
                        var triangle = triangleArray[triangleArrayIdx];

                        triangle.point0  = (ushort)vertRemap[triangles[3 * i + 0]];
                        triangle.point1  = (ushort)vertRemap[triangles[3 * i + 1]];
                        triangle.point2  = (ushort)vertRemap[triangles[3 * i + 2]];
                        triangle.surface = (ushort)s;

                        if (triangle.point0 != triangle.point1 && triangle.point0 != triangle.point2 && triangle.point1 != triangle.point2)
                        {
                            ++triangleArrayIdx;
                        }
                        else
                        {
                            UnityEngine.Debug.LogFormat("SetGeometryFromMesh({0}): Skipped degenerate triangle({1}, {2}, {3}) in submesh {4}", mesh.name, 3 * i + 0, 3 * i + 1, 3 * i + 2, s);
                        }
                    }
                }

                if (triangleArrayIdx > 0)
                {
                    AkSoundEngine.SetGeometry(
                        geometryID,
                        triangleArray,
                        (uint)triangleArrayIdx,
                        vertexArray,
                        (uint)vertexArray.Length,
                        surfaceArray,
                        (uint)surfaceArray.Count(),
                        associatedRoomID,
                        enableDiffraction,
                        enableDiffractionOnBoundaryEdges);
                }
                else
                {
                    UnityEngine.Debug.LogFormat("SetGeometry({0}): No valid triangle was found. Geometry was not set", mesh.name);
                }
            }
    }
示例#4
0
        /// <summary>
        /// Decimates a mesh.
        /// </summary>
        /// <param name="mesh">The mesh to decimate.</param>
        /// <param name="transform">The mesh transform.</param>
        /// <param name="quality">The desired quality.</param>
        /// <param name="recalculateNormals">If normals should be recalculated.</param>
        /// <param name="statusCallback">The optional status report callback.</param>
        /// <returns>The decimated mesh.</returns>
        public static UMesh DecimateMesh(UMesh mesh, UMatrix transform, float quality, bool recalculateNormals, DecimationAlgorithm.StatusReportCallback statusCallback = null)
        {
            if (mesh == null)
            {
                throw new ArgumentNullException("mesh");
            }

            int subMeshCount    = mesh.subMeshCount;
            var meshVertices    = mesh.vertices;
            var meshNormals     = mesh.normals;
            var meshTangents    = mesh.tangents;
            var meshUV1         = mesh.uv;
            var meshUV2         = mesh.uv2;
            var meshUV3         = mesh.uv3;
            var meshUV4         = mesh.uv4;
            var meshColors      = mesh.colors;
            var meshBoneWeights = mesh.boneWeights;
            var meshBindposes   = mesh.bindposes;

            int totalTriangleCount = 0;
            var meshIndices        = new int[subMeshCount][];

            for (int i = 0; i < subMeshCount; i++)
            {
                meshIndices[i]      = mesh.GetTriangles(i);
                totalTriangleCount += meshIndices[i].Length / 3;
            }

            // Transforms the vertices
            TransformVertices(meshVertices, ref transform);

            var vertices = ToSimplifyVertices(meshVertices);

            quality = UMath.Clamp01(quality);
            int targetTriangleCount = UMath.CeilToInt(totalTriangleCount * quality);
            var sourceMesh          = new Mesh(vertices, meshIndices);

            if (meshNormals != null && meshNormals.Length > 0)
            {
                sourceMesh.Normals = ToSimplifyVec(meshNormals);
            }
            if (meshTangents != null && meshTangents.Length > 0)
            {
                sourceMesh.Tangents = ToSimplifyVec(meshTangents);
            }
            if (meshUV1 != null && meshUV1.Length > 0)
            {
                sourceMesh.UV1 = ToSimplifyVec(meshUV1);
            }
            if (meshUV2 != null && meshUV2.Length > 0)
            {
                sourceMesh.UV2 = ToSimplifyVec(meshUV2);
            }
            if (meshUV3 != null && meshUV3.Length > 0)
            {
                sourceMesh.UV3 = ToSimplifyVec(meshUV3);
            }
            if (meshUV4 != null && meshUV4.Length > 0)
            {
                sourceMesh.UV4 = ToSimplifyVec(meshUV4);
            }
            if (meshColors != null && meshColors.Length > 0)
            {
                sourceMesh.Colors = ToSimplifyVec(meshColors);
            }
            if (meshBoneWeights != null && meshBoneWeights.Length > 0)
            {
                sourceMesh.BoneWeights = ToSimplifyBoneWeights(meshBoneWeights);
            }

            var algorithm = MeshDecimation.CreateAlgorithm(Algorithm.Default);

            algorithm.MaxVertexCount = ushort.MaxValue;
            if (statusCallback != null)
            {
                algorithm.StatusReport += statusCallback;
            }

            //var destMesh = MeshDecimation.DecimateMeshLossless( sourceMesh);
            var destMesh        = MeshDecimation.DecimateMesh(algorithm, sourceMesh, targetTriangleCount);
            var newMeshVertices = FromSimplifyVertices(destMesh.Vertices);

            if (statusCallback != null)
            {
                algorithm.StatusReport -= statusCallback;
            }

            return(CreateMesh(meshBindposes, newMeshVertices, destMesh, recalculateNormals));
        }