Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #ifndef __VCG_CREASE_CUT
00025 #define __VCG_CREASE_CUT
00026 #include<vcg/simplex/face/jumping_pos.h>
00027 #include<vcg/complex/algorithms/update/normal.h>
00028 namespace vcg {
00029 namespace tri {
00030
00034 template<class MESH_TYPE>
00035 void CreaseCut(MESH_TYPE &m, float angleRad)
00036 {
00037 tri::UpdateFlags<MESH_TYPE>::FaceFauxSignedCrease(m, -angleRad, angleRad);
00038 CutMeshAlongNonFauxEdges(m);
00039 }
00040
00049 template<class MESH_TYPE>
00050 void CutMeshAlongNonFauxEdges(MESH_TYPE &m)
00051 {
00052 typedef typename MESH_TYPE::FaceIterator FaceIterator;
00053 typedef typename MESH_TYPE::FaceType FaceType;
00054
00055 tri::Allocator<MESH_TYPE>::CompactVertexVector(m);
00056 tri::Allocator<MESH_TYPE>::CompactFaceVector(m);
00057 tri::RequireFFAdjacency(m);
00058
00059 tri::UpdateFlags<MESH_TYPE>::VertexClearV(m);
00060 std::vector<int> indVec(m.fn*3,-1);
00061 int newVertexCounter=m.vn;
00062 int startVn=m.vn;
00063 for(FaceIterator fi=m.face.begin();fi!=m.face.end();++fi)
00064 {
00065 for(int j=0;j<3;++j)
00066 if(!(*fi).V(j)->IsV() )
00067 {
00068 (*fi).V(j)->SetV();
00069
00070 face::JumpingPos<FaceType> iPos(&*fi,j,(*fi).V(j));
00071 size_t vertInd = Index(m, iPos.V());
00072 bool isBorderVertex = iPos.FindBorder();
00073 face::JumpingPos<FaceType> startPos=iPos;
00074 if(!isBorderVertex)
00075 {
00076 do {
00077 bool creaseFlag = !iPos.IsFaux();
00078 iPos.NextFE();
00079 if(creaseFlag) break;
00080 } while (startPos!=iPos);
00081 startPos=iPos;
00082 }
00083
00084 int locCreaseCounter=0;
00085 int curVertexCounter =vertInd;
00086
00087 do {
00088 size_t faceInd = Index(m,iPos.F());
00089 indVec[faceInd*3+ iPos.VInd()] = curVertexCounter;
00090
00091 if(!iPos.IsFaux())
00092 {
00093 ++locCreaseCounter;
00094 curVertexCounter=newVertexCounter;
00095 newVertexCounter++;
00096 }
00097 iPos.NextFE();
00098 } while (startPos!=iPos);
00099 if(locCreaseCounter>0 && (!isBorderVertex) ) newVertexCounter--;
00100
00101 }
00102 }
00103
00104
00105
00106 tri::Allocator<MESH_TYPE>::AddVertices(m,newVertexCounter-m.vn);
00107
00108 tri::UpdateFlags<MESH_TYPE>::VertexClearV(m);
00109 for(FaceIterator fi=m.face.begin();fi!=m.face.end();++fi)
00110 for(int j=0;j<3;++j)
00111 {
00112 size_t faceInd = Index(m, *fi);
00113 size_t vertInd = Index(m, (*fi).V(j));
00114 int curVertexInd = indVec[faceInd*3+ j];
00115 assert(curVertexInd != -1);
00116 assert(curVertexInd < m.vn);
00117 if(curVertexInd < startVn) assert(size_t(curVertexInd) == vertInd);
00118 if(curVertexInd >= startVn)
00119 {
00120 m.vert[curVertexInd].ImportData(*((*fi).V(j)));
00121 (*fi).V(j) = & m.vert[curVertexInd];
00122 }
00123 }
00124 }
00125
00126 }
00127 }
00128 #endif
00129