$search
00001 #ifndef HULL_LIB_H 00002 00003 #define HULL_LIB_H 00004 00005 00062 namespace ConvexDecomposition 00063 { 00064 00065 class HullResult 00066 { 00067 public: 00068 HullResult(void) 00069 { 00070 mPolygons = true; 00071 mNumOutputVertices = 0; 00072 mOutputVertices = 0; 00073 mNumFaces = 0; 00074 mNumIndices = 0; 00075 mIndices = 0; 00076 } 00077 bool mPolygons; // true if indices represents polygons, false indices are triangles 00078 unsigned int mNumOutputVertices; // number of vertices in the output hull 00079 double *mOutputVertices; // array of vertices, 3 doubles each x,y,z 00080 unsigned int mNumFaces; // the number of faces produced 00081 unsigned int mNumIndices; // the total number of indices 00082 unsigned int *mIndices; // pointer to indices. 00083 00084 // If triangles, then indices are array indexes into the vertex list. 00085 // If polygons, indices are in the form (number of points in face) (p1, p2, p3, ..) etc.. 00086 }; 00087 00088 class FHullResult 00089 { 00090 public: 00091 FHullResult(const HullResult &r) 00092 { 00093 mPolygons = r.mPolygons; 00094 mNumOutputVertices = r.mNumOutputVertices; 00095 mNumFaces = r.mNumFaces; 00096 mNumIndices = r.mNumIndices; 00097 mIndices = 0; 00098 mOutputVertices = 0; 00099 if ( mNumIndices ) 00100 { 00101 mIndices = new unsigned int[mNumIndices]; 00102 memcpy(mIndices,r.mIndices,sizeof(unsigned int)*mNumIndices); 00103 } 00104 if ( mNumOutputVertices ) 00105 { 00106 mOutputVertices = new float[mNumOutputVertices*3]; 00107 const double *src = r.mOutputVertices; 00108 float *dst = mOutputVertices; 00109 for (unsigned int i=0; i<mNumOutputVertices; i++) 00110 { 00111 dst[0] = (float) src[0]; 00112 dst[1] = (float) src[1]; 00113 dst[2] = (float) src[2]; 00114 dst+=3; 00115 src+=3; 00116 } 00117 } 00118 } 00119 ~FHullResult(void) 00120 { 00121 delete mIndices; 00122 delete mOutputVertices; 00123 } 00124 bool mPolygons; // true if indices represents polygons, false indices are triangles 00125 unsigned int mNumOutputVertices; // number of vertices in the output hull 00126 float *mOutputVertices; // array of vertices, 3 doubles each x,y,z 00127 unsigned int mNumFaces; // the number of faces produced 00128 unsigned int mNumIndices; // the total number of indices 00129 unsigned int *mIndices; // pointer to indices. 00130 00131 // If triangles, then indices are array indexes into the vertex list. 00132 // If polygons, indices are in the form (number of points in face) (p1, p2, p3, ..) etc.. 00133 }; 00134 00135 enum HullFlag 00136 { 00137 QF_TRIANGLES = (1<<0), // report results as triangles, not polygons. 00138 QF_REVERSE_ORDER = (1<<1), // reverse order of the triangle indices. 00139 QF_SKIN_WIDTH = (1<<2), // extrude hull based on this skin width 00140 QF_DEFAULT = 0 00141 }; 00142 00143 00144 class HullDesc 00145 { 00146 public: 00147 HullDesc(void) 00148 { 00149 mFlags = QF_DEFAULT; 00150 mVcount = 0; 00151 mVertices = 0; 00152 mVertexStride = 0; 00153 mNormalEpsilon = 0.001f; 00154 mMaxVertices = 4096; // maximum number of points to be considered for a convex hull. 00155 mSkinWidth = 0.01f; // default is one centimeter 00156 }; 00157 00158 HullDesc(HullFlag flag, 00159 unsigned int vcount, 00160 const double *vertices, 00161 unsigned int stride) 00162 { 00163 mFlags = flag; 00164 mVcount = vcount; 00165 mVertices = vertices; 00166 mVertexStride = stride; 00167 mNormalEpsilon = 0.001f; 00168 mMaxVertices = 4096; 00169 mSkinWidth = 0.01f; // default is one centimeter 00170 } 00171 00172 bool HasHullFlag(HullFlag flag) const 00173 { 00174 if ( mFlags & flag ) return true; 00175 return false; 00176 } 00177 00178 void SetHullFlag(HullFlag flag) 00179 { 00180 mFlags|=flag; 00181 } 00182 00183 void ClearHullFlag(HullFlag flag) 00184 { 00185 mFlags&=~flag; 00186 } 00187 00188 unsigned int mFlags; // flags to use when generating the convex hull. 00189 unsigned int mVcount; // number of vertices in the input point cloud 00190 const double *mVertices; // the array of vertices. 00191 unsigned int mVertexStride; // the stride of each vertex, in bytes. 00192 double mNormalEpsilon; // the epsilon for removing duplicates. This is a normalized value, if normalized bit is on. 00193 double mSkinWidth; 00194 unsigned int mMaxVertices; // maximum number of vertices to be considered for the hull! 00195 }; 00196 00197 enum HullError 00198 { 00199 QE_OK, // success! 00200 QE_FAIL // failed. 00201 }; 00202 00203 // This class is used when converting a convex hull into a triangle mesh. 00204 class ConvexHullVertex 00205 { 00206 public: 00207 double mPos[3]; 00208 double mNormal[3]; 00209 double mTexel[2]; 00210 }; 00211 00212 // A virtual interface to receive the triangles from the convex hull. 00213 class ConvexHullTriangleInterface 00214 { 00215 public: 00216 virtual void ConvexHullTriangle(const ConvexHullVertex &v1,const ConvexHullVertex &v2,const ConvexHullVertex &v3) = 0; 00217 }; 00218 00219 00220 00221 class HullLibrary 00222 { 00223 public: 00224 00225 HullError CreateConvexHull(const HullDesc &desc, // describes the input request 00226 HullResult &result); // contains the resulst 00227 00228 HullError ReleaseResult(HullResult &result); // release memory allocated for this result, we are done with it. 00229 00230 // Utility function to convert the output convex hull as a renderable set of triangles. Unfolds the polygons into 00231 // individual triangles, compute the vertex normals, and projects some texture co-ordinates. 00232 HullError CreateTriangleMesh(HullResult &answer,ConvexHullTriangleInterface *iface); 00233 private: 00234 double ComputeNormal(double *n,const double *A,const double *B,const double *C); 00235 void AddConvexTriangle(ConvexHullTriangleInterface *callback,const double *p1,const double *p2,const double *p3); 00236 00237 void BringOutYourDead(const double *verts,unsigned int vcount, double *overts,unsigned int &ocount,unsigned int *indices,unsigned indexcount); 00238 00239 bool CleanupVertices(unsigned int svcount, 00240 const double *svertices, 00241 unsigned int stride, 00242 unsigned int &vcount, // output number of vertices 00243 double *vertices, // location to store the results. 00244 double normalepsilon, 00245 double *scale); 00246 }; 00247 00248 }; 00249 00250 #endif