/// <summary> /// Reads a buffer mesh from a byte array /// </summary> /// <param name="source">Byte source</param> /// <param name="address">Address at which the buffermesh is located</param> public static BufferMesh Read(byte[] source, uint address, uint imageBase) { BufferVertex[] vertices = new BufferVertex[source.ToUInt16(address)]; bool continueWeight = source.ToUInt16(address + 2) != 0; BufferCorner[] corners = new BufferCorner[source.ToUInt32(address + 4)]; uint[] triangles = new uint[source.ToUInt32(address + 8)]; address += 12; BufferMaterial material = BufferMaterial.Read(source, ref address); uint tmpAddr = source.ToUInt32(address) - imageBase; for (int i = 0; i < vertices.Length; i++) { vertices[i] = BufferVertex.Read(source, ref tmpAddr); } tmpAddr = source.ToUInt32(address += 4) - imageBase; for (int i = 0; i < corners.Length; i++) { corners[i] = BufferCorner.Read(source, ref tmpAddr); } tmpAddr = source.ToUInt32(address += 4) - imageBase; for (int i = 0; i < triangles.Length; i++) { triangles[i] = source.ToUInt32(tmpAddr); tmpAddr += 4; } if (vertices.Length == 0) { return(new BufferMesh(corners, triangles, material)); } else if (corners.Length == 0) { return(new BufferMesh(vertices, continueWeight)); } else { return(new BufferMesh(vertices, continueWeight, corners, triangles, material)); } }
/// <summary> /// Optimizes the triangles and removes degenerate triangles <br/> /// Keeps the original vertex data /// </summary> public void Optimize() { if (Corners == null) { return; } BufferCorner[] corners = Corners; if (TriangleList != null) { corners = new BufferCorner[TriangleList.Length]; for (int i = 0; i < TriangleList.Length; i++) { corners[i] = Corners[TriangleList[i]]; } } // filter degenerate triangles int newArraySize = corners.Length; for (int i = 0; i < newArraySize; i += 3) { ushort index1 = corners[i].VertexIndex; ushort index2 = corners[i + 1].VertexIndex; ushort index3 = corners[i + 2].VertexIndex; if (index1 == index2 || index2 == index3 || index3 == index1) { corners[i] = corners[newArraySize - 3]; corners[i + 1] = corners[newArraySize - 2]; corners[i + 2] = corners[newArraySize - 1]; i -= 3; newArraySize -= 3; } } Array.Resize(ref corners, newArraySize); // get the triangle mapping (BufferCorner[] distinct, int[] map) = corners.CreateDistinctMap(); Corners = distinct; TriangleList = (uint[])(object)map; // i cant believe this works lol }