Back to home page

EIC code displayed by LXR

 
 

    


Warning, /include/Geant4/tools/tess_contour is written in an unsupported language. File is not indexed.

0001 // Copyright (C) 2010, Guy Barrand. All rights reserved.
0002 // See the file tools.license for terms.
0003 
0004 #ifndef tools_tess_contour
0005 #define tools_tess_contour
0006 
0007 #include "glutess/glutess"
0008 #include "lina/vec3f"
0009 #include "glprims"
0010 
0011 namespace tools {
0012 
0013 typedef struct {
0014   double pointA[3];
0015   double pointB[3];
0016   double pointC[3];
0017 } tess_triangle;
0018 
0019 class tess_contour {
0020 public:
0021   tess_contour(std::ostream& a_out,std::vector<tess_triangle>& a_triangles)
0022   :m_out(a_out)
0023   ,m_triangles(a_triangles)
0024   ,m_vertex_number(0),m_begin_type(gl::triangles()),m_error(false){}
0025   virtual ~tess_contour(){}
0026 protected:
0027   tess_contour(const tess_contour& a_from):m_out(a_from.m_out),m_triangles(a_from.m_triangles){}
0028   tess_contour& operator=(const tess_contour&){return *this;}
0029 public:
0030   void getFilledArea(const std::vector<std::vector<vec3f> >& aContour) {
0031     m_triangles.clear();
0032     m_combine_tmps.clear();
0033     m_error = false;
0034 
0035     GLUtesselator* tobj = gluNewTess();
0036 
0037     // NOTE : the gluTessCallback_<> are tools/glutess specific.
0038     ::gluTessCallback_GLU_TESS_VERTEX_DATA (tobj,vertexCallback);
0039     ::gluTessCallback_GLU_TESS_BEGIN_DATA  (tobj,beginCallback);
0040     ::gluTessCallback_GLU_TESS_END_DATA    (tobj,endCallback);
0041     ::gluTessCallback_GLU_TESS_ERROR_DATA  (tobj,errorCallback);
0042     ::gluTessCallback_GLU_TESS_COMBINE_DATA(tobj,combineCallback);
0043 
0044     ::gluTessProperty(tobj,(GLUenum)GLU_TESS_WINDING_RULE,GLU_TESS_WINDING_ODD);
0045 
0046     for(unsigned int a=0;a<aContour.size();a++) {
0047       if(aContour[a].size()<=1) continue; //should not happen.
0048       size_t vecSize = aContour[a].size()-1;
0049 
0050       typedef GLUdouble point[3];
0051       point* tab = new point[vecSize];
0052 
0053       ::gluTessBeginPolygon(tobj, this);
0054 
0055       ::gluTessBeginContour(tobj);
0056       for(size_t b=0;b<vecSize;b++) {
0057         tab[b][0] = aContour[a][b][0];
0058         tab[b][1] = aContour[a][b][1];
0059         tab[b][2] = aContour[a][b][2];
0060         ::gluTessVertex(tobj, tab[b],tab[b]);
0061       }
0062       ::gluTessEndContour(tobj);
0063 
0064       ::gluTessEndPolygon(tobj);
0065 
0066       delete [] tab;
0067     }
0068 
0069     ::gluDeleteTess(tobj);
0070 
0071     for(unsigned int index=0;index<m_combine_tmps.size();index++) {
0072       delete [] m_combine_tmps[index];
0073     }
0074     m_combine_tmps.clear();
0075 
0076     if(m_error) m_triangles.clear();
0077   }
0078 
0079 protected:
0080   void resetVertex() {m_vertex_number = 0;}
0081   void setBeginType(gl::mode_t aType) {m_begin_type = aType;}
0082   void setError(bool aError) {m_error = aError;}
0083   std::vector<double*>& combineTmps(){return m_combine_tmps;}
0084 
0085   void addVertex(const double* vertex) {
0086     // GLU_TRIANGLE_STRIP
0087     // Draws a connected group of triangles. One triangle is defined for each
0088     // vertex presented after the first two vertices. For odd n, vertices n,
0089     // n+1, and n+2 define triangle n. For even n, vertices n+1, n, and n+2
0090     // define triangle n. N-2 triangles are drawn.
0091     if (m_begin_type == gl::triangle_strip()) {
0092       m_tmp.pointC[0] = vertex[0];
0093       m_tmp.pointC[1] = vertex[1];
0094       m_tmp.pointC[2] = vertex[2];
0095 
0096       if(m_vertex_number>=2) m_triangles.push_back(m_tmp);
0097 
0098       int rest = m_vertex_number % 2;
0099       if(rest==1) {
0100         m_tmp.pointA[0] = vertex[0];
0101         m_tmp.pointA[1] = vertex[1];
0102         m_tmp.pointA[2] = vertex[2];
0103       } else {
0104         m_tmp.pointB[0] = vertex[0];
0105         m_tmp.pointB[1] = vertex[1];
0106         m_tmp.pointB[2] = vertex[2];
0107       }
0108       m_vertex_number++;
0109     }
0110 
0111     // GLU_TRIANGLE_FAN
0112     // Draws a connected group of triangles. One triangle is defined for each
0113     // vertex presented after the first two vertices. Vertices 1, n+1,
0114     // and n+2 define triangle n. N-2 triangles are drawn.
0115     else if (m_begin_type == gl::triangle_fan()) {
0116       if (m_vertex_number == 0) {
0117         m_tmp.pointA[0] = vertex[0];
0118         m_tmp.pointA[1] = vertex[1];
0119         m_tmp.pointA[2] = vertex[2];
0120       } else {
0121         m_tmp.pointC[0] = vertex[0];
0122         m_tmp.pointC[1] = vertex[1];
0123         m_tmp.pointC[2] = vertex[2];
0124 
0125         if (m_vertex_number >=2 ) {
0126           m_triangles.push_back(m_tmp);
0127         }
0128         m_tmp.pointB[0] = vertex[0];
0129         m_tmp.pointB[1] = vertex[1];
0130         m_tmp.pointB[2] = vertex[2];
0131       }
0132       m_vertex_number++;
0133     }
0134 
0135     // GLU_TRIANGLES
0136     // Treats each triplet of vertices as an independent triangle.
0137     // Vertices 3n-2, 3n-1, and 3n define triangle n. N/3 triangles are drawn.
0138     else if (m_begin_type == gl::triangles()) {
0139 
0140       int rest = m_vertex_number % 3;
0141 
0142       if(rest==2) {
0143         m_tmp.pointC[0] = vertex[0];
0144         m_tmp.pointC[1] = vertex[1];
0145         m_tmp.pointC[2] = vertex[2];
0146 
0147         m_triangles.push_back(m_tmp);
0148 
0149       } else if(rest==1) {
0150         m_tmp.pointB[0] = vertex[0];
0151         m_tmp.pointB[1] = vertex[1];
0152         m_tmp.pointB[2] = vertex[2];
0153 
0154       } else if(rest==0) {
0155         m_tmp.pointA[0] = vertex[0];
0156         m_tmp.pointA[1] = vertex[1];
0157         m_tmp.pointA[2] = vertex[2];
0158       }
0159       m_vertex_number++;
0160 
0161     } else {
0162       // do nothing and should never happend
0163     }
0164   }
0165 protected:
0166   typedef GLUvoid(*Func)();
0167 
0168   static void
0169   beginCallback(GLUenum aWhich,GLUvoid * aThis) {
0170     tess_contour* This = (tess_contour*)aThis;
0171     This->setBeginType(aWhich);
0172     This->resetVertex();
0173   }
0174 
0175   static void
0176   errorCallback(GLUenum aErrorCode,GLUvoid * aThis) {
0177     tess_contour* This = (tess_contour*)aThis;
0178     This->m_out << "tools::tess_contour::errorCallback : " << aErrorCode << std::endl;
0179     This->setError(true);
0180   }
0181 
0182   static void
0183   endCallback(void*){}
0184 
0185   static void
0186   vertexCallback(GLUvoid *vertex,GLUvoid* aThis) {
0187     tess_contour* This = (tess_contour*)aThis;
0188     This->addVertex((double*)vertex);
0189   }
0190 
0191   static void
0192   combineCallback(GLUdouble coords[3],
0193                               void* /*vertex_data*/[4],
0194                               GLUfloat /*weight*/[4],
0195                               void** dataOut,
0196                               void* aThis) {
0197     tess_contour* This = (tess_contour*)aThis;
0198     double* vertex = new double[3];
0199     vertex[0] = coords[0];
0200     vertex[1] = coords[1];
0201     vertex[2] = coords[2];
0202     This->combineTmps().push_back(vertex);
0203     *dataOut = vertex;
0204   }
0205 
0206 protected:
0207   std::ostream& m_out;
0208   std::vector<tess_triangle>& m_triangles;
0209   tess_triangle m_tmp;
0210   unsigned int m_vertex_number;
0211   gl::mode_t m_begin_type;
0212   bool m_error;
0213   std::vector<double*> m_combine_tmps;
0214 };
0215 
0216 }
0217 
0218 #endif