namespace Oni.Motoko { internal class GeometryDatWriter { private Geometry geometry; private ImporterFile importer; public static ImporterDescriptor Write(Geometry geometry, ImporterFile importer) { var writer = new GeometryDatWriter { geometry = geometry, importer = importer }; return writer.WriteGeometry(); } private ImporterDescriptor WriteGeometry() { var triangleStrips = Stripify.FromTriangleList(geometry.Triangles); var triangleList = Stripify.ToTriangleList(triangleStrips); var faceNormals = new Vector3[triangleList.Length / 3]; var faceIndices = new int[faceNormals.Length]; for (int i = 0; i < triangleList.Length; i += 3) { var p0 = geometry.Points[triangleList[i + 0]]; var p1 = geometry.Points[triangleList[i + 1]]; var p2 = geometry.Points[triangleList[i + 2]]; var faceNormal = Vector3.Normalize(Vector3.Cross(p1 - p0, p2 - p0)); int faceIndex = i / 3; faceNormals[faceIndex] = faceNormal; faceIndices[faceIndex] = faceIndex; } var m3gm = importer.CreateInstance(TemplateTag.M3GM, geometry.Name); var pnta = importer.CreateInstance(TemplateTag.PNTA); var vcra1 = importer.CreateInstance(TemplateTag.VCRA); var vcra2 = importer.CreateInstance(TemplateTag.VCRA); var txca = importer.CreateInstance(TemplateTag.TXCA); var idxa1 = importer.CreateInstance(TemplateTag.IDXA); var idxa2 = importer.CreateInstance(TemplateTag.IDXA); using (var writer = m3gm.OpenWrite(4)) { writer.Write(pnta); writer.Write(vcra1); writer.Write(vcra2); writer.Write(txca); writer.Write(idxa1); writer.Write(idxa2); if (geometry.TextureName != null) writer.Write(importer.CreateInstance(TemplateTag.TXMP, geometry.TextureName)); else writer.Write(0); writer.Skip(4); } pnta.WritePoints(geometry.Points); vcra1.WriteVectors(geometry.Normals); vcra2.WriteVectors(faceNormals); txca.WriteTexCoords(geometry.TexCoords); idxa1.WriteIndices(triangleStrips); idxa2.WriteIndices(faceIndices); return m3gm; } } }