//************************************************************************ //* Class implementing the marching cube algorithm //* Antoine Guilmard - 2006 //* //* - SetXRange(), SetYRange(), SetZRange() //* - SetFunction(), SetStep(), SetIsoLevel() //* - and Polygonise() //* - you could ComputeNormals() //* - finally GetVertexBuffer() and GetIndexBuffer() //* //************************************************************************ #include "StdAfx.h" #include "marchingcube.h" #include "math.h" //************************************************************************ // CMarchingCube Class //************************************************************************ CMarchingCube::CMarchingCube(void) { m_XMax=1; m_XMin=-1; m_YMax=1; m_YMin=-1; m_ZMax=1; m_ZMin=-1; m_Step=10; m_nVertex=0; m_nIndex=0; m_pFunction=NULL; } CMarchingCube::~CMarchingCube(void) { } //************************************************************************ // Main function : // - Space discretization => Grid // - Compute function value at each grid nodes // - Apply marching cube algorithm //************************************************************************ BOOL CMarchingCube::Polygonise() { int CubeIndex; GRID ***Grid; CELL Cell; m_nVertex=0; m_nIndex=0; /* Check parameters */ if (m_pFunction==NULL) return FALSE; if (m_XMax==m_XMin) return FALSE; if (m_YMax==m_YMin) return FALSE; if (m_ZMax==m_ZMin) return FALSE; if (m_Step==0) return FALSE; /* Space discretization */ Grid=new GRID**[m_Step]; for(UINT i=0;i=MC_MAX_VERTEX) return; m_VertexBuffer[m_nVertex].p=CELL[TriTable[CubeIndex][i+j]]; Index=m_nVertex; m_nVertex++; } if(m_nIndex>=MC_MAX_INDEX) return; m_IndexBuffer[m_nIndex]=Index; m_nIndex++; } } } //************************************************************************ // Interpolate in the cell...more precise //************************************************************************ VECTOR CMarchingCube::VertexInterpolate(VECTOR P1,VECTOR P2,double ValP1,double ValP2) { double mu; VECTOR P; if (fabs(m_IsoLevel-ValP1) < 0.000001) return(P1); if (fabs(m_IsoLevel-ValP2) < 0.000001) return(P2); if (fabs(ValP1-ValP2) < 0.000001) return(P1); mu = (m_IsoLevel - ValP1) / (ValP2 - ValP1); P.x = P1.x + mu * (P2.x - P1.x); P.y = P1.y + mu * (P2.y - P1.y); P.z = P1.z + mu * (P2.z - P1.z); return(P); } //************************************************************************ // Compute normals for each triangles //************************************************************************ void CMarchingCube::ComputeNormals() { double dpx,dpy,dpz,norme; double d=0.1; ISOVERTEX V1,V2; for(ULONG i=0;i