23 #ifndef __VCGLIB_APPEND 
   24 #define __VCGLIB_APPEND 
   26 #include <vcg/complex/allocate.h> 
   27 #include <vcg/complex/algorithms/update/selection.h> 
   38 template<
class MeshLeft, 
class ConstMeshRight>
 
   42  typedef typename MeshLeft::ScalarType          ScalarLeft;
 
   43  typedef typename MeshLeft::CoordType               CoordLeft;
 
   44  typedef typename MeshLeft::VertexType          VertexLeft;
 
   45  typedef typename MeshLeft::EdgeType                EdgeLeft;
 
   46  typedef typename MeshLeft::FaceType                FaceLeft;
 
   47  typedef typename MeshLeft::HEdgeType               HEdgeLeft;
 
   48  typedef typename MeshLeft::TetraType       TetraLeft;
 
   49  typedef typename MeshLeft::VertexPointer       VertexPointerLeft;
 
   50  typedef typename MeshLeft::VertexIterator  VertexIteratorLeft;
 
   51  typedef typename MeshLeft::EdgeIterator        EdgeIteratorLeft;
 
   52  typedef typename MeshLeft::HEdgeIterator       HEdgeIteratorLeft;
 
   53  typedef typename MeshLeft::FaceIterator        FaceIteratorLeft;
 
   54  typedef typename MeshLeft::TetraIterator   TetraIteratorLeft;
 
   57  typedef typename ConstMeshRight::ScalarType     ScalarRight;
 
   58  typedef typename ConstMeshRight::CoordType      CoordRight;
 
   59  typedef typename ConstMeshRight::VertexType     VertexRight;
 
   60  typedef typename ConstMeshRight::EdgeType       EdgeRight;
 
   61  typedef typename ConstMeshRight::HEdgeType      HEdgeRight;
 
   62  typedef typename ConstMeshRight::FaceType       FaceRight;
 
   63  typedef typename ConstMeshRight::TetraType      TetraRight;
 
   64  typedef typename ConstMeshRight::TetraPointer   TetraPointerRight;
 
   65  typedef typename ConstMeshRight::TetraIterator  TetraIteratorRight;
 
   66  typedef typename ConstMeshRight::VertexPointer  VertexPointerRight;
 
   67  typedef typename ConstMeshRight::VertexIterator VertexIteratorRight;
 
   68  typedef typename ConstMeshRight::EdgeIterator   EdgeIteratorRight;
 
   69  typedef typename ConstMeshRight::HEdgeIterator  HEdgeIteratorRight;
 
   70  typedef typename ConstMeshRight::FaceIterator   FaceIteratorRight;
 
   71  typedef typename ConstMeshRight::FacePointer    FacePointerRight;
 
   74    static size_t InvalidIndex() { 
return std::numeric_limits<size_t>::max(); }
 
   75         std::vector<size_t> vert, face, edge, hedge, tetra;
 
   78  static void ImportVertexAdj(MeshLeft &ml, 
const ConstMeshRight &mr, VertexLeft &vl,   
const VertexRight &vr, 
Remap &remap ){
 
   80    if(HasVEAdjacency(ml) && HasVEAdjacency(mr) && vr.cVEp() != 0){
 
   81      size_t i = Index(mr,vr.cVEp());
 
   82      vl.VEp() = (i>ml.edge.size())? 0 : &ml.edge[remap.edge[i]];
 
   87    if(HasPerVertexVFAdjacency(ml) && HasPerVertexVFAdjacency(mr) && vr.cVFp() != 0 ){
 
   88      size_t i = Index(mr,vr.cVFp());
 
   89      vl.VFp() = (i>ml.face.size())? 0 :&ml.face[remap.face[i]];
 
   94    if(HasVHAdjacency(ml) && HasVHAdjacency(mr) && vr.cVHp() != 0){
 
   95      vl.VHp() = &ml.hedge[remap.hedge[Index(mr,vr.cVHp())]];
 
  100    if(HasVTAdjacency(ml) && HasVTAdjacency(mr) && vr.cVTp() != 0){
 
  101      size_t i = Index(mr, vr.cVTp());
 
  102      vl.VTp() = (i > ml.edge.size()) ? 0 : &ml.tetra[remap.tetra[i]];
 
  107  static void ImportEdgeAdj(MeshLeft &ml, 
const ConstMeshRight &mr, EdgeLeft &el, 
const EdgeRight &er, Remap &remap)
 
  110      if(HasEEAdjacency(ml) && HasEEAdjacency(mr))
 
  111        for(
unsigned int vi = 0; vi < 2; ++vi)
 
  113          size_t idx = Index(mr,er.cEEp(vi));
 
  114          el.EEp(vi) = (idx>ml.edge.size())? 0 : &ml.edge[remap.edge[idx]];
 
  115          el.EEi(vi) = er.cEEi(vi);
 
  119      if(HasEFAdjacency(ml) && HasEFAdjacency(mr)){
 
  120        size_t idx = Index(mr,er.cEFp());
 
  121        el.EFp() = (idx>ml.face.size())? 0 :&ml.face[remap.face[idx]];
 
  122        el.EFi() = er.cEFi();
 
  126      if(HasEHAdjacency(ml) && HasEHAdjacency(mr))
 
  127        el.EHp() = &ml.hedge[remap.hedge[Index(mr,er.cEHp())]];
 
  131  static void ImportFaceAdj(MeshLeft &ml, 
const ConstMeshRight &mr, FaceLeft &fl, 
const FaceRight &fr, Remap &remap )
 
  134    if(HasFEAdjacency(ml) && HasFEAdjacency(mr)){
 
  135      assert(fl.VN() == fr.VN());
 
  136      for( 
int vi = 0; vi < fl.VN(); ++vi ){
 
  137        size_t idx = remap.edge[Index(mr,fr.cFEp(vi))];
 
  138        if(idx!=Remap::InvalidIndex())
 
  139          fl.FEp(vi) = &ml.edge[idx];
 
  144    if(HasFFAdjacency(ml) && HasFFAdjacency(mr)){
 
  145      assert(fl.VN() == fr.VN());
 
  146      for( 
int vi = 0; vi < fl.VN(); ++vi ){
 
  147        size_t idx = remap.face[Index(mr,fr.cFFp(vi))];
 
  148        if(idx!=Remap::InvalidIndex()){
 
  149          assert(idx >= 0 && idx < ml.face.size());
 
  150          fl.FFp(vi) = &ml.face[idx];
 
  151          fl.FFi(vi) = fr.cFFi(vi);
 
  157     if(HasPerFaceVFAdjacency(ml) && HasPerFaceVFAdjacency(mr))
 
  159         assert(fl.VN() == fr.VN());
 
  160         for (
int vi = 0; vi < fl.VN(); ++vi)
 
  162             const auto * fp     = fr.cVFp(vi);
 
  163             const auto   vfindex = fr.cVFi(vi);
 
  164             size_t fidx = (fp == 
nullptr) ? Remap::InvalidIndex() : remap.face[Index(mr,fp)];
 
  166             if (fidx == Remap::InvalidIndex()) 
 
  169                 assert(fl.cVFi(vi) == -1);
 
  173                 assert(fidx >= 0 && fidx < ml.face.size());
 
  174                 fl.VFp(vi) = &ml.face[fidx];
 
  175                 fl.VFi(vi) = vfindex;
 
  181    if(HasFHAdjacency(ml) && HasFHAdjacency(mr))
 
  182      fl.FHp() = &ml.hedge[remap.hedge[Index(mr,fr.cFHp())]];
 
  185  static void ImportHEdgeAdj(MeshLeft &ml, 
const ConstMeshRight &mr, HEdgeLeft &hl, 
const HEdgeRight &hr, Remap &remap, 
bool  ){
 
  187    if(HasHVAdjacency(ml) && HasHVAdjacency(mr))
 
  188      hl.HVp() = &ml.vert[remap.vert[Index(mr,hr.cHVp())]];
 
  191    if(HasHEAdjacency(ml) && HasHEAdjacency(mr)){
 
  192      size_t idx = Index(mr,hr.cHEp()) ;
 
  193      hl.HEp() = (idx>ml.edge.size())? 0 : &ml.edge[remap.edge[idx]];
 
  197    if(HasHFAdjacency(ml) && HasHFAdjacency(mr)){
 
  198      size_t idx = Index(mr,hr.cHFp());
 
  199      hl.HFp() = (idx>ml.face.size())? 0 :&ml.face[remap.face[idx]];
 
  204    if(HasHOppAdjacency(ml) && HasHOppAdjacency(mr))
 
  205      hl.HOp() = &ml.hedge[remap.hedge[Index(mr,hr.cHOp())]];
 
  208    if(HasHNextAdjacency(ml) && HasHNextAdjacency(mr))
 
  209      hl.HNp() = &ml.hedge[remap.hedge[Index(mr,hr.cHNp())]];
 
  212    if(HasHPrevAdjacency(ml) && HasHPrevAdjacency(mr))
 
  213      hl.HPp() = &ml.hedge[remap.hedge[Index(mr,hr.cHPp())]];
 
  216   static void ImportTetraAdj(MeshLeft &ml, 
const ConstMeshRight &mr, TetraLeft &tl, 
const TetraRight &tr, Remap &remap )
 
  219    if(HasTTAdjacency(ml) && HasTTAdjacency(mr)){
 
  220      for( 
int vi = 0; vi < 4; ++vi ){
 
  221        size_t idx = remap.tetra[Index(mr,tr.cTTp(vi))];
 
  222        if(idx != Remap::InvalidIndex()){
 
  223          tl.TTp(vi) = &ml.tetra[idx];
 
  224          tl.TTi(vi) = tr.cTTi(vi);
 
  253 static void Mesh(MeshLeft& ml, ConstMeshRight& mr, 
const bool selected = 
false, 
const bool adjFlag = 
false)
 
  262     assert(adjFlag == 
false || ml.IsEmpty()); 
 
  290         const ConstMeshRight& mr,
 
  291         const bool selected = 
false,
 
  292         const bool adjFlag = 
false)
 
  300     remap.vert.resize(mr.vert.size(), Remap::InvalidIndex());
 
  301     VertexIteratorLeft vp;
 
  311         if(!selected || v.IsS())
 
  313             size_t ind=Index(mr,v);
 
  314             remap.vert[ind]=int(Index(ml,*vp));
 
  319     remap.edge.resize(mr.edge.size(), Remap::InvalidIndex());
 
  329         if(!selected || e.IsS()){
 
  330             size_t ind=Index(mr,e);
 
  331             remap.edge[ind]=int(Index(ml,*ep));
 
  337     remap.face.resize(mr.face.size(), Remap::InvalidIndex());
 
  347         if(!selected || f.IsS()){
 
  348             size_t ind=Index(mr,f);
 
  349             remap.face[ind]=int(Index(ml,*fp));
 
  355     remap.hedge.resize(mr.hedge.size(),Remap::InvalidIndex());
 
  359         if(!selected || he.IsS()){
 
  360             size_t ind=Index(mr,he);
 
  361             assert(remap.hedge[ind]==Remap::InvalidIndex());
 
  362             HEdgeIteratorLeft hp = Allocator<MeshLeft>::AddHEdges(ml,1);
 
  363             (*hp).ImportData(he);
 
  364             remap.hedge[ind]=Index(ml,*hp);
 
  368     remap.tetra.resize(mr.tetra.size(), Remap::InvalidIndex());
 
  372         if (!selected || t.IsS()) {
 
  373             size_t idx = Index(mr, t);
 
  374             assert (remap.tetra[idx] == Remap::InvalidIndex());
 
  375             TetraIteratorLeft tp = Allocator<MeshLeft>::AddTetras(ml, 1);
 
  377             remap.tetra[idx] = Index(ml, *tp);
 
  387     std::vector<unsigned int> mappingTextures(mr.textures.size());
 
  389     unsigned int baseMlT = ml.textures.size();
 
  390     for (
unsigned int i = 0; i < mr.textures.size(); ++i) {
 
  391         auto it = std::find(ml.textures.begin(), ml.textures.end(), mr.textures[i]);
 
  393         if (it == ml.textures.end()) {
 
  395             mappingTextures[i] = baseMlT++;
 
  396             ml.textures.push_back(mr.textures[i]);
 
  400             mappingTextures[i] = it - ml.textures.begin();
 
  409     bool vertTexFlag = HasPerVertexTexCoord(ml) && HasPerVertexTexCoord(mr);
 
  414         if(!selected || v.IsS()){
 
  415             VertexLeft &vl = ml.vert[remap.vert[Index(mr,v)]];
 
  418                 ImportVertexAdj(ml,mr,vl,v,remap);
 
  420                 if (size_t(v.T().n()) < mappingTextures.size()) {
 
  422                     vl.T().n() = mappingTextures[v.T().n()];
 
  426                     vl.T().n() = v.T().n();
 
  435         if(!selected || e.IsS()){
 
  436             ml.edge[remap.edge[Index(mr,e)]].ImportData(e);
 
  438             EdgeLeft &el = ml.edge[remap.edge[Index(mr,e)]];
 
  439             if(HasEVAdjacency(ml) && HasEVAdjacency(mr)){
 
  440                 el.V(0) = &ml.vert[remap.vert[Index(mr,e.cV(0))]];
 
  441                 el.V(1) = &ml.vert[remap.vert[Index(mr,e.cV(1))]];
 
  443             if(adjFlag) ImportEdgeAdj(ml,mr,el,e,remap);
 
  448     bool wedgeTexFlag = HasPerWedgeTexCoord(ml) && HasPerWedgeTexCoord(mr);
 
  453         if(!selected || f.IsS())
 
  455             FaceLeft &fl = ml.face[remap.face[Index(mr,f)]];
 
  457             if(HasFVAdjacency(ml) && HasFVAdjacency(mr)){
 
  458                 for(int i = 0; i < fl.VN(); ++i)
 
  459                     fl.V(i) = &ml.vert[remap.vert[Index(mr,f.cV(i))]];
 
  463                 for(int i = 0; i < 3; ++i){
 
  464                     if (size_t(f.WT(i).n()) < mappingTextures.size()){
 
  466                         fl.WT(i).n() = mappingTextures[f.WT(i).n()];
 
  470                         fl.WT(i).n() = f.WT(i).n();
 
  474             if(adjFlag)  ImportFaceAdj(ml,mr,ml.face[remap.face[Index(mr,f)]],f,remap);
 
  482         if(!selected || he.IsS()){
 
  483             ml.hedge[remap.hedge[Index(mr,he)]].ImportData(he);
 
  484             ImportHEdgeAdj(ml,mr,ml.hedge[remap.hedge[Index(mr,he)]],he,remap,selected);
 
  491         if(!selected || t.IsS())
 
  493             TetraLeft &tl = ml.tetra[remap.tetra[Index(mr,t)]];
 
  495             if(HasFVAdjacency(ml) && HasFVAdjacency(mr)){
 
  496                 for(int i = 0; i < 4; ++i)
 
  497                     tl.V(i) = &ml.vert[remap.vert[Index(mr,t.cV(i))]];
 
  500             if(adjFlag)  ImportTetraAdj(ml, mr, ml.tetra[remap.tetra[Index(mr,t)]], t, remap);
 
  516     typename std::set< PointerToAttribute >::iterator al, ar;
 
  519     for (al = ml.vert_attr.begin(); al != ml.vert_attr.end(); ++al)
 
  520         if(!(*al)._name.empty())
 
  522             ar = mr.vert_attr.find(*al);
 
  523             if (ar != mr.vert_attr.end())
 
  526                 for (
const auto & v : mr.vert)
 
  528                     if( !v.IsD() && (!selected || v.IsS()))
 
  529                         (*al)._handle->CopyValue(remap.vert[Index(mr,v)], id_r, (*ar)._handle);
 
  536     for (al = ml.edge_attr.begin(); al != ml.edge_attr.end(); ++al)
 
  537         if (!(*al)._name.empty())
 
  539             ar = mr.edge_attr.find(*al);
 
  540             if (ar!= mr.edge_attr.end())
 
  543                 for (
const auto & e : mr.edge)
 
  545                     if( !e.IsD() && (!selected || e.IsS()))
 
  546                         (*al)._handle->CopyValue(remap.edge[Index(mr,e)], id_r, (*ar)._handle);
 
  553     for (al = ml.face_attr.begin(); al != ml.face_attr.end(); ++al)
 
  554         if (!(*al)._name.empty())
 
  556             ar = mr.face_attr.find(*al);
 
  557             if (ar!= mr.face_attr.end())
 
  560                 for (
const auto & f : mr.face)
 
  562                     if( !f.IsD() && (!selected || f.IsS()))
 
  563                         (*al)._handle->CopyValue(remap.face[Index(mr,f)], id_r, (*ar)._handle);
 
  570     for (al = ml.tetra_attr.begin(); al != ml.tetra_attr.end(); ++al)
 
  571         if (!(*al)._name.empty())
 
  573             ar = mr.tetra_attr.find(*al);
 
  574             if (ar!= mr.tetra_attr.end())
 
  577                 for (
const auto & t: mr.tetra)
 
  579                     if( !t.IsD() && (!selected || t.IsS()))
 
  580                         (*al)._handle->CopyValue(remap.tetra[Index(mr, t)], id_r, (*ar)._handle);
 
  601 static void MeshCopy(MeshLeft& ml, ConstMeshRight& mr, 
bool selected=
false, 
const bool adjFlag = 
false)
 
  604     Mesh(ml,mr,selected,adjFlag);
 
  605     ml.bbox.Import(mr.bbox);
 
  608 static void MeshCopyConst(MeshLeft& ml, 
const ConstMeshRight& mr, 
bool selected=
false, 
const bool adjFlag = 
false)
 
  611     MeshAppendConst(ml,mr,selected,adjFlag);
 
  612     ml.bbox.Import(mr.bbox);
 
  619 static void Selected(MeshLeft& ml, ConstMeshRight& mr)
 
static EdgeIterator AddEdges(MeshType &m, size_t n, PointerUpdater< EdgePointer > &pu)
Add n edges to the mesh. Function to add n edges to the mesh. The elements are added always to the en...
Definition: allocate.h:333
 
static VertexIterator AddVertices(MeshType &m, size_t n, PointerUpdater< VertexPointer > &pu)
Add n vertices to the mesh. Function to add n vertices to the mesh. The elements are added always to ...
Definition: allocate.h:189
 
static FaceIterator AddFaces(MeshType &m, size_t n)
Function to add n faces to the mesh. First wrapper, with no parameters.
Definition: allocate.h:615
 
Class to safely duplicate and append (portion of) meshes.
Definition: append.h:40
 
static void MeshAppendConst(MeshLeft &ml, const ConstMeshRight &mr, const bool selected=false, const bool adjFlag=false)
MeshAppendConst.
Definition: append.h:288
 
static void MeshCopy(MeshLeft &ml, ConstMeshRight &mr, bool selected=false, const bool adjFlag=false)
Copy the second mesh over the first one. The first mesh is destroyed. If requested only the selected ...
Definition: append.h:601
 
static void Mesh(MeshLeft &ml, ConstMeshRight &mr, const bool selected=false, const bool adjFlag=false)
Append the second mesh to the first one.
Definition: append.h:253
 
static void Selected(MeshLeft &ml, ConstMeshRight &mr)
Append only the selected elements of second mesh to the first one.
Definition: append.h:619
 
static size_t VertexCount(const MeshType &m)
This function returns the number of selected vertices.
Definition: selection.h:300
 
static size_t EdgeCount(const MeshType &m)
This function returns the number of selected edges.
Definition: selection.h:290
 
static size_t FaceCount(const MeshType &m)
This function returns the number of selected faces.
Definition: selection.h:280
 
static size_t VertexFromEdgeLoose(MeshType &m, bool preserveSelection=false)
Select all the vertices that are touched by at least a single selected edge.
Definition: selection.h:399
 
static size_t VertexFromFaceLoose(MeshType &m, bool preserveSelection=false)
Select all the vertices that are touched by at least a single selected faces.
Definition: selection.h:386
 
void ForEachTetra(const MeshType &m, Callable action)
Definition: foreach.h:270
 
void ForEachEdge(const MeshType &m, Callable action)
Definition: foreach.h:222
 
void ForEachFace(const MeshType &m, Callable action)
Definition: foreach.h:78
 
void ForEachVertex(const MeshType &m, Callable action)
Definition: foreach.h:126
 
void ForEachHEdge(const MeshType &m, Callable action)
Definition: foreach.h:174
 
Definition: namespaces.dox:6