From: ageay Date: Fri, 25 Jan 2013 11:30:50 +0000 (+0000) Subject: Debugging orientCorrectlyPoly. More general implementation X-Git-Tag: V6_main_FINAL~414 X-Git-Url: http://git.salome-platform.org/gitweb/?a=commitdiff_plain;h=02607961182ec067486a80e3a058f64885018561;p=tools%2Fmedcoupling.git Debugging orientCorrectlyPoly. More general implementation --- diff --git a/src/MEDCoupling/MEDCouplingUMesh.cxx b/src/MEDCoupling/MEDCouplingUMesh.cxx index 465419372..327c593c8 100644 --- a/src/MEDCoupling/MEDCouplingUMesh.cxx +++ b/src/MEDCoupling/MEDCouplingUMesh.cxx @@ -4767,8 +4767,18 @@ void MEDCouplingUMesh::orientCorrectlyPolyhedrons() throw(INTERP_KERNEL::Excepti { INTERP_KERNEL::NormalizedCellType type=(INTERP_KERNEL::NormalizedCellType)conn[connI[i]]; if(type==INTERP_KERNEL::NORM_POLYHED) - if(!IsPolyhedronWellOriented(conn+connI[i]+1,conn+connI[i+1],coordsPtr)) - TryToCorrectPolyhedronOrientation(conn+connI[i]+1,conn+connI[i+1],coordsPtr); + { + try + { + if(!IsPolyhedronWellOriented(conn+connI[i]+1,conn+connI[i+1],coordsPtr)) + TryToCorrectPolyhedronOrientation(conn+connI[i]+1,conn+connI[i+1],coordsPtr); + } + catch(INTERP_KERNEL::Exception& e) + { + std::ostringstream oss; oss << "Something wrong in polyhedron #" << i << " : " << e.what(); + throw INTERP_KERNEL::Exception(oss.str().c_str()); + } + } } updateTime(); } @@ -6500,42 +6510,63 @@ void MEDCouplingUMesh::ComputeVecAndPtOfFace(double eps, const double *coords, c */ void MEDCouplingUMesh::TryToCorrectPolyhedronOrientation(int *begin, int *end, const double *coords) throw(INTERP_KERNEL::Exception) { - std::vector > edges; + std::list< std::pair > edgesOK,edgesFinished; std::size_t nbOfFaces=std::count(begin,end,-1)+1; - int *bgFace=begin; - std::vector isPerm(nbOfFaces); - for(std::size_t i=0;i isPerm(nbOfFaces,false);//field on faces False: I don't know, True : oriented + isPerm[0]=true; + int *bgFace=begin,*endFace=std::find(begin+1,end,-1); + std::size_t nbOfEdgesInFace=std::distance(bgFace,endFace); + for(std::size_t l=0;l p1(bgFace[l],bgFace[(l+1)%nbOfEdgesInFace]); edgesOK.push_back(p1); } + // + while(std::find(isPerm.begin(),isPerm.end(),false)!=isPerm.end()) { - int *endFace=std::find(bgFace+1,end,-1); - std::size_t nbOfEdgesInFace=std::distance(bgFace,endFace); - for(std::size_t l=0;l p1(bgFace[l],bgFace[(l+1)%nbOfEdgesInFace]); - edges.push_back(p1); - } - int *bgFace2=endFace+1; - for(std::size_t k=i+1;k p2(bgFace2[j],bgFace2[(j+1)%nbOfEdgesInFace2]); - if(std::find(edges.begin(),edges.end(),p2)!=edges.end()) + bool b; + for(std::size_t j=0;j tmp(nbOfEdgesInFace2-1); - std::copy(bgFace2+1,endFace2,tmp.rbegin()); - std::copy(tmp.begin(),tmp.end(),bgFace2+1); - isPerm[k]=true; - continue; + std::pair p1(bgFace[j],bgFace[(j+1)%nbOfEdgesInFace]); + std::pair p2(p1.second,p1.first); + bool b1=std::find(edgesOK.begin(),edgesOK.end(),p1)!=edgesOK.end(); + bool b2=std::find(edgesOK.begin(),edgesOK.end(),p2)!=edgesOK.end(); + if(b1 || b2) { b=b2; isPerm[i]=true; smthChanged++; break; } + } + if(isPerm[i]) + { + if(!b) + std::reverse(bgFace+1,endFace); + for(std::size_t j=0;j p1(bgFace[j],bgFace[(j+1)%nbOfEdgesInFace]); + std::pair p2(p1.second,p1.first); + if(std::find(edgesOK.begin(),edgesOK.end(),p1)!=edgesOK.end()) + { std::ostringstream oss; oss << "Face #" << j << " of polyhedron looks bad !"; throw INTERP_KERNEL::Exception(oss.str().c_str()); } + if(std::find(edgesFinished.begin(),edgesFinished.end(),p1)!=edgesFinished.end() || std::find(edgesFinished.begin(),edgesFinished.end(),p2)!=edgesFinished.end()) + { std::ostringstream oss; oss << "Face #" << j << " of polyhedron looks bad !"; throw INTERP_KERNEL::Exception(oss.str().c_str()); } + std::list< std::pair >::iterator it=std::find(edgesOK.begin(),edgesOK.end(),p2); + if(it!=edgesOK.end()) + { + edgesOK.erase(it); + edgesFinished.push_back(p1); + } + else + edgesOK.push_back(p1); + } } } - bgFace2=endFace2+1; + bgFace=endFace+1; } - bgFace=endFace+1; + if(smthChanged==0) + { throw INTERP_KERNEL::Exception("The polyhedron looks too bad to be repaired !"); } } + if(!edgesOK.empty()) + { throw INTERP_KERNEL::Exception("The polyhedron looks too bad to be repaired : Some edges are shared only once !"); } if(INTERP_KERNEL::calculateVolumeForPolyh2(begin,(int)std::distance(begin,end),coords)<-EPS_FOR_POLYH_ORIENTATION) {//not lucky ! The first face was not correctly oriented : reorient all faces... bgFace=begin; diff --git a/src/MEDCoupling_Swig/MEDCouplingBasicsTest.py b/src/MEDCoupling_Swig/MEDCouplingBasicsTest.py index 34444816a..cdae0a4cb 100644 --- a/src/MEDCoupling_Swig/MEDCouplingBasicsTest.py +++ b/src/MEDCoupling_Swig/MEDCouplingBasicsTest.py @@ -10818,6 +10818,28 @@ class MEDCouplingBasicsTest(unittest.TestCase): pass pass + def testSwigCellOrientation1(self): + coords=DataArrayDouble([-0.21606,-0.10803,0.29999999999999999,-0.21606,-0.10803,0.37700000000000006,0,-0.10803,0.29999999999999999,0,-0.10803,0.37700000000000006,0,0.10803,0.29999999999999999,0,0.10803,0.37700000000000006,-0.21606,0.10803,0.29999999999999999,-0.21606,0.10803,0.37700000000000006,0,0.03601,0.29999999999999999,0,0.03601,0.37700000000000006,0,-0.03601,0.29999999999999999,0,-0.03601,0.37700000000000006],12,3) + conn=[[0,2,10,8,4,6],[1,3,11,9,5,7],[0,1,3,2],[2,3,11,10],[10,11,9,8],[8,9,5,4],[4,5,7,6],[6,7,1,0]] + for i in xrange(256): + mesh=MEDCouplingUMesh("FluidMesh_1",3); + mesh.allocateCells(0) + conn2=[elt[:] for elt in conn] + code=bin(i)[2:] ; code='0'*(8-len(code))+code + for face,rev in zip(conn2,code): + if bool(int(rev)): + face.reverse() + pass + pass + conn3=[elt+[-1] for elt in conn2] + conn3=sum(conn3,[])[:-1] + mesh.insertNextCell(NORM_POLYHED,conn3) + mesh.setCoords(coords) + mesh.orientCorrectlyPolyhedrons() + self.assertTrue(mesh.getBarycenterAndOwner().isEqual(DataArrayDouble([-0.10803,0.,0.3385],1,3),1e-12)) + pass + pass + def setUp(self): pass pass