public void AddVertex(ref MyVoxelVertex vertex)//Vector3 pos, Vector3 normal, MyVoxelMaterialsEnum material, float ambient) { var material = vertex.Material; byte alphaIndex; if (Material0.Index == material) alphaIndex = 0; else if (Material1.Index == material) alphaIndex = 1; else if (Material2.Index == material) alphaIndex = 2; else throw new System.InvalidOperationException("Should not be there, invalid material"); Vertices[VertexCount].Position = vertex.Position; Vertices[VertexCount].Ambient = vertex.Ambient; Vertices[VertexCount].Normal = vertex.Normal; Vertices[VertexCount].MaterialAlphaIndex = alphaIndex; VertexCount++; }
public void PrepareCache( MyVoxelVertex[] vertices, int vertexCount, MyVoxelTriangle[] triangles, int triangleCount, float positionScale, Vector3 positionOffset, bool createPhysicsShape) { using (m_syncRoot.AcquireExclusiveUsing()) { if (vertexCount == 0) { VoxelVerticesCount = 0; VoxelTrianglesCount = 0; m_octree = null; m_voxelVertices = null; PositionOffset = new Vector3(0f); PositionScale = 0f; return; } Debug.Assert(vertexCount <= Int16.MaxValue); // copy voxel vertices m_voxelVertices = new MyPackedVoxelVertex[vertexCount]; for (int i = 0; i < vertexCount; i++) m_voxelVertices[i] = (MyPackedVoxelVertex)vertices[i]; Profiler.Begin("build octree"); if (m_octree == null) m_octree = new MyOctree(); m_octree.Init(ref m_voxelVertices, ref vertexCount, ref triangles, ref triangleCount, out VoxelTriangles); Profiler.End(); // set size only after the arrays are fully allocated VoxelVerticesCount = vertexCount; VoxelTrianglesCount = triangleCount; PositionOffset = positionOffset; PositionScale = positionScale; if (createPhysicsShape) CreateMeshShape(); } }
private static void AddVertexToBuffer(MySingleMaterialHelper materialHelper, ref MyVoxelVertex vertex0, int matIndex, short vertexIndex0) { MyVoxelCacheCellRenderHelper.CreateArrayIfNotExist(matIndex); if (MyVoxelCacheCellRenderHelper.SingleMaterialIndicesLookup[matIndex][vertexIndex0].CalcCounter != MyVoxelCacheCellRenderHelper.SingleMaterialIndicesLookupCount[matIndex]) { int nextVertexIndex = materialHelper.VertexCount; // Short overflow check System.Diagnostics.Debug.Assert(nextVertexIndex <= short.MaxValue); // copy position and ambient materialHelper.Vertices[nextVertexIndex].Position = vertex0.Position; materialHelper.Vertices[nextVertexIndex].Ambient = vertex0.Ambient; // Copy normal materialHelper.Vertices[nextVertexIndex].Normal = vertex0.Normal; MyVoxelCacheCellRenderHelper.SingleMaterialIndicesLookup[matIndex][vertexIndex0].CalcCounter = MyVoxelCacheCellRenderHelper.SingleMaterialIndicesLookupCount[matIndex]; MyVoxelCacheCellRenderHelper.SingleMaterialIndicesLookup[matIndex][vertexIndex0].VertexIndex = (short)nextVertexIndex; materialHelper.VertexCount++; } }
public void GetUnpackedVertex(int index, out MyVoxelVertex vertex) { vertex = (MyVoxelVertex)m_voxelVertices[index]; vertex.Position = vertex.Position * PositionScale + PositionOffset; }
// We want to skip all wrong triangles, those that have two vertex at almost the same location, etc. bool IsWrongTriangle(ref MyVoxelVertex edge0, ref MyVoxelVertex edge1, ref MyVoxelVertex edge2) { return MyMeshPartSolver.IsWrongTriangle(edge0.Position, edge1.Position, edge2.Position); }
private void CreateTriangles(ref Vector3I coord0, int cubeIndex, ref Vector3I tempVoxelCoord0) { MyVoxelVertex tmpVertex = new MyVoxelVertex(); Vector3I edge = new Vector3I(coord0.X - 1, coord0.Y - 1, coord0.Z - 1); for (int i = 0; MyMarchingCubesConstants.TriangleTable[cubeIndex, i] != -1; i += 3) { // Edge indexes inside the cube int edgeIndex0 = MyMarchingCubesConstants.TriangleTable[cubeIndex, i + 0]; int edgeIndex1 = MyMarchingCubesConstants.TriangleTable[cubeIndex, i + 1]; int edgeIndex2 = MyMarchingCubesConstants.TriangleTable[cubeIndex, i + 2]; MyEdge edge0 = m_edges[edgeIndex0]; MyEdge edge1 = m_edges[edgeIndex1]; MyEdge edge2 = m_edges[edgeIndex2]; // Edge indexes inside the cell Vector4I edgeConversion0 = MyMarchingCubesConstants.EdgeConversion[edgeIndex0]; Vector4I edgeConversion1 = MyMarchingCubesConstants.EdgeConversion[edgeIndex1]; Vector4I edgeConversion2 = MyMarchingCubesConstants.EdgeConversion[edgeIndex2]; MyEdgeVertex edgeVertex0 = m_edgeVertex[edge.X + edgeConversion0.X][edge.Y + edgeConversion0.Y][edge.Z + edgeConversion0.Z][edgeConversion0.W]; MyEdgeVertex edgeVertex1 = m_edgeVertex[edge.X + edgeConversion1.X][edge.Y + edgeConversion1.Y][edge.Z + edgeConversion1.Z][edgeConversion1.W]; MyEdgeVertex edgeVertex2 = m_edgeVertex[edge.X + edgeConversion2.X][edge.Y + edgeConversion2.Y][edge.Z + edgeConversion2.Z][edgeConversion2.W]; MyVoxelVertex compressedVertex0 = new MyVoxelVertex(); compressedVertex0.Position = edge0.Position; MyVoxelVertex compressedVertex1 = new MyVoxelVertex(); compressedVertex1.Position = edge1.Position; MyVoxelVertex compressedVertex2 = new MyVoxelVertex(); compressedVertex2.Position = edge2.Position; // We want to skip all wrong triangles, those that have two vertex at almost the same location, etc. // We do it simply, by calculating triangle normal and then checking if this normal has length large enough if (IsWrongTriangle(ref compressedVertex0, ref compressedVertex1, ref compressedVertex2) == true) { continue; } // Vertex at edge 0 if (edgeVertex0.CalcCounter != m_edgeVertexCalcCounter) { // If vertex at edge0 wasn't calculated for this cell during this precalc, we need to add it // Short overflow check System.Diagnostics.Debug.Assert(m_resultVerticesCounter <= short.MaxValue); edgeVertex0.CalcCounter = m_edgeVertexCalcCounter; edgeVertex0.VertexIndex = m_resultVerticesCounter; tmpVertex.Position = (edge0.Position - m_originPosition) / m_positionScale; tmpVertex.Normal = edge0.Normal; tmpVertex.Ambient = edge0.Ambient; tmpVertex.Material = edge0.Material; m_resultVertices[m_resultVerticesCounter] = tmpVertex; m_resultVerticesCounter++; } // Vertex at edge 1 if (edgeVertex1.CalcCounter != m_edgeVertexCalcCounter) { // If vertex at edge1 wasn't calculated for this cell during this precalc, we need to add it // Short overflow check System.Diagnostics.Debug.Assert(m_resultVerticesCounter <= short.MaxValue); edgeVertex1.CalcCounter = m_edgeVertexCalcCounter; edgeVertex1.VertexIndex = m_resultVerticesCounter; tmpVertex.Position = (edge1.Position - m_originPosition) / m_positionScale; tmpVertex.Normal = edge1.Normal; tmpVertex.Ambient = edge1.Ambient; tmpVertex.Material = edge1.Material; m_resultVertices[m_resultVerticesCounter] = tmpVertex; m_resultVerticesCounter++; } // Vertex at edge 2 if (edgeVertex2.CalcCounter != m_edgeVertexCalcCounter) { // If vertex at edge2 wasn't calculated for this cell during this precalc, we need to add it // Short overflow check System.Diagnostics.Debug.Assert(m_resultVerticesCounter <= short.MaxValue); edgeVertex2.CalcCounter = m_edgeVertexCalcCounter; edgeVertex2.VertexIndex = m_resultVerticesCounter; tmpVertex.Position = (edge2.Position - m_originPosition) / m_positionScale; tmpVertex.Normal = edge2.Normal; tmpVertex.Ambient = edge2.Ambient; tmpVertex.Material = edge2.Material; m_resultVertices[m_resultVerticesCounter] = tmpVertex; m_resultVerticesCounter++; } // Triangle m_resultTriangles[m_resultTrianglesCounter].VertexIndex0 = edgeVertex0.VertexIndex; m_resultTriangles[m_resultTrianglesCounter].VertexIndex1 = edgeVertex1.VertexIndex; m_resultTriangles[m_resultTrianglesCounter].VertexIndex2 = edgeVertex2.VertexIndex; Debug.Assert(edgeVertex0.VertexIndex < m_resultVerticesCounter); Debug.Assert(edgeVertex1.VertexIndex < m_resultVerticesCounter); Debug.Assert(edgeVertex2.VertexIndex < m_resultVerticesCounter); m_resultTrianglesCounter++; } }