From 4e878d8ed8723b14456cef32a32dfa37cd1a2758 Mon Sep 17 00:00:00 2001 From: Pierre Kraemer Date: Wed, 12 Feb 2014 18:17:04 +0100 Subject: [PATCH] template in the dart/cell markers --- include/Algo/Render/GL2/topo3PrimalRender.hpp | 13 +- include/Algo/Render/GL2/topoRender.hpp | 6 +- include/Container/containerBrowser.h | 7 +- include/Container/containerBrowser.hpp | 81 +- include/Topology/generic/cellmarker.h | 178 +- include/Topology/generic/dartmarker.h | 276 ++- include/Topology/generic/genericmap.h | 133 +- include/Topology/generic/genericmap.hpp | 136 +- include/Topology/generic/mapMono.h | 102 +- include/Topology/generic/mapMono.hpp | 135 ++ include/Topology/generic/mapMulti.h | 102 +- include/Topology/generic/mapMulti.hpp | 180 +- include/Topology/generic/traversor3Virt.h | 16 +- include/Topology/generic/traversor3Virt.hpp | 12 +- include/Topology/generic/traversorCell.h | 4 +- include/Topology/generic/traversorCell.hpp | 6 +- include/Topology/generic/traversorCellVirt.h | 6 +- .../Topology/generic/traversorCellVirt.hpp | 6 +- include/Topology/map/map1.hpp | 8 +- include/Topology/map/map2.hpp | 12 +- include/Topology/map/map3.h | 8 - include/Topology/map/map3.hpp | 1603 ++++++++++++++- src/Topology/generic/genericmap.cpp | 396 +--- src/Topology/generic/mapMono.cpp | 181 ++ src/Topology/generic/mapMulti.cpp | 181 ++ src/Topology/map/embeddedMap2.cpp | 12 + src/Topology/map/embeddedMap3.cpp | 8 +- src/Topology/map/map1.cpp | 30 - src/Topology/map/map2.cpp | 69 - src/Topology/map/map3.cpp | 1727 ----------------- 30 files changed, 2810 insertions(+), 2824 deletions(-) delete mode 100644 src/Topology/map/map1.cpp delete mode 100644 src/Topology/map/map2.cpp delete mode 100644 src/Topology/map/map3.cpp diff --git a/include/Algo/Render/GL2/topo3PrimalRender.hpp b/include/Algo/Render/GL2/topo3PrimalRender.hpp index ef48f1ca..1f167a30 100644 --- a/include/Algo/Render/GL2/topo3PrimalRender.hpp +++ b/include/Algo/Render/GL2/topo3PrimalRender.hpp @@ -125,9 +125,6 @@ void Topo3PrimalRender::updateData(typename PFP::MAP& mapx, const EMBV& position typedef typename PFP::REAL REAL; typedef Geom::Vec3f VEC3F; - Map3& map = dynamic_cast(mapx); // TODO reflechir comment virer ce warning quand on compile avec PFP::MAP=Map3 - - if (m_attIndex.map() != &mapx) m_attIndex = mapx.template getAttribute("dart_index"); if (!m_attIndex.isValid()) @@ -197,7 +194,7 @@ void Topo3PrimalRender::updateData(typename PFP::MAP& mapx, const EMBV& position *positionDartBuf++ = PFP::toVec3f(P); *positionDartBuf++ = PFP::toVec3f(PP); - if (map.isBoundaryMarked3(d)) + if (mapx.isBoundaryMarked3(d)) { *colorDartBuf++ = m_boundaryDartsColor; *colorDartBuf++ = m_boundaryDartsColor; @@ -216,8 +213,8 @@ void Topo3PrimalRender::updateData(typename PFP::MAP& mapx, const EMBV& position *positionDartBuf++ = PFP::toVec3f(Q); *positionDartBuf++ = PFP::toVec3f(QQ); - Dart dx = map.phi3(d); - if (map.isBoundaryMarked3(dx)) + Dart dx = mapx.phi3(d); + if (mapx.isBoundaryMarked3(dx)) { *colorDartBuf++ = m_boundaryDartsColor; *colorDartBuf++ = m_boundaryDartsColor; @@ -251,9 +248,9 @@ void Topo3PrimalRender::updateData(typename PFP::MAP& mapx, const EMBV& position m_nbRel2=0; - for (Dart d = map.begin(); d != map.end(); map.next(d)) + for (Dart d = mapx.begin(); d != mapx.end(); mapx.next(d)) { - Dart e = map.phi2(map.phi3(d)); + Dart e = mapx.phi2(mapx.phi3(d)); //if (d < e) { diff --git a/include/Algo/Render/GL2/topoRender.hpp b/include/Algo/Render/GL2/topoRender.hpp index 924f143d..9404240c 100644 --- a/include/Algo/Render/GL2/topoRender.hpp +++ b/include/Algo/Render/GL2/topoRender.hpp @@ -66,14 +66,12 @@ void TopoRender::updateDataBoundary(typename PFP::MAP& map, const VertexAttribut template void TopoRender::updateData(typename PFP::MAP& map, const VertexAttribute& positions, float ke, float kf, bool withBoundary) { - Map2* ptrMap2 = dynamic_cast(&map); - if (ptrMap2 != NULL) + if (map.mapTypeName()[0] == "M") // "Map2" { updateDataMap(map, positions, ke, kf, withBoundary); return; } - GMap2* ptrGMap2 = dynamic_cast(&map); - if (ptrGMap2 != NULL) + if (map.mapTypeName()[0] == "G") // "GMap2" { updateDataGMap(map, positions, ke, kf, withBoundary); return; diff --git a/include/Container/containerBrowser.h b/include/Container/containerBrowser.h index 7381cc95..fcae12fa 100644 --- a/include/Container/containerBrowser.h +++ b/include/Container/containerBrowser.h @@ -37,15 +37,16 @@ namespace CGoGN * Browser that traverses all darts and jumps over * those not selected by the selector */ +template class DartContainerBrowserSelector : public ContainerBrowser { protected: AttributeContainer* m_cont ; const FunctorSelect* m_selector ; - AttribMap& m_map; + MAP& m_map; public: - DartContainerBrowserSelector(AttribMap& m, const FunctorSelect& fs); + DartContainerBrowserSelector(MAP& m, const FunctorSelect& fs); ~DartContainerBrowserSelector(); unsigned int begin() const; unsigned int end() const; @@ -54,6 +55,8 @@ public: void disable(); } ; + + template class ContainerBrowserCellMarked : public ContainerBrowser { diff --git a/include/Container/containerBrowser.hpp b/include/Container/containerBrowser.hpp index e7bc984c..e56a021e 100644 --- a/include/Container/containerBrowser.hpp +++ b/include/Container/containerBrowser.hpp @@ -21,57 +21,44 @@ * Contact information: cgogn@unistra.fr * * * *******************************************************************************/ + #include "Topology/generic/dart.h" #include "Topology/generic/attribmap.h" - namespace CGoGN { - -inline DartContainerBrowserSelector::DartContainerBrowserSelector(AttribMap& m, const FunctorSelect& fs): +template +inline DartContainerBrowserSelector::DartContainerBrowserSelector(MAP& m, const FunctorSelect& fs): m_map(m) { - if (GenericMap::isMultiRes()) - { - m_cont = &(m.getMRAttributeContainer()); - } - else - { - m_cont = &(m.getAttributeContainer()); - } + m_cont = &m.getDartContainer(); m_selector = fs.copy(); } -inline DartContainerBrowserSelector::~DartContainerBrowserSelector() +template +inline DartContainerBrowserSelector::~DartContainerBrowserSelector() { delete m_selector; } -inline unsigned int DartContainerBrowserSelector::begin() const +template +inline unsigned int DartContainerBrowserSelector::begin() const { - if (GenericMap::isMultiRes()) - { - unsigned int it = m_cont->realBegin() ; - while ( (it != m_cont->realEnd()) && !m_selector->operator()(m_map.indexDart(it)) ) - m_cont->realNext(it); - return it; - } - else - { - unsigned int it = m_cont->realBegin() ; - while ( (it != m_cont->realEnd()) && !m_selector->operator()(Dart(it)) ) - m_cont->realNext(it); - return it; - } + unsigned int it = m_cont->realBegin() ; + while ( (it != m_cont->realEnd()) && !m_selector->operator()(m_map.indexDart(it)) ) + m_cont->realNext(it); + return it; } -inline unsigned int DartContainerBrowserSelector::end() const +template +inline unsigned int DartContainerBrowserSelector::end() const { return m_cont->realEnd(); } -inline void DartContainerBrowserSelector::next(unsigned int& it) const +template +inline void DartContainerBrowserSelector::next(unsigned int& it) const { do { @@ -80,39 +67,55 @@ inline void DartContainerBrowserSelector::next(unsigned int& it) const while ( (it != m_cont->realEnd()) && !m_selector->operator()(Dart(it)) ) ; } - -inline void DartContainerBrowserSelector::enable() +template +inline void DartContainerBrowserSelector::enable() { m_cont->setContainerBrowser(this); } -inline void DartContainerBrowserSelector::disable() +template +inline void DartContainerBrowserSelector::disable() { m_cont->setContainerBrowser(NULL); } + + + + inline ContainerBrowserLinked::ContainerBrowserLinked(AttribMap& m, unsigned int orbit): - autoAttribute(true), m_first(0xffffffff), m_end(0xffffffff) + autoAttribute(true), + m_first(0xffffffff), + m_end(0xffffffff) { m_cont = &(m.getAttributeContainer(orbit)); m_links = m_cont->addAttribute("Browser_Links") ; } - inline ContainerBrowserLinked::ContainerBrowserLinked(AttributeContainer& c): - m_cont(&c), autoAttribute(true), m_first(0xffffffff), m_end(0xffffffff) + m_cont(&c), + autoAttribute(true), + m_first(0xffffffff), + m_end(0xffffffff) { m_links = m_cont->addAttribute("Browser_Links") ; } inline ContainerBrowserLinked::ContainerBrowserLinked(AttributeContainer& c, AttributeMultiVector* links): - m_cont(&c), m_links(links), autoAttribute(false), m_first(0xffffffff), m_end(0xffffffff) + m_cont(&c), + m_links(links), + autoAttribute(false), + m_first(0xffffffff), + m_end(0xffffffff) {} inline ContainerBrowserLinked::ContainerBrowserLinked(ContainerBrowserLinked& cbl): - m_cont(cbl.m_cont), m_links(cbl.m_links), m_first(0xffffffff), m_end(0xffffffff) + m_cont(cbl.m_cont), + m_links(cbl.m_links), + m_first(0xffffffff), + m_end(0xffffffff) {} inline ContainerBrowserLinked::~ContainerBrowserLinked() @@ -157,7 +160,6 @@ inline void ContainerBrowserLinked::pushBack(unsigned int it) } } - inline void ContainerBrowserLinked::enable() { m_cont->setContainerBrowser(this); @@ -181,13 +183,11 @@ inline ContainerBrowserCellMarked::ContainerBrowserCellMarked(AttribMap& m m_cont = &(m.getAttributeContainer()); } - template inline ContainerBrowserCellMarked::~ContainerBrowserCellMarked() { } - template inline unsigned int ContainerBrowserCellMarked::begin() const { @@ -226,5 +226,4 @@ inline void ContainerBrowserCellMarked::disable() m_cont->setContainerBrowser(NULL); } - } // namespace CGoGN diff --git a/include/Topology/generic/cellmarker.h b/include/Topology/generic/cellmarker.h index 3e8377ed..78862ee3 100644 --- a/include/Topology/generic/cellmarker.h +++ b/include/Topology/generic/cellmarker.h @@ -41,7 +41,6 @@ class CellMarkerGen friend class GenericMap ; protected: - GenericMap& m_map ; Mark m_mark ; AttributeMultiVector* m_markVector ; unsigned int m_thread ; @@ -49,15 +48,12 @@ protected: bool releaseOnDestruct ; public: - CellMarkerGen(GenericMap& map, unsigned int cell, unsigned int thread = 0) : - m_map(map), + CellMarkerGen(unsigned int cell, unsigned int thread = 0) : m_thread(thread), m_cell(cell), releaseOnDestruct(true) {} - - ~CellMarkerGen() {} @@ -66,6 +62,11 @@ public: void updateMarkVector(AttributeMultiVector* amv) { m_markVector = amv ; } +protected: + // protected copy constructor to forbid its usage + CellMarkerGen(const CellMarkerGen& /*cm*/) + {} + /** * set if the mark has to be release on destruction or not */ @@ -86,30 +87,36 @@ public: * generic class that allows the marking of cells * \warning no default constructor */ -template +template class CellMarkerBase : public CellMarkerGen { +protected: + MAP& m_map ; + public: /** * constructor * @param map the map on which we work */ - CellMarkerBase(GenericMap& map, unsigned int thread = 0) : CellMarkerGen(map, CELL, thread) + CellMarkerBase(MAP& map, unsigned int thread = 0) : + CellMarkerGen(CELL, thread), + m_map(map) { - if(!m_map.isOrbitEmbedded()) - m_map.addEmbedding() ; - m_mark = m_map.getMarkerSet(m_thread).getNewMark() ; - m_markVector = m_map.getMarkVector(m_thread) ; + if(!m_map.template isOrbitEmbedded()) + m_map.template addEmbedding() ; + m_mark = m_map.template getMarkerSet(m_thread).getNewMark() ; + m_markVector = m_map.template getMarkVector(m_thread) ; m_map.cellMarkers[m_thread].push_back(this) ; } - CellMarkerBase(const GenericMap& map, unsigned int thread = 0) : - CellMarkerGen(const_cast(map), CELL, thread) + CellMarkerBase(const MAP& map, unsigned int thread = 0) : + CellMarkerGen(CELL, thread), + m_map(const_cast(map)) { - if(!m_map.isOrbitEmbedded()) - m_map.addEmbedding() ; - m_mark = m_map.getMarkerSet(m_thread).getNewMark() ; - m_markVector = m_map.getMarkVector(m_thread) ; + if(!m_map.template isOrbitEmbedded()) + m_map.template addEmbedding() ; + m_mark = m_map.template getMarkerSet(m_thread).getNewMark() ; + m_markVector = m_map.template getMarkVector(m_thread) ; m_map.cellMarkers[m_thread].push_back(this) ; } @@ -117,7 +124,7 @@ public: { if(releaseOnDestruct) { - m_map.getMarkerSet(m_thread).releaseMark(m_mark) ; + m_map.template getMarkerSet(m_thread).releaseMark(m_mark) ; std::vector& cmg = m_map.cellMarkers[m_thread]; for(std::vector::iterator it = cmg.begin(); it != cmg.end(); ++it) @@ -134,7 +141,9 @@ public: protected: // protected copy constructor to forbid its usage - CellMarkerBase(const CellMarkerGen& cm) : CellMarkerGen(cm.m_map, CELL) + CellMarkerBase(const CellMarkerBase& cm) : + m_map(cm.m_map), + CellMarkerGen(CELL) {} public: @@ -143,7 +152,7 @@ public: */ inline void mark(Dart d) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); unsigned int a = m_map.getEmbedding(d) ; @@ -157,7 +166,7 @@ public: */ inline void unmark(Dart d) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); unsigned int a = m_map.getEmbedding(d) ; @@ -171,7 +180,7 @@ public: */ inline bool isMarked(Dart d) const { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); unsigned int a = m_map.getEmbedding(d) ; @@ -185,7 +194,7 @@ public: */ inline void mark(unsigned int em) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); m_markVector->operator[](em).setMark(m_mark) ; @@ -196,7 +205,7 @@ public: */ inline void unmark(unsigned int em) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); m_markVector->operator[](em).unsetMark(m_mark) ; @@ -207,7 +216,7 @@ public: */ inline bool isMarked(unsigned int em) const { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); if (em == EMBNULL) @@ -220,20 +229,20 @@ public: */ inline void markAll() { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); - AttributeContainer& cont = m_map.getAttributeContainer() ; + AttributeContainer& cont = m_map.template getAttributeContainer() ; for (unsigned int i = cont.begin(); i != cont.end(); cont.next(i)) m_markVector->operator[](i).setMark(m_mark) ; } inline bool isAllUnmarked() { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); - AttributeContainer& cont = m_map.getAttributeContainer() ; + AttributeContainer& cont = m_map.template getAttributeContainer() ; for (unsigned int i = cont.begin(); i != cont.end(); cont.next(i)) if(m_markVector->operator[](i).testMark(m_mark)) return false ; @@ -245,15 +254,15 @@ public: * class that allows the marking of cells * \warning no default constructor */ -template -class CellMarker : public CellMarkerBase +template +class CellMarker : public CellMarkerBase { public: - CellMarker(GenericMap& map, unsigned int thread = 0) : CellMarkerBase(map, thread) + CellMarker(MAP& map, unsigned int thread = 0) : CellMarkerBase(map, thread) {} - CellMarker(const GenericMap& map, unsigned int thread = 0) : - CellMarkerBase(map, thread) + CellMarker(const MAP& map, unsigned int thread = 0) : + CellMarkerBase(map, thread) {} ~CellMarker() @@ -262,7 +271,8 @@ public: } protected: - CellMarker(const CellMarker& cm) : CellMarkerBase(cm) + CellMarker(const CellMarker& cm) : + CellMarkerBase(cm) {} public: @@ -282,18 +292,19 @@ public: * the marked cells are stored to optimize the unmarking task at destruction * \warning no default constructor */ -template -class CellMarkerStore: public CellMarkerBase +template +class CellMarkerStore: public CellMarkerBase { protected: std::vector m_markedCells ; public: - CellMarkerStore(GenericMap& map, unsigned int thread = 0) : CellMarkerBase(map, thread) + CellMarkerStore(MAP& map, unsigned int thread = 0) : + CellMarkerBase(map, thread) {} - CellMarkerStore(const GenericMap& map, unsigned int thread = 0) : - CellMarkerBase(map, thread) + CellMarkerStore(const MAP& map, unsigned int thread = 0) : + CellMarkerBase(map, thread) {} ~CellMarkerStore() @@ -304,19 +315,20 @@ public: } protected: - CellMarkerStore(const CellMarkerStore& cm) : CellMarkerBase(cm) + CellMarkerStore(const CellMarkerStore& cm) : + CellMarkerBase(cm) {} public: inline void mark(Dart d) { - CellMarkerBase::mark(d) ; + CellMarkerBase::mark(d) ; m_markedCells.push_back(this->m_map.template getEmbedding(d)) ; } inline void mark(unsigned int em) { - CellMarkerBase::mark(em) ; + CellMarkerBase::mark(em) ; m_markedCells.push_back(em) ; } @@ -335,21 +347,21 @@ public: * the marked Darts are stored to optimize the unmarking task at destruction * \warning no default constructor */ -template -class CellMarkerMemo: public CellMarkerBase +template +class CellMarkerMemo: public CellMarkerBase { protected: std::vector m_markedDarts ; public: - CellMarkerMemo(GenericMap& map, unsigned int thread = 0) : CellMarkerBase(map, thread) + CellMarkerMemo(MAP& map, unsigned int thread = 0) : + CellMarkerBase(map, thread) {} - CellMarkerMemo(const GenericMap& map, unsigned int thread = 0) : - CellMarkerBase(map, thread) + CellMarkerMemo(const MAP& map, unsigned int thread = 0) : + CellMarkerBase(map, thread) {} - ~CellMarkerMemo() { unmarkAll() ; @@ -358,7 +370,8 @@ public: } protected: - CellMarkerMemo(const CellMarkerMemo& cm) : CellMarkerBase(cm) + CellMarkerMemo(const CellMarkerMemo& cm) : + CellMarkerBase(cm) {} public: @@ -366,7 +379,7 @@ public: { if(!this->isMarked(d)) { - CellMarkerBase::mark(d) ; + CellMarkerBase::mark(d) ; m_markedDarts.push_back(d) ; } } @@ -383,7 +396,7 @@ public: } - inline std::vector get_markedCells() + inline const std::vector& get_markedCells() { return m_markedDarts; } @@ -394,18 +407,18 @@ public: * the markers are not unmarked at destruction * \warning no default constructor */ -template -class CellMarkerNoUnmark: public CellMarkerBase +template +class CellMarkerNoUnmark: public CellMarkerBase { public: - CellMarkerNoUnmark(GenericMap& map, unsigned int thread = 0) : CellMarkerBase(map, thread) + CellMarkerNoUnmark(MAP& map, unsigned int thread = 0) : + CellMarkerBase(map, thread) {} - CellMarkerNoUnmark(const GenericMap& map, unsigned int thread = 0) : - CellMarkerBase(map, thread) + CellMarkerNoUnmark(const MAP& map, unsigned int thread = 0) : + CellMarkerBase(map, thread) {} - ~CellMarkerNoUnmark() { // assert(isAllUnmarked()) ; @@ -413,7 +426,8 @@ public: } protected: - CellMarkerNoUnmark(const CellMarkerNoUnmark& cm) : CellMarkerBase(cm) + CellMarkerNoUnmark(const CellMarkerNoUnmark& cm) : + CellMarkerBase(cm) {} public: @@ -428,17 +442,22 @@ public: } }; +// Selector and count functors testing for marker existence +/********************************************************/ /** * selector that say if a dart has its cell marked */ -template +template class SelectorCellMarked : public FunctorSelect { protected: - const CellMarkerBase& m_cmarker ; + const CellMarkerBase& m_cmarker ; + public: - SelectorCellMarked(const CellMarkerBase& cm) : m_cmarker(cm) {} + SelectorCellMarked(const CellMarkerBase& cm) : + m_cmarker(cm) + {} inline bool operator()(Dart d) const { @@ -449,44 +468,59 @@ public: inline FunctorSelect* copy() const { return new SelectorCellMarked(m_cmarker); } }; -template +template class SelectorCellUnmarked : public FunctorSelect { protected: - const CellMarkerBase& m_cmarker ; + const CellMarkerBase& m_cmarker ; + public: - SelectorCellUnmarked(const CellMarkerBase& cm) : m_cmarker(cm) {} + SelectorCellUnmarked(const CellMarkerBase& cm) : + m_cmarker(cm) + {} + inline bool operator()(Dart d) const { if (!m_cmarker.isMarked(d)) return true ; return false ; } - inline FunctorSelect* copy() const { return new SelectorCellUnmarked(m_cmarker); } + + inline FunctorSelect* copy() const + { + return new SelectorCellUnmarked(m_cmarker); + } }; // Functor version (needed for use with foreach_xxx) -template +template class FunctorCellIsMarked : public FunctorType { protected: - CellMarkerBase& m_marker; + CellMarkerBase& m_marker; + public: - FunctorCellIsMarked(CellMarkerBase& cm) : m_marker(cm) {} + FunctorCellIsMarked(CellMarkerBase& cm) : + m_marker(cm) + {} + inline bool operator()(Dart d) { return m_marker.isMarked(d); } }; -template +template class FunctorCellIsUnmarked : public FunctorType { protected: - CellMarkerBase& m_marker; + CellMarkerBase& m_marker; public: - FunctorCellIsUnmarked(CellMarkerBase& cm) : m_marker(cm) {} + FunctorCellIsUnmarked(CellMarkerBase& cm) : + m_marker(cm) + {} + inline bool operator()(Dart d) { return !m_marker.isMarked(d); diff --git a/include/Topology/generic/dartmarker.h b/include/Topology/generic/dartmarker.h index c4e68f93..06389662 100644 --- a/include/Topology/generic/dartmarker.h +++ b/include/Topology/generic/dartmarker.h @@ -42,38 +42,75 @@ class DartMarkerGen friend class GenericMap ; protected: - GenericMap& m_map ; Mark m_mark ; AttributeMultiVector* m_markVector ; unsigned int m_thread ; bool releaseOnDestruct ; +public: + /** + * constructor + */ + DartMarkerGen(unsigned int thread = 0) : + m_thread(thread), + releaseOnDestruct(true) + {} + + ~DartMarkerGen() + {} + + inline unsigned int getThread() { return m_thread ; } + + inline void updateMarkVector(AttributeMultiVector* amv) { m_markVector = amv ; } + +protected: + // protected copy constructor to forbid its usage + DartMarkerGen(const DartMarkerGen& /*dm*/) + {} + + /** + * set if the mark has to be release on destruction or not + */ + inline void setReleaseOnDestruct(bool b) + { + releaseOnDestruct = b ; + } +} ; + +template +class DartMarkerTmpl : public DartMarkerGen +{ +protected: + MAP& m_map ; + public: /** * constructor * @param map the map on which we work */ - DartMarkerGen(GenericMap& map, unsigned int thread = 0) : - m_map(map), m_thread(thread), releaseOnDestruct(true) + DartMarkerTmpl(MAP& map, unsigned int thread = 0) : + DartMarkerGen(thread), + m_map(map) { - m_mark = m_map.getMarkerSet(m_thread).getNewMark() ; + m_mark = m_map.template getMarkerSet(m_thread).getNewMark() ; m_markVector = m_map.getMarkVector(m_thread) ; m_map.dartMarkers[m_thread].push_back(this) ; } - DartMarkerGen(const GenericMap& map, unsigned int thread = 0) : - m_map(const_cast(map)), m_thread(thread), releaseOnDestruct(true) + DartMarkerTmpl(const MAP& map, unsigned int thread = 0) : + DartMarkerGen(thread), + m_map(const_cast(map)) { - m_mark = m_map.getMarkerSet(m_thread).getNewMark() ; - m_markVector = m_map.getMarkVector(m_thread) ; + m_mark = m_map.template getMarkerSet(m_thread).getNewMark() ; + m_markVector = m_map.template getMarkVector(m_thread) ; m_map.dartMarkers[m_thread].push_back(this) ; } - ~DartMarkerGen() + ~DartMarkerTmpl() { if (releaseOnDestruct) { - m_map.getMarkerSet(m_thread).releaseMark(m_mark) ; + m_map.template getMarkerSet(m_thread).releaseMark(m_mark) ; std::vector& dmg = m_map.dartMarkers[m_thread] ; for (std::vector::iterator it = dmg.begin(); it != dmg.end(); ++it) { @@ -87,30 +124,11 @@ public: } } - inline unsigned int getThread() - { - return m_thread ; - } - - inline void updateMarkVector(AttributeMultiVector* amv) - { - m_markVector = amv ; - } - protected: // protected copy constructor to forbid its usage - DartMarkerGen(const DartMarkerGen& dm) : + DartMarkerTmpl(const DartMarkerTmpl& dm) : m_map(dm.m_map) - { - } - - /** - * set if the mark has to be release on destruction or not - */ - inline void setReleaseOnDestruct(bool b) - { - releaseOnDestruct = b ; - } + {} public: /** @@ -118,7 +136,7 @@ public: */ inline void mark(Dart d) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); unsigned int d_index = m_map.dartIndex(d) ; m_markVector->operator[](d_index).setMark(m_mark) ; } @@ -128,7 +146,7 @@ public: */ inline void unmark(Dart d) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); unsigned int d_index = m_map.dartIndex(d) ; m_markVector->operator[](d_index).unsetMark(m_mark) ; } @@ -138,7 +156,7 @@ public: */ inline bool isMarked(Dart d) const { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); unsigned int d_index = m_map.dartIndex(d) ; return m_markVector->operator[](d_index).testMark(m_mark) ; } @@ -149,8 +167,8 @@ public: template inline void markOrbit(Dart d) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); - FunctorMark fm(m_map, m_mark, m_markVector) ; + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); + FunctorMark fm(m_map, m_mark, m_markVector) ; m_map.foreach_dart_of_orbit(d, fm, m_thread) ; } @@ -160,40 +178,18 @@ public: template inline void unmarkOrbit(Dart d) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); - FunctorUnmark fm(m_map, m_mark, m_markVector) ; + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); + FunctorUnmark fm(m_map, m_mark, m_markVector) ; m_map.foreach_dart_of_orbit(d, fm, m_thread) ; } -// /** -// * mark the darts of the given orbit of d in the parent map -// */ -// template -// void markOrbitInParent(unsigned int orbit, Dart d) -// { -// assert(m_map.getMarkerSet(DART, m_thread).testMark(m_mark)); -// FunctorMark fm(m_map, m_mark, m_map.getMarkVector(DART, m_thread)) ; -// foreach_dart_of_orbit_in_parent(dynamic_cast(&m_map), orbit, d, fm, m_thread); -// } -// -// /** -// * unmark the darts of the given orbit of d in the parent map -// */ -// template -// void unmarkOrbitInParent(unsigned int orbit, Dart d) -// { -// assert(m_map.getMarkerSet(DART, m_thread).testMark(m_mark)); -// FunctorUnmark fm(m_map, m_mark, m_map.getMarkVector(DART, m_thread)) ; -// foreach_dart_of_orbit_in_parent(dynamic_cast(&m_map), orbit, d, fm, m_thread); -// } - /** * mark all darts */ inline void markAll() { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); - AttributeContainer& cont = m_map.getAttributeContainer() ; + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); + AttributeContainer& cont = m_map.template getAttributeContainer() ; for (unsigned int i = cont.begin(); i != cont.end(); cont.next(i)) m_markVector->operator[](i).setMark(m_mark) ; } @@ -201,36 +197,35 @@ public: /** * unmark all darts */ -// virtual void unmarkAll() = 0 ; + virtual void unmarkAll() = 0 ; inline bool isAllUnmarked() { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(m_map.template getMarkerSet(m_thread).testMark(m_mark)); assert(m_markVector != NULL); - AttributeContainer& cont = m_map.getAttributeContainer() ; + AttributeContainer& cont = m_map.template getAttributeContainer() ; for (unsigned int i = cont.begin(); i != cont.end(); cont.next(i)) if (m_markVector->operator[](i).testMark(m_mark)) return false ; return true ; } -} ; +}; /** * class that allows the marking of darts * \warning no default constructor */ -class DartMarker : public DartMarkerGen +template +class DartMarker : public DartMarkerTmpl { public: + DartMarker(const MAP& map) : + DartMarkerTmpl(map) + {} - DartMarker(const GenericMap& map) : - DartMarkerGen(map) - { } - - DartMarker(const GenericMap& map, unsigned int thread) : - DartMarkerGen(map, thread) - { - } + DartMarker(const MAP& map, unsigned int thread) : + DartMarkerTmpl(map, thread) + {} ~DartMarker() { @@ -239,17 +234,16 @@ public: protected: DartMarker(const DartMarker& dm) : - DartMarkerGen(dm) - { - } + DartMarkerTmpl(dm) + {} public: inline void unmarkAll() { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); - AttributeContainer& cont = m_map.getAttributeContainer() ; + assert(this->m_map.template getMarkerSet(this->m_thread).testMark(this->m_mark)); + AttributeContainer& cont = this->m_map.template getAttributeContainer() ; for (unsigned int i = cont.realBegin(); i != cont.realEnd(); cont.realNext(i)) - m_markVector->operator[](i).unsetMark(m_mark) ; + this->m_markVector->operator[](i).unsetMark(this->m_mark) ; } } ; @@ -258,21 +252,20 @@ public: * the marked darts are stored to optimize the unmarking task at destruction * \warning no default constructor */ -class DartMarkerStore : public DartMarkerGen +template +class DartMarkerStore : public DartMarkerTmpl { protected: std::vector m_markedDarts ; public: - DartMarkerStore(const GenericMap& map) : - DartMarkerGen(map) - { } - - - DartMarkerStore(const GenericMap& map, unsigned int thread) : - DartMarkerGen(map, thread) - { } + DartMarkerStore(const MAP& map) : + DartMarkerTmpl(map) + {} + DartMarkerStore(const MAP& map, unsigned int thread) : + DartMarkerTmpl(map, thread) + {} ~DartMarkerStore() { @@ -283,45 +276,31 @@ public: protected: DartMarkerStore(const DartMarkerStore& dm) : - DartMarkerGen(dm), m_markedDarts(dm.m_markedDarts) - { - } + DartMarkerTmpl(dm), + m_markedDarts(dm.m_markedDarts) + {} public: inline void mark(Dart d) { - DartMarkerGen::mark(d) ; - unsigned int d_index = m_map.dartIndex(d) ; + DartMarkerTmpl::mark(d) ; + unsigned int d_index = this->m_map.dartIndex(d) ; m_markedDarts.push_back(d_index) ; } template inline void markOrbit(Dart d) { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); - FunctorMarkStore fm(m_map, m_mark, m_markVector, m_markedDarts) ; - m_map.foreach_dart_of_orbit(d, fm, m_thread) ; + assert(this->m_map.getMarkerSet(this->m_thread).testMark(this->m_mark)); + FunctorMarkStore fm(this->m_map, this->m_mark, this->m_markVector, m_markedDarts) ; + this->m_map.foreach_dart_of_orbit(d, fm, this->m_thread) ; } -// template -// void markOrbitInParent(unsigned int orbit, Dart d) -// { -// assert(m_map.getMarkerSet(DART, m_thread).testMark(m_mark)); -// FunctorMarkStore fm(m_map, m_mark, m_map.getMarkVector(DART, m_thread), m_markedDarts) ; -// foreach_dart_of_orbit_in_parent(dynamic_cast(&m_map), orbit, d, fm, m_thread); -// } - -// void mark(unsigned int d) -// { -// DartMarkerGen::mark(d) ; -// m_markedDarts.push_back(d) ; -// } - inline void unmarkAll() { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); + assert(this->m_map.getMarkerSet(this->m_thread).testMark(this->m_mark)); for (std::vector::iterator it = m_markedDarts.begin(); it != m_markedDarts.end(); ++it) - m_markVector->operator[](*it).unsetMark(m_mark) ; + this->m_markVector->operator[](*it).unsetMark(this->m_mark) ; } } ; @@ -330,17 +309,17 @@ public: * the markers are not unmarked at destruction * \warning no default constructor */ -class DartMarkerNoUnmark : public DartMarkerGen +template +class DartMarkerNoUnmark : public DartMarkerTmpl { public: - DartMarkerNoUnmark(const GenericMap& map) : - DartMarkerGen(map) - { } + DartMarkerNoUnmark(const MAP& map) : + DartMarkerTmpl(map) + {} - - DartMarkerNoUnmark(const GenericMap& map, unsigned int th) : - DartMarkerGen(map, th) - { } + DartMarkerNoUnmark(const MAP& map, unsigned int thread) : + DartMarkerTmpl(map, thread) + {} ~DartMarkerNoUnmark() { @@ -350,55 +329,60 @@ public: protected: DartMarkerNoUnmark(const DartMarkerNoUnmark& dm) : - DartMarkerGen(dm) - { - } + DartMarkerTmpl(dm) + {} public: inline void unmarkAll() { - assert(m_map.getMarkerSet(m_thread).testMark(m_mark)); - AttributeContainer& cont = m_map.getAttributeContainer() ; + assert(this->m_map.getMarkerSet(this->m_thread).testMark(this->m_mark)); + AttributeContainer& cont = this->m_map.template getAttributeContainer() ; for (unsigned int i = cont.realBegin(); i != cont.realEnd(); cont.realNext(i)) - m_markVector->operator[](i).unsetMark(m_mark) ; + this->m_markVector->operator[](i).unsetMark(this->m_mark) ; } } ; // Selector and count functors testing for marker existence /********************************************************/ +template class SelectorMarked : public FunctorSelect { protected: - DartMarkerGen& m_marker ; + DartMarkerTmpl& m_marker ; + public: - SelectorMarked(DartMarkerGen& m) : + SelectorMarked(DartMarkerTmpl& m) : m_marker(m) - { - } + {} + inline bool operator()(Dart d) const { return m_marker.isMarked(d) ; } + inline FunctorSelect* copy() const { return new SelectorMarked(m_marker) ; } } ; +template class SelectorUnmarked : public FunctorSelect { protected: - DartMarkerGen& m_marker ; + DartMarkerTmpl& m_marker ; + public: - SelectorUnmarked(DartMarkerGen& m) : + SelectorUnmarked(DartMarkerTmpl& m) : m_marker(m) - { - } + {} + inline bool operator()(Dart d) const { return !m_marker.isMarked(d) ; } + inline FunctorSelect* copy() const { return new SelectorUnmarked(m_marker) ; @@ -407,30 +391,34 @@ public: // Functor version (needed for use with foreach_xxx) +template class FunctorIsMarked : public FunctorType { protected: - DartMarkerGen& m_marker ; + DartMarkerTmpl& m_marker ; + public: - FunctorIsMarked(DartMarkerGen& dm) : + FunctorIsMarked(DartMarkerTmpl& dm) : m_marker(dm) - { - } + {} + inline bool operator()(Dart d) { return m_marker.isMarked(d) ; } } ; +template class FunctorIsUnmarked : public FunctorType { protected: - DartMarkerGen& m_marker ; + DartMarkerTmpl& m_marker ; + public: - FunctorIsUnmarked(DartMarkerGen& dm) : + FunctorIsUnmarked(DartMarkerTmpl& dm) : m_marker(dm) - { - } + {} + inline bool operator()(Dart d) { return !m_marker.isMarked(d) ; diff --git a/include/Topology/generic/genericmap.h b/include/Topology/generic/genericmap.h index aa8a13d5..19066d76 100644 --- a/include/Topology/generic/genericmap.h +++ b/include/Topology/generic/genericmap.h @@ -50,7 +50,7 @@ namespace CGoGN class AttributeHandlerGen ; class DartMarkerGen ; class CellMarkerGen ; -template class CellMarkerBase ; +//template class CellMarkerBase ; class GenericMap { @@ -62,10 +62,9 @@ class GenericMap template friend class VolumeAutoAttribute ; friend class DartMarkerGen ; friend class CellMarkerGen ; - template friend class CellMarkerBase ; + template friend class CellMarkerBase ; protected: - /** * Attributes Containers */ @@ -109,7 +108,6 @@ protected: std::vector dartMarkers[NB_THREAD] ; std::vector cellMarkers[NB_THREAD] ; - public: static const unsigned int UNKNOWN_ATTRIB = AttributeContainer::UNKNOWN ; @@ -165,17 +163,19 @@ public: * @param d * @return index of dart (depends on map implementation) */ - virtual unsigned int dartIndex(Dart d) const ; +// virtual unsigned int dartIndex(Dart d) const = 0; /** - * @return the number of darts in the map + * get the Dart of index in topological table */ - virtual unsigned int getNbDarts() ; +// virtual Dart indexDart(unsigned int index) const = 0; /** - * return true if the dart d refers to a valid index + * @return the number of darts in the map */ - bool isDartValid(Dart d) ; + virtual unsigned int getNbDarts() ; + +// AttributeContainer& getDartContainer() = 0; /**************************************** * EMBEDDING MANAGEMENT * @@ -189,35 +189,6 @@ public: bool isOrbitEmbedded(unsigned int orbit) const ; - /** - * get the cell index of the given dimension associated to dart d - * @return EMBNULL if the orbit of d is not attached to any cell - */ - template - unsigned int getEmbedding(Dart d) const; - - /** - * Set the cell index of the given dimension associated to dart d - */ - template - void setDartEmbedding(Dart d, unsigned int emb) ; - - /** - * Set the cell index of the given dimension associated to dart d - * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding) !!! WARNING !!! - */ - template - void initDartEmbedding(Dart d, unsigned int emb) ; - - /** - * Copy the index of the cell associated to a dart over an other dart - * @param orbit the id of orbit embedding - * @param dest the dart to overwrite - * @param src the dart to copy - */ - template - void copyDartEmbedding(Dart dest, Dart src) ; - /** * Allocation of some place in attrib table * @param orbit the orbit of embedding @@ -226,47 +197,6 @@ public: template unsigned int newCell() ; - /** - * Set the index of the associated cell to all the darts of an orbit - * @param orbit orbit to embed - * @param d a dart of the topological vertex - * @param em index of attribute to store as embedding - */ - template - void setOrbitEmbedding(Dart d, unsigned int em) ; - - /** - * Set the index of the associated cell to all the darts of an orbit - * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding)!!! WARNING !!! - */ - template - void initOrbitEmbedding(Dart d, unsigned int em) ; - - /** - * Associate an new cell to all darts of an orbit - * @param orbit orbit to embed - * @param d a dart of the topological cell - * @return index of the attribute in table - */ - template - unsigned int setOrbitEmbeddingOnNewCell(Dart d) ; - - /** - * Associate an new cell to all darts of an orbit - * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding)!!! WARNING !!! - */ - template - unsigned int initOrbitEmbeddingNewCell(Dart d) ; - - /** - * Copy the cell associated to a dart over an other dart - * @param orbit attribute orbit to use - * @param d the dart to overwrite (dest) - * @param e the dart to copy (src) - */ - template - void copyCell(Dart d, Dart e) ; - /** * Line of attributes i is overwritten with line j * @param orbit attribute orbit to use @@ -284,13 +214,6 @@ public: template void initCell(unsigned int i) ; - /** - * Traverse the map and embed all orbits of the given dimension with a new cell - * @param realloc if true -> all the orbits are embedded on new cells, if false -> already embedded orbits are not impacted - */ - template - void initAllOrbitsEmbedding(bool realloc = false) ; - /**************************************** * QUICK TRAVERSAL MANAGEMENT * ****************************************/ @@ -440,14 +363,6 @@ public: /**************************************** * SAVE & LOAD * ****************************************/ -public: - /** - * check if an xml node has a given name - * @param node the xml node - * @param name the name - * @ return true if node has the good name - */ -// bool chechXmlNode(xmlNodePtr node, const std::string& name) ; /** * update the pointer of embedding vector after loading @@ -459,38 +374,24 @@ public: */ virtual void update_topo_shortcuts(); - /** - * Save map in a XML file - * @param filename the file name - * @return true if OK - */ -// bool saveMapXml(const std::string& filename, bool compress = false) ; - - /** - * Load map from a XML file - * @param filename the file name - * @return true if OK - */ -// bool loadMapXml(const std::string& filename, bool compress = false) ; - /** * Save map in a binary file * @param filename the file name * @return true if OK */ - bool saveMapBin(const std::string& filename) const; + virtual bool saveMapBin(const std::string& filename) const = 0; /** * Load map from a binary file * @param filename the file name * @return true if OK */ - bool loadMapBin(const std::string& filename) ; + virtual bool loadMapBin(const std::string& filename) = 0 ; /** * copy from another map (of same type) */ - bool copyFrom(const GenericMap& map) ; + virtual bool copyFrom(const GenericMap& map) = 0 ; /** * Dump attributes types and names per orbit @@ -511,11 +412,11 @@ public: * DARTS TRAVERSALS * ****************************************/ -// /** -// * Apply a functor on each dart of the map -// * @param f a ref to the functor obj -// */ -// bool foreach_dart(FunctorType& f) ; + /** + * Apply a functor on each dart of the map + * @param f a ref to the functor obj + */ + bool foreach_dart(FunctorType& f) ; virtual Dart begin() const; virtual Dart end() const; diff --git a/include/Topology/generic/genericmap.hpp b/include/Topology/generic/genericmap.hpp index db760016..e6602d6a 100644 --- a/include/Topology/generic/genericmap.hpp +++ b/include/Topology/generic/genericmap.hpp @@ -90,10 +90,10 @@ inline unsigned int GenericMap::getNbDarts() return m_attribs[DART].size() ; } -inline bool GenericMap::isDartValid(Dart d) -{ - return !d.isNil() && m_attribs[DART].used(dartIndex(d)) ; -} +//inline bool GenericMap::isDartValid(Dart d) +//{ +// return !d.isNil() && m_attribs[DART].used(dartIndex(d)) ; +//} /**************************************** * EMBEDDING MANAGEMENT * @@ -110,61 +110,6 @@ inline bool GenericMap::isOrbitEmbedded(unsigned int orbit) const return (orbit == DART) || (m_embeddings[orbit] != NULL) ; } -template -inline unsigned int GenericMap::getEmbedding(Dart d) const -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - - unsigned int d_index = dartIndex(d); - - if (ORBIT == DART) - return d_index; - - return (*m_embeddings[ORBIT])[d_index] ; -} - -template -void GenericMap::setDartEmbedding(Dart d, unsigned int emb) -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - - unsigned int old = getEmbedding(d); - - if (old == emb) // if same emb - return; // nothing to do - - if (old != EMBNULL) // if different - { - if(m_attribs[ORBIT].unrefLine(old)) // then unref the old emb - { - for (unsigned int t = 0; t < m_nbThreads; ++t) // clear the markers if it was the - (*m_markTables[ORBIT][t])[old].clear(); // last unref of the line - } - } - - if (emb != EMBNULL) - m_attribs[ORBIT].refLine(emb); // ref the new emb - - (*m_embeddings[ORBIT])[dartIndex(d)] = emb ; // finally affect the embedding to the dart -} - -template -void GenericMap::initDartEmbedding(Dart d, unsigned int emb) -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - assert(getEmbedding(d) == EMBNULL || !"initDartEmbedding called on already embedded dart"); - if(emb != EMBNULL) - m_attribs[ORBIT].refLine(emb); // ref the new emb - (*m_embeddings[ORBIT])[dartIndex(d)] = emb ; // affect the embedding to the dart -} - -template -inline void GenericMap::copyDartEmbedding(Dart dest, Dart src) -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - setDartEmbedding(dest, getEmbedding(src)); -} - template inline unsigned int GenericMap::newCell() { @@ -172,54 +117,6 @@ inline unsigned int GenericMap::newCell() return m_attribs[ORBIT].insertLine(); } -template -inline void GenericMap::setOrbitEmbedding(Dart d, unsigned int em) -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - FunctorSetEmb fsetemb(*this, em); - foreach_dart_of_orbit(d, fsetemb); -} - -template -inline void GenericMap::initOrbitEmbedding(Dart d, unsigned int em) -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - FunctorInitEmb fsetemb(*this, em); - foreach_dart_of_orbit(d, fsetemb); -} - -template -inline unsigned int GenericMap::setOrbitEmbeddingOnNewCell(Dart d) -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - unsigned int em = newCell(); - setOrbitEmbedding(d, em); - return em; -} - -template -inline unsigned int GenericMap::initOrbitEmbeddingNewCell(Dart d) -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - unsigned int em = newCell(); - initOrbitEmbedding(d, em); - return em; -} - -template -inline void GenericMap::copyCell(Dart d, Dart e) -{ - assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); - unsigned int dE = getEmbedding(d) ; - unsigned int eE = getEmbedding(e) ; - if(eE != EMBNULL) // if the source is NULL, nothing to copy - { - if(dE == EMBNULL) // if the dest is NULL, create a new cell - dE = setOrbitEmbeddingOnNewCell(d) ; - m_attribs[ORBIT].copyLine(dE, eE) ; // copy the data - } -} - template inline void GenericMap::copyCell(unsigned int i, unsigned int j) { @@ -234,23 +131,6 @@ inline void GenericMap::initCell(unsigned int i) m_attribs[ORBIT].initLine(i) ; } -template -void GenericMap::initAllOrbitsEmbedding(bool realloc) -{ - if(!isOrbitEmbedded()) - addEmbedding() ; - DartMarker mark(*this) ; - for(Dart d = begin(); d != end(); next(d)) - { - if(!mark.isMarked(d)) - { - mark.markOrbit(d) ; - if(realloc || getEmbedding(d) == EMBNULL) - setOrbitEmbeddingOnNewCell(d) ; - } - } -} - /**************************************** * QUICK TRAVERSAL MANAGEMENT * ****************************************/ @@ -352,7 +232,7 @@ inline void GenericMap::updateQuickIncidentTraversal() buffer.push_back(e); delete tra_loc; buffer.push_back(NIL); - std::vector& vd = (*ptrVD)[getEmbedding(d)]; + std::vector& vd = (*ptrVD)[MAP::getEmbedding(d)]; vd.reserve(buffer.size()); vd.assign(buffer.begin(),buffer.end()); } @@ -375,8 +255,6 @@ inline void GenericMap::disableQuickIncidentTraversal() } } - - template inline void GenericMap::enableQuickAdjacentTraversal() { @@ -413,7 +291,7 @@ inline void GenericMap::updateQuickAdjacentTraversal() buffer.push_back(e); buffer.push_back(NIL); delete tra_loc; - std::vector& vd = (*ptrVD)[getEmbedding(d)]; + std::vector& vd = (*ptrVD)[MAP::getEmbedding(d)]; vd.reserve(buffer.size()); vd.assign(buffer.begin(),buffer.end()); } @@ -548,7 +426,7 @@ bool GenericMap::foreach_dart_of_orbit(Dart d, FunctorType& f, unsigned int thre template bool GenericMap::foreach_orbit(FunctorType& fonct, unsigned int thread) const { - TraversorCell trav(*this, true, thread); + TraversorCell trav(*reinterpret_cast(this), true, thread); bool found = false; for (Dart d = trav.begin(); !found && d != trav.end(); d = trav.next()) diff --git a/include/Topology/generic/mapMono.h b/include/Topology/generic/mapMono.h index 402984ee..edcf5864 100644 --- a/include/Topology/generic/mapMono.h +++ b/include/Topology/generic/mapMono.h @@ -32,6 +32,8 @@ namespace CGoGN class MapMono : public AttribMap { + template friend class DartMarkerTmpl ; + public: MapMono() {} @@ -54,11 +56,18 @@ protected: return d.index; } + inline Dart indexDart(unsigned int index) const + { + return Dart(index); + } + /** * @return the number of darts in the map */ inline virtual unsigned int getNbDarts(); + inline AttributeContainer& getDartContainer(); + /**************************************** * RELATIONS MANAGEMENT * ****************************************/ @@ -93,7 +102,7 @@ protected: /**************************************** * DARTS TRAVERSALS * ****************************************/ - +public: /** * Begin of map * @return the first dart of the map @@ -112,6 +121,97 @@ protected: * @param d reference to the dart to be modified */ inline virtual void next(Dart& d) const; + + /**************************************** + * EMBEDDING MANAGEMENT * + ****************************************/ + + /** + * get the cell index of the given dimension associated to dart d + * @return EMBNULL if the orbit of d is not attached to any cell + */ + template + inline unsigned int getEmbedding(Dart d) const; + + /** + * Set the cell index of the given dimension associated to dart d + */ + template + void setDartEmbedding(Dart d, unsigned int emb) ; + + /** + * Set the cell index of the given dimension associated to dart d + * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding) !!! WARNING !!! + */ + template + void initDartEmbedding(Dart d, unsigned int emb) ; + + /** + * Copy the index of the cell associated to a dart over an other dart + * @param orbit the id of orbit embedding + * @param dest the dart to overwrite + * @param src the dart to copy + */ + template + inline void copyDartEmbedding(Dart dest, Dart src) ; + + /** + * Set the index of the associated cell to all the darts of an orbit + * @param orbit orbit to embed + * @param d a dart of the topological vertex + * @param em index of attribute to store as embedding + */ + template + void setOrbitEmbedding(Dart d, unsigned int em) ; + + /** + * Set the index of the associated cell to all the darts of an orbit + * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding)!!! WARNING !!! + */ + template + void initOrbitEmbedding(Dart d, unsigned int em) ; + + /** + * Associate an new cell to all darts of an orbit + * @param orbit orbit to embed + * @param d a dart of the topological cell + * @return index of the attribute in table + */ + template + unsigned int setOrbitEmbeddingOnNewCell(Dart d) ; + + /** + * Associate an new cell to all darts of an orbit + * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding)!!! WARNING !!! + */ + template + unsigned int initOrbitEmbeddingOnNewCell(Dart d) ; + + /** + * Copy the cell associated to a dart over an other dart + * @param orbit attribute orbit to use + * @param d the dart to overwrite (dest) + * @param e the dart to copy (src) + */ + template + void copyCell(Dart d, Dart e) ; + + /** + * Traverse the map and embed all orbits of the given dimension with a new cell + * @param realloc if true -> all the orbits are embedded on new cells, if false -> already embedded orbits are not impacted + */ + template + void initAllOrbitsEmbedding(bool realloc = false) ; + + /**************************************** + * SAVE & LOAD * + ****************************************/ + + bool saveMapBin(const std::string& filename) const; + + bool loadMapBin(const std::string& filename); + + bool copyFrom(const GenericMap& map); } ; } //namespace CGoGN diff --git a/include/Topology/generic/mapMono.hpp b/include/Topology/generic/mapMono.hpp index 636c4326..1e7481a6 100644 --- a/include/Topology/generic/mapMono.hpp +++ b/include/Topology/generic/mapMono.hpp @@ -48,6 +48,11 @@ inline void MapMono::deleteDart(Dart d) deleteDartLine(d.index) ; } +inline AttributeContainer& MapMono::getDartContainer() +{ + return m_attribs[DART]; +} + /**************************************** * RELATIONS MANAGEMENT * ****************************************/ @@ -170,4 +175,134 @@ inline void MapMono::next(Dart& d) const m_attribs[DART].next(d.index) ; } +/**************************************** + * EMBEDDING MANAGEMENT * + ****************************************/ + +template +inline unsigned int MapMono::getEmbedding(Dart d) const +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + unsigned int d_index = dartIndex(d); + + if (ORBIT == DART) + return d_index; + + return (*m_embeddings[ORBIT])[d_index] ; +} + +template +void MapMono::setDartEmbedding(Dart d, unsigned int emb) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + unsigned int old = getEmbedding(d); + + if (old == emb) // if same emb + return; // nothing to do + + if (old != EMBNULL) // if different + { + if(m_attribs[ORBIT].unrefLine(old)) // then unref the old emb + { + for (unsigned int t = 0; t < m_nbThreads; ++t) // clear the markers if it was the + (*m_markTables[ORBIT][t])[old].clear(); // last unref of the line + } + } + + if (emb != EMBNULL) + m_attribs[ORBIT].refLine(emb); // ref the new emb + + (*m_embeddings[ORBIT])[dartIndex(d)] = emb ; // finally affect the embedding to the dart +} + +template +void MapMono::initDartEmbedding(Dart d, unsigned int emb) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + assert(getEmbedding(d) == EMBNULL || !"initDartEmbedding called on already embedded dart"); + + if(emb != EMBNULL) + m_attribs[ORBIT].refLine(emb); // ref the new emb + (*m_embeddings[ORBIT])[dartIndex(d)] = emb ; // affect the embedding to the dart +} + +template +inline void MapMono::copyDartEmbedding(Dart dest, Dart src) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + setDartEmbedding(dest, getEmbedding(src)); +} + +template +inline void MapMono::setOrbitEmbedding(Dart d, unsigned int em) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + FunctorSetEmb fsetemb(*this, em); + foreach_dart_of_orbit(d, fsetemb); +} + +template +inline void MapMono::initOrbitEmbedding(Dart d, unsigned int em) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + FunctorInitEmb fsetemb(*this, em); + foreach_dart_of_orbit(d, fsetemb); +} + +template +inline unsigned int MapMono::setOrbitEmbeddingOnNewCell(Dart d) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + unsigned int em = newCell(); + setOrbitEmbedding(d, em); + return em; +} + +template +inline unsigned int MapMono::initOrbitEmbeddingOnNewCell(Dart d) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + unsigned int em = newCell(); + initOrbitEmbedding(d, em); + return em; +} + +template +inline void MapMono::copyCell(Dart d, Dart e) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + unsigned int dE = getEmbedding(d) ; + unsigned int eE = getEmbedding(e) ; + if(eE != EMBNULL) // if the source is NULL, nothing to copy + { + if(dE == EMBNULL) // if the dest is NULL, create a new cell + dE = setOrbitEmbeddingOnNewCell(d) ; + copyCell(dE, eE); // copy the data + } +} + +template +void MapMono::initAllOrbitsEmbedding(bool realloc) +{ + if(!isOrbitEmbedded()) + addEmbedding() ; + DartMarker mark(*this) ; + for(Dart d = begin(); d != end(); next(d)) + { + if(!mark.isMarked(d)) + { + mark.markOrbit(d) ; + if(realloc || getEmbedding(d) == EMBNULL) + setOrbitEmbeddingOnNewCell(d) ; + } + } +} + } // namespace CGoGN diff --git a/include/Topology/generic/mapMulti.h b/include/Topology/generic/mapMulti.h index da413e78..fd64e321 100644 --- a/include/Topology/generic/mapMulti.h +++ b/include/Topology/generic/mapMulti.h @@ -25,13 +25,15 @@ #ifndef __MAP_MULTI__ #define __MAP_MULTI__ -#include "attribmap.h" +#include "Topology/generic/attribmap.h" namespace CGoGN { class MapMulti : public AttribMap { + template friend class DartMarkerTmpl ; + public: MapMulti() { @@ -83,7 +85,7 @@ protected: /**************************************** * DARTS MANAGEMENT * ****************************************/ - +public: inline virtual Dart newDart(); inline virtual void deleteDart(Dart d); @@ -105,11 +107,14 @@ protected: */ virtual unsigned int getNbDarts() ; + inline AttributeContainer& getDartContainer(); + /** * get the insertion level of a dart */ unsigned int getDartLevel(Dart d) const ; +protected: /** * */ @@ -156,7 +161,7 @@ protected: /**************************************** * MR CONTAINER MANAGEMENT * ****************************************/ - +public: /** * get the MR attribute container */ @@ -266,6 +271,97 @@ protected: * @param d reference to the dart to be modified */ inline virtual void next(Dart& d) const; + + /**************************************** + * EMBEDDING MANAGEMENT * + ****************************************/ + + /** + * get the cell index of the given dimension associated to dart d + * @return EMBNULL if the orbit of d is not attached to any cell + */ + template + inline unsigned int getEmbedding(Dart d) const; + + /** + * Set the cell index of the given dimension associated to dart d + */ + template + void setDartEmbedding(Dart d, unsigned int emb) ; + + /** + * Set the cell index of the given dimension associated to dart d + * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding) !!! WARNING !!! + */ + template + void initDartEmbedding(Dart d, unsigned int emb) ; + + /** + * Copy the index of the cell associated to a dart over an other dart + * @param orbit the id of orbit embedding + * @param dest the dart to overwrite + * @param src the dart to copy + */ + template + inline void copyDartEmbedding(Dart dest, Dart src) ; + + /** + * Set the index of the associated cell to all the darts of an orbit + * @param orbit orbit to embed + * @param d a dart of the topological vertex + * @param em index of attribute to store as embedding + */ + template + void setOrbitEmbedding(Dart d, unsigned int em) ; + + /** + * Set the index of the associated cell to all the darts of an orbit + * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding)!!! WARNING !!! + */ + template + void initOrbitEmbedding(Dart d, unsigned int em) ; + + /** + * Associate an new cell to all darts of an orbit + * @param orbit orbit to embed + * @param d a dart of the topological cell + * @return index of the attribute in table + */ + template + unsigned int setOrbitEmbeddingOnNewCell(Dart d) ; + + /** + * Associate an new cell to all darts of an orbit + * !!! WARNING !!! use only on freshly inserted darts (no unref is done on old embedding)!!! WARNING !!! + */ + template + unsigned int initOrbitEmbeddingOnNewCell(Dart d) ; + + /** + * Copy the cell associated to a dart over an other dart + * @param orbit attribute orbit to use + * @param d the dart to overwrite (dest) + * @param e the dart to copy (src) + */ + template + void copyCell(Dart d, Dart e) ; + + /** + * Traverse the map and embed all orbits of the given dimension with a new cell + * @param realloc if true -> all the orbits are embedded on new cells, if false -> already embedded orbits are not impacted + */ + template + void initAllOrbitsEmbedding(bool realloc = false) ; + + /**************************************** + * SAVE & LOAD * + ****************************************/ + + bool saveMapBin(const std::string& filename) const; + + bool loadMapBin(const std::string& filename); + + bool copyFrom(const GenericMap& map); } ; } //namespace CGoGN diff --git a/include/Topology/generic/mapMulti.hpp b/include/Topology/generic/mapMulti.hpp index 8a01ae71..5957650a 100644 --- a/include/Topology/generic/mapMulti.hpp +++ b/include/Topology/generic/mapMulti.hpp @@ -29,7 +29,7 @@ namespace CGoGN * DARTS MANAGEMENT * ****************************************/ -inline virtual Dart MapMulti::newDart() +inline Dart MapMulti::newDart() { Dart d = GenericMap::newDart() ; @@ -62,10 +62,10 @@ inline virtual Dart MapMulti::newDart() return Dart::create(mrdi) ; } -inline virtual void MapMulti::deleteDart(Dart d) +inline void MapMulti::deleteDart(Dart d) { - unsigned int index = (*m_mrDarts[m_mrCurrentLevel])[d.index] ; - + unsigned int index = dartIndex(d); +/* if(getDartLevel(d) > m_mrCurrentLevel) { unsigned int di = (*m_mrDarts[m_mrCurrentLevel + 1])[d.index]; @@ -79,37 +79,42 @@ inline virtual void MapMulti::deleteDart(Dart d) (*m_mrDarts[m_mrCurrentLevel])[d.index] = MRNULL ; return; } - +*/ // a MRdart can only be deleted on its insertion level if(getDartLevel(d) == m_mrCurrentLevel) { - if(isDartValid(d)) - { +// if(isDartValid(d)) +// { deleteDartLine(index) ; m_mrattribs.removeLine(d.index); m_mrNbDarts[m_mrCurrentLevel]--; - } +// } } else { unsigned int di = (*m_mrDarts[m_mrCurrentLevel - 1])[d.index]; - // si le brin de niveau i pointe sur le meme brin que le niveau i-1 + // si le brin de niveau i pointe sur un autre brin que le niveau i-1w if(di != index) { - if(isDartValid(d))//index)) +// if(isDartValid(d))//index)) deleteDartLine(index) ; } for(unsigned int i = m_mrCurrentLevel; i <= getMaxLevel(); ++i) // for all levels from current to max - (*m_mrDarts[i])[d.index] = di ; //copy the index from previous level + (*m_mrDarts[i])[d.index] = di ; // copy the index from previous level } } -inline virtual unsigned int MapMulti::dartIndex(Dart d) const +inline unsigned int MapMulti::dartIndex(Dart d) const { return (*m_mrDarts[m_mrCurrentLevel])[d.index] ; } +inline Dart MapMulti::indexDart(unsigned int index) const +{ + return Dart( (*m_mrDarts[m_mrCurrentLevel])[index] ) ; +} + inline unsigned int MapMulti::getNbInsertedDarts(unsigned int level) { if(level < m_mrDarts.size()) @@ -175,6 +180,11 @@ inline void MapMulti::duplicateDartAtOneLevel(Dart d, unsigned int level) (*m_mrDarts[level])[d.index] = copyDartLine(dartIndex(d)) ; } +inline MapMulti::AttributeContainer& getDartContainer() +{ + return m_mrattribs; +} + /**************************************** * RELATIONS MANAGEMENT * ****************************************/ @@ -197,19 +207,19 @@ inline void MapMulti::addPermutation() } template -inline Dart MapMulti::getInvolution(Dart d) +inline Dart MapMulti::getInvolution(Dart d) const { return (*m_involution[I])[dartIndex(d)]; } template -inline Dart MapMulti::getPermutation(Dart d) +inline Dart MapMulti::getPermutation(Dart d) const { return (*m_permutation[I])[dartIndex(d)]; } template -inline Dart MapMulti::getPermutationInv(Dart d) +inline Dart MapMulti::getPermutationInv(Dart d) const { return (*m_permutation_inv[I])[dartIndex(d)]; } @@ -243,8 +253,8 @@ inline void MapMulti::permutationUnsew(Dart d) template inline void MapMulti::involutionSew(Dart d, Dart e) { - assert((*m_phi2)[dartIndex(d)] == d) ; - assert((*m_phi2)[dartIndex(e)] == e) ; + assert((*m_involution[I])[dartIndex(d)] == d) ; + assert((*m_involution[I])[dartIndex(e)] == e) ; (*m_involution[I])[dartIndex(d)] = e ; (*m_involution[I])[dartIndex(e)] = d ; } @@ -331,7 +341,7 @@ inline unsigned int MapMulti::getMaxLevel() * DARTS TRAVERSALS * ****************************************/ -inline virtual Dart begin() const +inline Dart MapMulti::begin() const { unsigned int d = m_mrattribs.begin() ; if(d != m_mrattribs.end()) @@ -342,12 +352,12 @@ inline virtual Dart begin() const return Dart::create(d) ; } -inline virtual Dart end() const +inline Dart MapMulti::end() const { return Dart::create(m_mrattribs.end()) ; } -inline virtual void next(Dart& d) const +inline void MapMulti::next(Dart& d) const { do { @@ -355,4 +365,134 @@ inline virtual void next(Dart& d) const } while (d.index != m_mrattribs.end() && getDartLevel(d) > m_mrCurrentLevel) ; } +/**************************************** + * EMBEDDING MANAGEMENT * + ****************************************/ + +template +inline unsigned int MapMulti::getEmbedding(Dart d) const +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + unsigned int d_index = dartIndex(d); + + if (ORBIT == DART) + return d_index; + + return (*m_embeddings[ORBIT])[d_index] ; +} + +template +void MapMulti::setDartEmbedding(Dart d, unsigned int emb) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + unsigned int old = getEmbedding(d); + + if (old == emb) // if same emb + return; // nothing to do + + if (old != EMBNULL) // if different + { + if(m_attribs[ORBIT].unrefLine(old)) // then unref the old emb + { + for (unsigned int t = 0; t < m_nbThreads; ++t) // clear the markers if it was the + (*m_markTables[ORBIT][t])[old].clear(); // last unref of the line + } + } + + if (emb != EMBNULL) + m_attribs[ORBIT].refLine(emb); // ref the new emb + + (*m_embeddings[ORBIT])[dartIndex(d)] = emb ; // finally affect the embedding to the dart +} + +template +void MapMulti::initDartEmbedding(Dart d, unsigned int emb) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + assert(getEmbedding(d) == EMBNULL || !"initDartEmbedding called on already embedded dart"); + + if(emb != EMBNULL) + m_attribs[ORBIT].refLine(emb); // ref the new emb + (*m_embeddings[ORBIT])[dartIndex(d)] = emb ; // affect the embedding to the dart +} + +template +inline void MapMulti::copyDartEmbedding(Dart dest, Dart src) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + setDartEmbedding(dest, getEmbedding(src)); +} + +template +inline void MapMulti::setOrbitEmbedding(Dart d, unsigned int em) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + FunctorSetEmb fsetemb(*this, em); + foreach_dart_of_orbit(d, fsetemb); +} + +template +inline void MapMulti::initOrbitEmbedding(Dart d, unsigned int em) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + FunctorInitEmb fsetemb(*this, em); + foreach_dart_of_orbit(d, fsetemb); +} + +template +inline unsigned int MapMulti::setOrbitEmbeddingOnNewCell(Dart d) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + unsigned int em = newCell(); + setOrbitEmbedding(d, em); + return em; +} + +template +inline unsigned int MapMulti::initOrbitEmbeddingNewCell(Dart d) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + + unsigned int em = newCell(); + initOrbitEmbedding(d, em); + return em; +} + +template +inline void MapMulti::copyCell(Dart d, Dart e) +{ + assert(isOrbitEmbedded() || !"Invalid parameter: orbit not embedded"); + unsigned int dE = getEmbedding(d) ; + unsigned int eE = getEmbedding(e) ; + if(eE != EMBNULL) // if the source is NULL, nothing to copy + { + if(dE == EMBNULL) // if the dest is NULL, create a new cell + dE = setOrbitEmbeddingOnNewCell(d) ; + copyCell(dE, eE); // copy the data + } +} + +template +void MapMulti::initAllOrbitsEmbedding(bool realloc) +{ + if(!isOrbitEmbedded()) + addEmbedding() ; + DartMarker mark(*this) ; + for(Dart d = begin(); d != end(); next(d)) + { + if(!mark.isMarked(d)) + { + mark.markOrbit(d) ; + if(realloc || getEmbedding(d) == EMBNULL) + setOrbitEmbeddingOnNewCell(d) ; + } + } +} + } // namespace CGoGN diff --git a/include/Topology/generic/traversor3Virt.h b/include/Topology/generic/traversor3Virt.h index 627e1f06..5a41fb82 100644 --- a/include/Topology/generic/traversor3Virt.h +++ b/include/Topology/generic/traversor3Virt.h @@ -43,13 +43,14 @@ class VMarkerForTraversor { private: MAP& m_map ; - DartMarkerStore* m_dmark ; - CellMarkerStore* m_cmark ; + DartMarkerStore* m_dmark ; + CellMarkerStore* m_cmark ; + public: VMarkerForTraversor(MAP& map, bool forceDartMarker = false, unsigned int thread = 0) ; ~VMarkerForTraversor(); - DartMarkerStore* dmark(); - CellMarkerStore* cmark(); + DartMarkerStore* dmark(); + CellMarkerStore* cmark(); void mark(Dart d); void unmark(Dart d); bool isMarked(Dart d); @@ -65,8 +66,8 @@ class VTraversor3XY: public Traversor { private: MAP& m_map ; - DartMarkerStore* m_dmark ; - CellMarkerStore* m_cmark ; + DartMarkerStore* m_dmark ; + CellMarkerStore* m_cmark ; Dart m_current ; TraversorDartsOfOrbit m_tradoo; @@ -79,6 +80,7 @@ public: VTraversor3XY(MAP& map, Dart dart, bool forceDartMarker = false, unsigned int thread = 0) ; VTraversor3XY(MAP& map, Dart dart, VMarkerForTraversor& tmo, bool forceDartMarker = false, unsigned int thread = 0) ; ~VTraversor3XY(); + Dart begin() ; Dart end() ; Dart next() ; @@ -102,9 +104,7 @@ public: VTraversor3XXaY(MAP& map, Dart dart, bool forceDartMarker = false, unsigned int thread = 0); Dart begin(); - Dart end(); - Dart next(); }; diff --git a/include/Topology/generic/traversor3Virt.hpp b/include/Topology/generic/traversor3Virt.hpp index 988f4e4c..8c534ea9 100644 --- a/include/Topology/generic/traversor3Virt.hpp +++ b/include/Topology/generic/traversor3Virt.hpp @@ -39,9 +39,9 @@ VMarkerForTraversor::VMarkerForTraversor(MAP& map, bool forceDartMar m_cmark(NULL) { if(!forceDartMarker && map.isOrbitEmbedded(ORBIT)) - m_cmark = new CellMarkerStore(map, thread) ; + m_cmark = new CellMarkerStore(map, thread) ; else - m_dmark = new DartMarkerStore(map, thread) ; + m_dmark = new DartMarkerStore(map, thread) ; } template @@ -80,13 +80,13 @@ bool VMarkerForTraversor::isMarked(Dart d) } template -CellMarkerStore* VMarkerForTraversor::cmark() +CellMarkerStore* VMarkerForTraversor::cmark() { return m_cmark; } template -DartMarkerStore* VMarkerForTraversor::dmark() +DartMarkerStore* VMarkerForTraversor::dmark() { return m_dmark; } @@ -113,9 +113,9 @@ VTraversor3XY::VTraversor3XY(MAP& map, Dart dart, bool forceDar else { if(!forceDartMarker && map.isOrbitEmbedded(ORBY)) - m_cmark = new CellMarkerStore(map, thread) ; + m_cmark = new CellMarkerStore(map, thread) ; else - m_dmark = new DartMarkerStore(map, thread) ; + m_dmark = new DartMarkerStore(map, thread) ; } } diff --git a/include/Topology/generic/traversorCell.h b/include/Topology/generic/traversorCell.h index 6b162ecd..83ee869f 100644 --- a/include/Topology/generic/traversorCell.h +++ b/include/Topology/generic/traversorCell.h @@ -55,8 +55,8 @@ private: const AttributeContainer* cont ; unsigned int qCurrent ; - DartMarker* dmark ; - CellMarker* cmark ; + DartMarker* dmark ; + CellMarker* cmark ; const AttributeMultiVector* quickTraversal ; Dart current ; diff --git a/include/Topology/generic/traversorCell.hpp b/include/Topology/generic/traversorCell.hpp index 2c276918..251280ac 100644 --- a/include/Topology/generic/traversorCell.hpp +++ b/include/Topology/generic/traversorCell.hpp @@ -30,7 +30,7 @@ TraversorCell::TraversorCell(const MAP& map, bool forceDartMarker, u m(map), dmark(NULL), cmark(NULL), quickTraversal(NULL), current(NIL), firstTraversal(true) { if(forceDartMarker) - dmark = new DartMarker(map, thread) ; + dmark = new DartMarker(map, thread) ; else { quickTraversal = map.template getQuickTraversal() ; @@ -42,9 +42,9 @@ TraversorCell::TraversorCell(const MAP& map, bool forceDartMarker, u else { if(map.template isOrbitEmbedded()) - cmark = new CellMarker(map, thread) ; + cmark = new CellMarker(map, thread) ; else - dmark = new DartMarker(map, thread) ; + dmark = new DartMarker(map, thread) ; } } } diff --git a/include/Topology/generic/traversorCellVirt.h b/include/Topology/generic/traversorCellVirt.h index 7bdffbea..da2e78ed 100644 --- a/include/Topology/generic/traversorCellVirt.h +++ b/include/Topology/generic/traversorCellVirt.h @@ -42,9 +42,9 @@ private: const AttributeContainer* cont ; unsigned int qCurrent ; - DartMarker* dmark ; - CellMarker* cmark ; - const AttributeMultiVector* quickTraversal ; + DartMarker* dmark ; + CellMarker* cmark ; + AttributeMultiVector* quickTraversal ; Dart current ; bool firstTraversal ; diff --git a/include/Topology/generic/traversorCellVirt.hpp b/include/Topology/generic/traversorCellVirt.hpp index 79ee215c..0c054843 100644 --- a/include/Topology/generic/traversorCellVirt.hpp +++ b/include/Topology/generic/traversorCellVirt.hpp @@ -30,7 +30,7 @@ VTraversorCell::VTraversorCell(const MAP& map, bool forceDartMarker, m(map), dmark(NULL), cmark(NULL), quickTraversal(NULL), current(NIL), firstTraversal(true) { if(forceDartMarker) - dmark = new DartMarker(map, thread) ; + dmark = new DartMarker(map, thread) ; else { quickTraversal = map.template getQuickTraversal() ; @@ -41,9 +41,9 @@ VTraversorCell::VTraversorCell(const MAP& map, bool forceDartMarker, else { if(map.template isOrbitEmbedded()) - cmark = new CellMarker(map, thread) ; + cmark = new CellMarker(map, thread) ; else - dmark = new DartMarker(map, thread) ; + dmark = new DartMarker(map, thread) ; } } } diff --git a/include/Topology/map/map1.hpp b/include/Topology/map/map1.hpp index 9af94595..f76f6378 100644 --- a/include/Topology/map/map1.hpp +++ b/include/Topology/map/map1.hpp @@ -74,13 +74,13 @@ inline void Map1::update_topo_shortcuts() template inline Dart Map1::phi1(Dart d) const { - return MAP::getPermutation<0>(d); + return MAP::template getPermutation<0>(d); } template inline Dart Map1::phi_1(Dart d) const { - return MAP::getPermutationInv<0>(d); + return MAP::template getPermutationInv<0>(d); } template @@ -118,13 +118,13 @@ inline Dart Map1::alpha_1(Dart d) const template inline void Map1::phi1sew(Dart d, Dart e) { - MAP::permutationSew<0>(d,e); + MAP::template permutationSew<0>(d,e); } template inline void Map1::phi1unsew(Dart d) { - MAP::permutationUnsew<0>(d); + MAP::template permutationUnsew<0>(d); } /*! @name Generator and Deletor diff --git a/include/Topology/map/map2.hpp b/include/Topology/map/map2.hpp index 37061c2b..3c72a334 100644 --- a/include/Topology/map/map2.hpp +++ b/include/Topology/map/map2.hpp @@ -71,7 +71,7 @@ inline void Map2::update_topo_shortcuts() template inline Dart Map2::phi2(Dart d) const { - return MAP::getInvolution<0>(d); + return MAP::template getInvolution<0>(d); } template @@ -111,7 +111,7 @@ inline Dart Map2::alpha1(Dart d) const template inline Dart Map2::alpha_1(Dart d) const { - return phi1(phi2(d)) ; + return this->phi1(phi2(d)) ; } template @@ -129,13 +129,13 @@ inline Dart Map2::phi12(Dart d) const template inline void Map2::phi2sew(Dart d, Dart e) { - MAP::involutionSew<0>(d,e); + MAP::template involutionSew<0>(d,e); } template inline void Map2::phi2unsew(Dart d) { - MAP::involutionUnsew<0>(d); + MAP::template involutionUnsew<0>(d); } /*! @name Generator and Deletor @@ -282,7 +282,7 @@ Dart Map2::deleteVertex(Dart d) if(res == NIL && this->phi1(this->phi1(d)) != d) res = this->phi1(d) ; - Dart f = phi_1(phi2(vit)) ; + Dart f = this->phi_1(phi2(vit)) ; this->phi1sew(vit, f) ; vit = phi2(this->phi_1(vit)) ; @@ -416,7 +416,7 @@ void Map2::insertEdgeInVertex(Dart d, Dart e) { assert(!sameVertex(d,e)); assert(phi2(e) == this->phi_1(e)); - phi1sew(this->phi_1(d), this->phi_1(e)); + this->phi1sew(this->phi_1(d), this->phi_1(e)); } template diff --git a/include/Topology/map/map3.h b/include/Topology/map/map3.h index dc3a87bf..f4ab168a 100644 --- a/include/Topology/map/map3.h +++ b/include/Topology/map/map3.h @@ -171,7 +171,6 @@ public: */ virtual bool uncutEdge(Dart d); - /** * Precondition for deleting edge */ @@ -240,7 +239,6 @@ public: //!! sewVolumes Pre-condition bool sewVolumesPreCond(Dart d, Dart e); - //! Sew two oriented volumes along their faces. /*! The oriented faces should not be phi3-linked and have the same degree * @param d a dart of the first volume @@ -264,17 +262,14 @@ public: virtual bool mergeVolumes(Dart /*d*/, Dart /*e*/) { assert("use mergeVolumes(d,e) only in dimension 2");return false;} - //! Split a volume into two volumes along a edge path /*! @param vd a vector of darts */ virtual void splitVolume(std::vector& vd); - //! Split a volume into two volumes along a edge path and add the given face between virtual void splitVolumeWithFace(std::vector& vd, Dart d); - //! Collapse a volume (that is deleted) possibly merging its vertices /*! \warning * @param d a dart in the deleted volume @@ -283,7 +278,6 @@ public: virtual Dart collapseVolume(Dart d, bool delDegenerateVolumes = true); //@} - //BROUILLON Dart faceToEdge(Dart d); @@ -303,7 +297,6 @@ public: */ unsigned int vertexDegree(Dart d) const; - //! Check number of edges of the vertex of d with given parameter /*! @param d a dart * @param vd degree to compare with @@ -311,7 +304,6 @@ public: */ int checkVertexDegree(Dart d, unsigned int vd) const; - //! Compute the number of edges of the vertex of d on the boundary /*! @param d a dart */ diff --git a/include/Topology/map/map3.hpp b/include/Topology/map/map3.hpp index 9188e1d9..62fb6e55 100644 --- a/include/Topology/map/map3.hpp +++ b/include/Topology/map/map3.hpp @@ -22,6 +22,8 @@ * * *******************************************************************************/ +#include "Topology/generic/traversor3.h" + namespace CGoGN { @@ -71,7 +73,7 @@ inline void Map3::update_topo_shortcuts() template inline Dart Map3::phi3(Dart d) const { - return MAP::getInvolution<1>(d); + return MAP::template getInvolution<1>(d); } template @@ -119,75 +121,1628 @@ inline Dart Map3::alpha2(Dart d) const template inline Dart Map3::alpha_2(Dart d) const { - return phi2(phi3(d)); + return this->phi2(phi3(d)); } template inline void Map3::phi3sew(Dart d, Dart e) { - MAP::involutionSew<1>(d,e); + MAP::template involutionSew<1>(d,e); } template inline void Map3::phi3unsew(Dart d) { - MAP::involutionUnsew<1>(d); + MAP::template involutionUnsew<1>(d); } -/*! @name Topological Queries - * Return or set various topological information +/*! @name Generator and Deletor + * To generate or delete volumes in a 3-map *************************************************************************/ template -inline bool Map3::sameEdge(Dart d, Dart e) const +void Map3::deleteVolume(Dart d, bool withBoundary) { - return ParentMap::sameOrientedEdge(d, e) || ParentMap::sameOrientedEdge(this->phi2(d), e) ; + if(withBoundary) + { + DartMarkerStore mark(*this); // Lock a marker + + std::vector visitedFaces; // Faces that are traversed + visitedFaces.reserve(512); + visitedFaces.push_back(d); // Start with the face of d + + mark.markOrbit(d) ; + + for(unsigned int i = 0; i < visitedFaces.size(); ++i) + { + Dart e = visitedFaces[i] ; + + if(!isBoundaryFace(e)) + unsewVolumes(e) ; + + do // add all face neighbours to the table + { + Dart ee = this->phi2(e) ; + if(!mark.isMarked(ee)) // not already marked + { + visitedFaces.push_back(ee) ; + mark.markOrbit(ee) ; + } + e = this->phi1(e) ; + } while(e != visitedFaces[i]) ; + } + + Dart dd = phi3(d) ; + ParentMap::deleteCC(d) ; //deleting the volume + ParentMap::deleteCC(dd) ; //deleting its border (created from the unsew operation) + + return; + } + + //else remove the CC and create fixed points + DartMarkerStore mark(*this); // Lock a marker + + std::vector visitedFaces; // Faces that are traversed + visitedFaces.reserve(512); + visitedFaces.push_back(d); // Start with the face of d + + mark.markOrbit(d) ; + + for(unsigned int i = 0; i < visitedFaces.size(); ++i) + { + Dart e = visitedFaces[i] ; + + Dart it = e ; + do + { + phi3unsew(it); + it = this->phi1(it) ; + } while(it != e) ; + + do // add all face neighbours to the table + { + Dart ee = this->phi2(e) ; + if(!mark.isMarked(ee)) // not already marked + { + visitedFaces.push_back(ee) ; + mark.markOrbit(ee) ; + } + e = this->phi1(e) ; + } while(e != visitedFaces[i]) ; + } + + ParentMap::deleteCC(d) ; //deleting the volume } template -inline bool Map3::sameFace(Dart d, Dart e) const +void Map3::fillHole(Dart d) { - return ParentMap::sameOrientedFace(d, e) || ParentMap::sameOrientedFace(phi3(d), e) ; + assert(isBoundaryFace(d)) ; + Dart dd = d ; + if(!this->isBoundaryMarked3(dd)) + dd = phi3(dd) ; + this->template boundaryUnmarkOrbit(dd) ; } template -inline bool Map3::isBoundaryFace(Dart d) const +void Map3::createHole(Dart d) { - return this->isBoundaryMarked3(d) || this->isBoundaryMarked3(phi3(d)); + assert(!isBoundaryFace(d)) ; + this->template boundaryMarkOrbit(d) ; } -/*! @name Cell Functors - * Apply functors to all darts of a cell +/*! @name Topological Operators + * Topological operations on 3-maps *************************************************************************/ template -inline bool Map3::foreach_dart_of_face(Dart d, FunctorType& f, unsigned int thread) const +Dart Map3::splitVertex(std::vector& vd) { - return ParentMap::foreach_dart_of_face(d, f, thread) || ParentMap::foreach_dart_of_face(phi3(d), f, thread); + //assert(checkPathAroundVertex(vd)) ; + + //bool boundE = false; + + Dart prev = vd.front(); //elt 0 + + Dart db1 = NIL; + if(isBoundaryFace(this->phi2(prev))) + db1 = this->phi2(phi3(this->phi1(this->phi2(prev)))); + + Dart fs = this->phi_1(this->phi2(this->phi_1(prev))); //first side + + ParentMap::splitVertex(prev, this->phi2(fs)); + + for(unsigned int i = 1; i < vd.size(); ++i) + { + prev = vd[i]; + + Dart fs = this->phi_1(this->phi2(this->phi_1(prev))); //first side + + ParentMap::splitVertex(prev, this->phi2(fs)); + + Dart d1 = this->phi_1(this->phi2(this->phi_1(vd[i-1]))); + Dart d2 = this->phi1(this->phi2(vd[i])); + + phi3sew(d1, d2); + } + + Dart db2 = NIL; + if(isBoundaryFace(this->phi2(this->phi_1(prev)))) + db2 = this->phi2(phi3(this->phi2(this->phi_1(prev)))); + + if(db1 != NIL && db2 != NIL) + { + ParentMap::splitVertex(db1, db2); + phi3sew(this->phi1(this->phi2(db2)), this->phi_1(phi3(this->phi2(db2)))); + phi3sew(this->phi1(this->phi2(db1)), this->phi_1(phi3(this->phi2(db1)))); + } + else + { + Dart dbegin = this->phi1(this->phi2(vd.front())); + Dart dend = this->phi_1(this->phi2(this->phi_1(vd.back()))); + phi3sew(dbegin, dend); + } + + return this->phi_1(this->phi2(this->phi_1(prev))); } template -inline bool Map3::foreach_dart_of_volume(Dart d, FunctorType& f, unsigned int thread) const +Dart Map3::deleteVertex(Dart d) { - return ParentMap::foreach_dart_of_cc(d, f, thread); + //if(isBoundaryVertex(d)) + // return NIL ; + + // Save the darts around the vertex + // (one dart per face should be enough) + std::vector fstoretmp; + fstoretmp.reserve(128); + FunctorStore fs(fstoretmp); + foreach_dart_of_vertex(d, fs); + + // just one dart per face + std::vector fstore; + fstore.reserve(128); + DartMarker mf(*this); + for(unsigned int i = 0; i < fstoretmp.size(); ++i) + { + if(!mf.isMarked(fstoretmp[i])) + { + mf.markOrbit(fstoretmp[i]); + fstore.push_back(fstoretmp[i]); + } + } + + std::cout << "nb faces " << fstore.size() << std::endl; + + Dart res = NIL ; + for(std::vector::iterator it = fstore.begin() ; it != fstore.end() ; ++it) + { + Dart fit = *it ; + Dart end = this->phi_1(fit) ; + fit = this->phi1(fit) ; + + if(fit == end) + { + std::cout << " mmmmmmmmmmmmmmmmmmmmmerrrrrrrrrrrrrrrrrde !!!!!!!!!!!! " << std::endl; + +// Dart d2 = phi2(fit) ; +// Dart d23 = phi3(d2) ; +// Dart d3 = phi3(fit) ; +// Dart d32 = phi2(d3) ; +// +// //phi3unsew() +// phi3sew(d3,23); +// +// fit = phi_1(fit); +// +// d2 = phi2(fit) ; +// d23 = phi3(d2) ; +// d3 = phi3(fit) ; +// d32 = phi2(d3) ; +// phi3sew(d3,23); + +// Map2::deleteCC(fit); + } + else + { + while(fit != end) + { + Dart d2 = this->phi2(fit) ; + Dart d3 = phi3(fit) ; + Dart d32 = this->phi2(d3) ; + + if(res == NIL) + res = d2 ; + + this->phi2unsew(d2) ; + this->phi2unsew(d32) ; + this->phi2sew(d2, d32) ; + this->phi2sew(fit, d3) ; + + fit = this->phi1(fit) ; + } + } + } + + ParentMap::deleteCC(d) ; + + return res ; } template -inline bool Map3::foreach_dart_of_vertex2(Dart d, FunctorType& f, unsigned int thread) const +Dart Map3::cutEdge(Dart d) { - return ParentMap::foreach_dart_of_vertex(d, f, thread); + Dart prev = d; + Dart dd = this->alpha2(d); + Dart nd = ParentMap::cutEdge(d); + + while (dd != d) + { + prev = dd; + dd = alpha2(dd); + + ParentMap::cutEdge(prev); + + Dart d3 = phi3(prev); + phi3unsew(prev); + phi3sew(prev, this->phi1(d3)); + phi3sew(d3, this->phi1(prev)); + } + + Dart d3 = phi3(d); + phi3unsew(d); + phi3sew(d, this->phi1(d3)); + phi3sew(d3, this->phi1(d)); + + return nd; } template -inline bool Map3::foreach_dart_of_edge2(Dart d, FunctorType& f, unsigned int thread) const +bool Map3::uncutEdge(Dart d) { - return ParentMap::foreach_dart_of_edge(d, f, thread); + if(vertexDegree(this->phi1(d)) == 2) + { + Dart prev = d ; + phi3unsew(this->phi1(prev)) ; + + Dart dd = d; + do + { + prev = dd; + dd = this->alpha2(dd); + + phi3unsew(this->phi2(prev)) ; + phi3unsew(this->phi2(this->phi1(prev))) ; + ParentMap::uncutEdge(prev); + phi3sew(dd, this->phi2(prev)); + } while (dd != d) ; + + return true; + } + return false; } template -inline bool Map3::foreach_dart_of_face2(Dart d, FunctorType& f, unsigned int thread) const +bool Map3::deleteEdgePreCond(Dart d) { - return ParentMap::foreach_dart_of_face(d, f, thread); + unsigned int nb1 = vertexDegree(d); + unsigned int nb2 = vertexDegree(this->phi1(d)); + return (nb1!=2) && (nb2!=2); +} + +template +Dart Map3::deleteEdge(Dart d) +{ + assert(deleteEdgePreCond(d)); + + if(isBoundaryEdge(d)) + return NIL ; + + Dart res = NIL ; + Dart dit = d ; + do + { + Dart fit = dit ; + Dart end = fit ; + fit = this->phi1(fit) ; + while(fit != end) + { + Dart d2 = this->phi2(fit) ; + Dart d3 = phi3(fit) ; + Dart d32 = this->phi2(d3) ; + + if(res == NIL) + res = d2 ; + + this->phi2unsew(d2) ; + this->phi2unsew(d32) ; + this->phi2sew(d2, d32) ; + this->phi2sew(fit, d3) ; + + fit = this->phi1(fit) ; + } + dit = this->alpha2(dit) ; + } while(dit != d) ; + + ParentMap::deleteCC(d) ; + + return res ; +} + +template +Dart Map3::collapseEdge(Dart d, bool delDegenerateVolumes) +{ + Dart resV = NIL; + Dart dit = d; + + std::vector darts; + do + { + darts.push_back(dit); + dit = this->alpha2(dit); + } while(dit != d); + + for (std::vector::iterator it = darts.begin(); it != darts.end(); ++it) + { + Dart x = this->phi2(this->phi_1(*it)); + + Dart resCV = NIL; + + if(!isBoundaryFace(this->phi2(this->phi1(*it)))) + resCV = phi3(this->phi2(this->phi1(*it))); + else if(!isBoundaryFace(this->phi2(this->phi_1(*it)))) + resCV = phi3(this->phi2(this->phi_1(*it))); + + resV = ParentMap::collapseEdge(*it, true); + if (delDegenerateVolumes) + if(collapseDegeneretedVolume(x) && resCV != NIL) + resV = resCV; + } + + return resV; +} + + +template +bool Map3::splitFacePreCond(Dart d, Dart e) +{ + return (d != e && this->sameOrientedFace(d, e)) ; +} + +template +void Map3::splitFace(Dart d, Dart e) +{ +// assert(d != e && sameOrientedFace(d, e)) ; + assert(splitFacePreCond(d,e)); + + Dart dd = this->phi1(phi3(d)); + Dart ee = this->phi1(phi3(e)); + + ParentMap::splitFace(d, e); + ParentMap::splitFace(dd, ee); + + phi3sew(this->phi_1(d), this->phi_1(ee)); + phi3sew(this->phi_1(e), this->phi_1(dd)); +} + +template +bool Map3::mergeFaces(Dart d) +{ + assert(edgeDegree(d)==2); + + Dart dd = phi3(d); + + phi3unsew(d); + phi3unsew(dd); + + //use code of mergesFaces to override the if(isBoundaryEdge) + //we have to merge the faces if the face is linked to a border also +// Map2::mergeFaces(d); + Dart e = this->phi2(d) ; + this->phi2unsew(d) ; + Map1::mergeCycles(d, this->phi1(e)) ; + Map1::splitCycle(e, this->phi1(d)) ; + Map1::deleteCycle(d) ; +// ParentMap::mergeFaces(dd); + e = this->phi2(dd) ; + this->phi2unsew(dd) ; + Map1::mergeCycles(dd, this->phi1(e)) ; + Map1::splitCycle(e, this->phi1(dd)) ; + Map1::deleteCycle(dd); + + return true; +} + +template +Dart Map3::collapseFace(Dart d, bool delDegenerateVolumes) +{ + Dart resV = NIL; + Dart stop = this->phi_1(d); + Dart dit = d; + std::vector vd; + vd.reserve(32); + + do + { + vd.push_back(this->alpha2(dit)); + dit = this->phi1(dit); + } + while(dit != stop); + + for(std::vector::iterator it = vd.begin() ; it != vd.end() ; ++it) + resV = Map3::collapseEdge(*it, delDegenerateVolumes); + + return resV; +} + +template +bool Map3::collapseDegeneretedVolume(Dart d) +{ + Dart e1 = d; + Dart e2 = this->phi2(d); + + do + { + if (e1 != this->phi2(e2)) + return false; + e1 = this->phi1(e1); + e2 = this->phi_1(e2); + }while (e1 != d); + + if (e2 != this->phi2(d)) + return false; + + // degenerated: + do + { + Dart f1 = phi3(e1); + Dart f2 = phi3(e2); + phi3unsew(e1); + phi3unsew(e2); + phi3sew(f1,f2); + e1 = this->phi1(e1); + e2 = this->phi_1(e2); + }while (e1 != d); + + ParentMap::deleteCC(d) ; + return true; +} + +template +bool Map3::sewVolumesPreCond(Dart d, Dart e) +{ + return (this->faceDegree(d) == this->faceDegree(e)); +} + +template +void Map3::sewVolumes(Dart d, Dart e, bool withBoundary) +{ + assert(sewVolumesPreCond(d,e)); + + // if sewing with fixed points + if (!withBoundary) + { + assert(phi3(d) == d && phi3(e) == e) ; + Dart fitD = d ; + Dart fitE = e ; + do + { + phi3sew(fitD, fitE) ; + fitD = this->phi1(fitD) ; + fitE = this->phi_1(fitE) ; + } while(fitD != d) ; + return ; + } + + Dart dd = phi3(d) ; + Dart ee = phi3(e) ; + + Dart fitD = dd ; + Dart fitE = ee ; + do + { + Dart fitD2 = this->phi2(fitD) ; + Dart fitE2 = this->phi2(fitE) ; + if(fitD2 != fitE) + { + this->phi2unsew(fitD) ; + this->phi2unsew(fitE) ; + this->phi2sew(fitD2, fitE2) ; + this->phi2sew(fitD, fitE) ; + } + phi3unsew(fitD) ; + phi3unsew(fitE) ; + fitD = this->phi1(fitD) ; + fitE = this->phi_1(fitE) ; + } while(fitD != dd) ; + ParentMap::deleteCC(dd) ; + + fitD = d ; + fitE = e ; + do + { + phi3sew(fitD, fitE) ; + fitD = this->phi1(fitD) ; + fitE = this->phi_1(fitE) ; + } while(fitD != d) ; +} + +template +bool Map3::unsewVolumesPreCond(Dart d) +{ + return (!this->isBoundaryFace(d)) ; +} + +template +void Map3::unsewVolumes(Dart d, bool withBoundary) +{ + assert(unsewVolumesPreCond(d)) ; + + if (!withBoundary) + { + Dart fitD = d ; + do + { + phi3unsew(fitD) ; + fitD = this->phi1(fitD) ; + } while(fitD != d) ; + return ; + } + + unsigned int nbE = this->faceDegree(d) ; + Dart d3 = phi3(d); + + Dart b1 = newBoundaryCycle(nbE) ; + Dart b2 = newBoundaryCycle(nbE) ; + + Dart fit1 = d ; + Dart fit2 = d3 ; + Dart fitB1 = b1 ; + Dart fitB2 = b2 ; + do + { + Dart f = findBoundaryFaceOfEdge(fit1) ; + if(f != NIL) + { + Dart f2 = this->phi2(f) ; + this->phi2unsew(f) ; + this->phi2sew(fitB1, f) ; + this->phi2sew(fitB2, f2) ; + } + else + this->phi2sew(fitB1, fitB2) ; + + phi3unsew(fit1) ; + phi3sew(fit1, fitB1) ; + phi3sew(fit2, fitB2) ; + + fit1 = this->phi1(fit1) ; + fit2 = this->phi_1(fit2) ; + fitB1 = this->phi_1(fitB1) ; + fitB2 = this->phi1(fitB2) ; + } while(fitB1 != b1) ; +} + +template +bool Map3::mergeVolumes(Dart d, bool deleteFace) +{ + if(!Map3::isBoundaryFace(d)) + { + ParentMap::mergeVolumes(d, phi3(d), deleteFace); // merge the two volumes along common face + return true ; + } + return false ; +} + +template +void Map3::splitVolume(std::vector& vd) +{ + //assert(checkSimpleOrientedPath(vd)) ; + + Dart e = vd.front(); + Dart e2 = this->phi2(e); + + ParentMap::splitSurface(vd, true, true); + + //sew the two connected components + Map3::sewVolumes(this->phi2(e), this->phi2(e2), false); +} + +template +void Map3::splitVolumeWithFace(std::vector& vd, Dart d) +{ + assert(vd.size() == this->faceDegree(d)); + + // deconnect edges around the path + // sew the given face into the paths + Dart dit = d; + for(std::vector::iterator it = vd.begin() ; it != vd.end() ; ++it) + { + Dart it2 = this->phi2(*it); + ParentMap::unsewFaces(*it, false) ; + + ParentMap::sewFaces(*it, dit, false); + ParentMap::sewFaces(it2, phi3(dit), false); + + dit = this->phi_1(dit); + } +} + +template +Dart Map3::collapseVolume(Dart d, bool delDegenerateVolumes) +{ + Dart resV = NIL; + std::vector vd; + vd.reserve(32); + + vd.push_back(d); + vd.push_back(this->alpha2(this->phi1(d))); + vd.push_back(this->alpha2(this->phi_1(this->phi2(this->phi1(d))))); + +// Traversor3WF tra(*this, phi1(d)); +// for(Dart dit = tra.begin() ; dit != tra.end() ; dit = tra.next()) +// { +// vd.push_back(alpha2(dit)); +// } +// vd.pop_back(); + + for(std::vector::iterator it = vd.begin() ; it != vd.end() ; ++it) + resV = Map3::collapseEdge(*it, delDegenerateVolumes); + + return resV; +} + +template +Dart Map3::faceToEdge(Dart d) +{ + Dart dc = this->phi2(this->phi1(d)); + Dart dc1 = this->phi_1(d); + Dart dc2 = this->phi1(this->phi2(dc)); + + ParentMap::unsewFaces(dc, false); + ParentMap::unsewFaces(dc1, false); + ParentMap::unsewFaces(dc2, false); + + unsewFaces(phi3(dc), false); + unsewFaces(phi3(dc1), false); + unsewFaces(phi3(dc2), false); + + return dc; +} + +/*! @name Topological Queries + * Return or set various topological information + *************************************************************************/ + +template +bool Map3::sameVertex(Dart d, Dart e) const +{ + DartMarkerStore mv(*this); // Lock a marker + + std::vector darts; // Darts that are traversed + darts.reserve(256); + darts.push_back(d); // Start with the dart d + mv.mark(d); + + for(unsigned int i = 0; i < darts.size(); ++i) + { + if(darts[i] == e) + return true; + + // add phi21 and phi23 successor if they are not marked yet + Dart d2 = this->phi2(darts[i]); + Dart d21 = this->phi1(d2); // turn in volume + Dart d23 = phi3(d2); // change volume + + if(!mv.isMarked(d21)) + { + darts.push_back(d21); + mv.mark(d21); + } + if(!mv.isMarked(d23)) + { + darts.push_back(d23); + mv.mark(d23); + } + } + return false; +} + +template +unsigned int Map3::vertexDegree(Dart d) const +{ + unsigned int count = 0; + + Traversor3VE > trav3VE(*this, d); + for(Dart dit = trav3VE.begin() ; dit != trav3VE.end() ; dit = trav3VE.next()) + ++count; + + return count; +} + +template +int Map3::checkVertexDegree(Dart d, unsigned int vd) const +{ + unsigned int count = 0; + + Traversor3VE > trav3VE(*this, d); + Dart dit = trav3VE.begin(); + for( ; (count <= vd) && (dit != trav3VE.end()) ; dit = trav3VE.next()) + ++count; + + return count - vd; +} + +template +unsigned int Map3::vertexDegreeOnBoundary(Dart d) const +{ + assert(Map3::isBoundaryVertex(d)); + return ParentMap::vertexDegree(d); +} + +template +bool Map3::isBoundaryVertex(Dart d) const +{ + DartMarkerStore mv(*this); // Lock a marker + + std::vector darts; // Darts that are traversed + darts.reserve(256); + darts.push_back(d); // Start with the dart d + mv.mark(d); + + for(unsigned int i = 0; i < darts.size(); ++i) + { + if(this->isBoundaryMarked3(darts[i])) + return true ; + + //add phi21 and phi23 successor if they are not marked yet + Dart d2 = this->phi2(darts[i]); + Dart d21 = this->phi1(d2); // turn in volume + Dart d23 = phi3(d2); // change volume + + if(!mv.isMarked(d21)) + { + darts.push_back(d21); + mv.mark(d21); + } + if(!mv.isMarked(d23)) + { + darts.push_back(d23); + mv.mark(d23); + } + } + return false ; +} + +template +Dart Map3::findBoundaryFaceOfVertex(Dart d) const +{ + DartMarkerStore mv(*this); // Lock a marker + + std::vector darts; // Darts that are traversed + darts.reserve(256); + darts.push_back(d); // Start with the dart d + mv.mark(d); + + for(unsigned int i = 0; i < darts.size(); ++i) + { + if(this->isBoundaryMarked3(darts[i])) + return darts[i]; + + //add phi21 and phi23 successor if they are not marked yet + Dart d2 = this->phi2(darts[i]); + Dart d21 = this->phi1(d2); // turn in volume + Dart d23 = phi3(d2); // change volume + + if(!mv.isMarked(d21)) + { + darts.push_back(d21); + mv.mark(d21); + } + if(!mv.isMarked(d23)) + { + darts.push_back(d23); + mv.mark(d23); + } + } + return NIL ; +} + +template +bool Map3::sameOrientedEdge(Dart d, Dart e) const +{ + Dart it = d; + do + { + if(it == e) + return true; + it = alpha2(it); + } while (it != d); + return false; +} + +template +inline bool Map3::sameEdge(Dart d, Dart e) const +{ + return sameOrientedEdge(d, e) || sameOrientedEdge(this->phi2(d), e) ; +} + +template +unsigned int Map3::edgeDegree(Dart d) const +{ + unsigned int deg = 0; + Dart it = d; + do + { + if(!this->isBoundaryMarked3(it)) + ++deg; + it = alpha2(it); + } while(it != d); + return deg; +} + +template +bool Map3::isBoundaryEdge(Dart d) const +{ + Dart it = d; + do + { + if(this->isBoundaryMarked3(it)) + return true ; + it = alpha2(it); + } while(it != d); + return false; +} + +template +Dart Map3::findBoundaryFaceOfEdge(Dart d) const +{ + Dart it = d; + do + { + if (this->isBoundaryMarked3(it)) + return it ; + it = alpha2(it); + } while(it != d); + return NIL ; +} + +template +inline bool Map3::sameFace(Dart d, Dart e) const +{ + return ParentMap::sameOrientedFace(d, e) || ParentMap::sameOrientedFace(phi3(d), e) ; +} + +template +inline bool Map3::isBoundaryFace(Dart d) const +{ + return this->isBoundaryMarked3(d) || this->isBoundaryMarked3(phi3(d)); +} + +template +bool Map3::isBoundaryVolume(Dart d) const +{ + Traversor3WF > tra(*this, d); + for(Dart dit = tra.begin() ; dit != tra.end() ; dit = tra.next()) + { + if(isBoundaryMarked3(phi3(dit))) + return true ; + } + return false; +} + +template +bool Map3::hasBoundaryEdge(Dart d) const +{ + Traversor3WE > tra(*this, d); + for(Dart dit = tra.begin() ; dit != tra.end() ; dit = tra.next()) + { + if(isBoundaryEdge(dit)) + return true; + } + + return false; +} + +template +bool Map3::check() const +{ + std::cout << "Check: topology begin" << std::endl; + DartMarkerStore m(*this); + for(Dart d = Map3::begin(); d != Map3::end(); Map3::next(d)) + { + Dart d3 = phi3(d); + if (phi3(d3) != d) // phi3 involution ? + { + std::cout << "Check: phi3 is not an involution" << std::endl; + return false; + } + + if(this->phi1(d3) != phi3(this->phi_1(d))) + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - Check: phi3 , faces are not entirely sewn" << std::endl; + else + std::cout << "Check: phi3 , faces are not entirely sewn" << std::endl; + std::cout << "face : " << this->phi1(d3) << " and face = " << phi3(this->phi_1(d)) << std::endl; + return false; + } + + Dart d2 = this->phi2(d); + if (this->phi2(d2) != d) // phi2 involution ? + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - "; + std::cout << "Check: phi2 is not an involution" << std::endl; + return false; + } + + Dart d1 = this->phi1(d); + if (this->phi_1(d1) != d) // phi1 a une image correcte ? + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - "; + std::cout << "Check: unconsistent phi_1 link" << std::endl; + return false; + } + + if (m.isMarked(d1)) // phi1 a un seul antécédent ? + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - "; + std::cout << "Check: dart with two phi1 predecessors" << std::endl; + return false; + } + m.mark(d1); + + if (d1 == d) + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - "; + std::cout << "Check: (warning) face loop (one edge)" << std::endl; + } + + if (this->phi1(d1) == d) + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - "; + std::cout << "Check: (warning) face with only two edges" << std::endl; + } + + if (this->phi2(d1) == d) + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - "; + std::cout << "Check: (warning) dandling edge (phi2)" << std::endl; + } + + if (phi3(d1) == d) + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - "; + std::cout << "Check: (warning) dandling edge (phi3)" << std::endl; + } + } + + for(Dart d = this->begin(); d != this->end(); this->next(d)) + { + if (!m.isMarked(d)) // phi1 a au moins un antécédent ? + { + if(this->isBoundaryMarked3(d)) + std::cout << "Boundary case - "; + std::cout << "Check: dart with no phi1 predecessor" << std::endl; + return false; + } + } + + std::cout << "Check: topology ok" << std::endl; + + return true; +} + +/*! @name Cell Functors + * Apply functors to all darts of a cell + *************************************************************************/ + +template +bool Map3::foreach_dart_of_vertex(Dart d, FunctorType& f, unsigned int thread) const +{ + DartMarkerStore mv(*this, thread); // Lock a marker + bool found = false; // Last functor return value + + std::vector darts; // Darts that are traversed + darts.reserve(256); + darts.push_back(d); // Start with the dart d + mv.mark(d); + + for(unsigned int i = 0; !found && i < darts.size(); ++i) + { + // add phi21 and phi23 successor if they are not marked yet + Dart d2 = this->phi2(darts[i]); + Dart d21 = this->phi1(d2); // turn in volume + Dart d23 = phi3(d2); // change volume + + if(!mv.isMarked(d21)) + { + darts.push_back(d21); + mv.mark(d21); + } + if(!mv.isMarked(d23)) + { + darts.push_back(d23); + mv.mark(d23); + } + + found = f(darts[i]); + } + return found; +} + +template +bool Map3::foreach_dart_of_edge(Dart d, FunctorType& f, unsigned int thread) const +{ + Dart it = d; + do + { + if (ParentMap::foreach_dart_of_edge(it, f, thread)) + return true; + it = alpha2(it); + } while (it != d); + return false; +} + +template +inline bool Map3::foreach_dart_of_face(Dart d, FunctorType& f, unsigned int thread) const +{ + return ParentMap::foreach_dart_of_face(d, f, thread) || ParentMap::foreach_dart_of_face(phi3(d), f, thread); +} + +template +inline bool Map3::foreach_dart_of_volume(Dart d, FunctorType& f, unsigned int thread) const +{ + return ParentMap::foreach_dart_of_cc(d, f, thread); +} + +template +bool Map3::foreach_dart_of_cc(Dart d, FunctorType& f, unsigned int thread) const +{ + DartMarkerStore mv(*this,thread); // Lock a marker + bool found = false; // Last functor return value + + std::vector darts; // Darts that are traversed + darts.reserve(1024); + darts.push_back(d); // Start with the dart d + mv.mark(d); + + for(unsigned int i = 0; !found && i < darts.size(); ++i) + { + // add all successors if they are not marked yet + Dart d2 = this->phi1(darts[i]); // turn in face + Dart d3 = this->phi2(darts[i]); // change face + Dart d4 = phi3(darts[i]); // change volume + + if (!mv.isMarked(d2)) + { + darts.push_back(d2); + mv.mark(d2); + } + if (!mv.isMarked(d3)) + { + darts.push_back(d2); + mv.mark(d2); + } + if (!mv.isMarked(d4)) + { + darts.push_back(d4); + mv.mark(d4); + } + + found = f(darts[i]); + } + return found; +} + +template +inline bool Map3::foreach_dart_of_vertex2(Dart d, FunctorType& f, unsigned int thread) const +{ + return ParentMap::foreach_dart_of_vertex(d, f, thread); +} + +template +inline bool Map3::foreach_dart_of_edge2(Dart d, FunctorType& f, unsigned int thread) const +{ + return ParentMap::foreach_dart_of_edge(d, f, thread); +} + +template +inline bool Map3::foreach_dart_of_face2(Dart d, FunctorType& f, unsigned int thread) const +{ + return ParentMap::foreach_dart_of_face(d, f, thread); +} + +/*! @name Close map after import or creation + * These functions must be used with care, generally only by import/creation algorithms + *************************************************************************/ + +template +Dart Map3::newBoundaryCycle(unsigned int nbE) +{ + Dart d = Map1::newCycle(nbE); + this->template boundaryMarkOrbit(d); + return d; +} + +template +unsigned int Map3::closeHole(Dart d, bool forboundary) +{ + assert(phi3(d) == d); // Nothing to close + DartMarkerStore m(*this) ; + + std::vector visitedFaces; // Faces that are traversed + visitedFaces.reserve(1024) ; + visitedFaces.push_back(d); // Start with the face of d + m.markOrbit(d) ; + + unsigned int count = 0 ; + + // For every face added to the list + for(unsigned int i = 0; i < visitedFaces.size(); ++i) + { + Dart it = visitedFaces[i] ; + Dart f = it ; + + unsigned int degree = this->faceDegree(f) ; + Dart b = newBoundaryCycle(degree) ; + ++count ; + + Dart bit = b ; + do + { + Dart e = alpha2(f) ; + bool found = false ; + do + { + if(phi3(e) == e) + { + found = true ; + if(!m.isMarked(e)) + { + visitedFaces.push_back(e) ; + m.markOrbit(e) ; + } + } + else if(this->isBoundaryMarked3(e)) + { + found = true ; + this->phi2sew(e, bit) ; + } + else + e = alpha2(e) ; + } while(!found) ; + + phi3sew(f, bit) ; + bit = this->phi_1(bit) ; + f = this->phi1(f); + } while(f != it) ; + } + + return count ; +} + +template +unsigned int Map3::closeMap() +{ + // Search the map for topological holes (fix points of phi3) + unsigned int nb = 0 ; + for (Dart d = this->begin(); d != this->end(); this->next(d)) + { + if (phi3(d) == d) + { + ++nb ; + closeHole(d); + } + } + return nb ; +} + +/*! @name Compute dual + * These functions compute the dual mesh + *************************************************************************/ + +template +void Map3::reverseOrientation() +{ + +} + +template +void Map3::computeDual() +{ + DartAttribute old_phi1 = this->template getAttribute("phi1") ; + DartAttribute old_phi_1 = this->template getAttribute("phi_1") ; + DartAttribute new_phi1 = this->template addAttribute("new_phi1") ; + DartAttribute new_phi_1 = this->template addAttribute("new_phi_1") ; + + DartAttribute old_phi2 = this->template getAttribute("phi2") ; + DartAttribute new_phi2 = this->template addAttribute("new_phi2") ; + + for(Dart d = this->begin(); d != this->end(); this->next(d)) + { + Dart dd = this->phi2(phi3(d)) ; + new_phi1[d] = dd ; + new_phi_1[dd] = d ; + + Dart ddd = this->phi1(phi3(d)); + new_phi2[d] = ddd; + new_phi2[ddd] = d; + } + + this->template swapAttributes(old_phi1, new_phi1) ; + this->template swapAttributes(old_phi_1, new_phi_1) ; + this->template swapAttributes(old_phi2, new_phi2) ; + + this->removeAttribute(new_phi1) ; + this->removeAttribute(new_phi_1) ; + this->removeAttribute(new_phi2) ; + + this->swapEmbeddingContainers(VERTEX, VOLUME) ; + +// unsigned int count = 0; + +// std::vector vbound; + +// //std::cout << "nb faces : " << closeMap() << std::endl; + +// for(Dart d = begin(); d != end(); next(d)) +// { +// if(isBoundaryMarked3(d) && !isBoundaryMarked3(phi3(d))) +// { +// vbound.push_back(d); +// } +// } +// +// std::cout << "vbound size = " << vbound.size() << std::endl; +// +// for(std::vector::iterator it = vbound.begin() ; it != vbound.end() ; ++it) +// { +// Dart d = *it; +// //Dart d3 = phi3(d); +// phi3unsew(d); +// //phi3unsew(d3); +// } +// +// //std::cout << "nb faces : " << closeMap() << std::endl; +// +// if(d == 14208) +// { +// std::cout << "yeahhhhhhhh" << std::endl; +// std::cout << "isBoundaryMarked ? " << isBoundaryMarked3(phi3(phi2(14208))) << std::endl; +// +// } +// +// //boundaryUnmark<3>(d); +// +// } +// if(d == 1569) +// { +// std::cout << "d " << std::endl; +// +// Traversor3WE t(*this,d); +// for(Dart dit = t.begin() ; dit != t.end() ; dit = t.next()) +// { +// Dart temp = dit; +// do +// { +// if(isBoundaryMarked3(d)) +// std::cout << "d boundary " << std::endl; +// +// temp = alpha2(temp); +// }while(temp != dit); +// } +// +// if(isBoundaryMarked3(d)) +// std::cout << "d boundary " << std::endl; +// +// if(isBoundaryMarked3(phi1(d))) +// std::cout << "phi1(d) boundary " << std::endl; +// +// if(isBoundaryMarked3(phi_1(d))) +// std::cout << "phi_1(d) boundary " << std::endl; +// +// if(isBoundaryMarked3(phi2(d))) +// std::cout << "phi2(d) boundary " << std::endl; +// +// if(isBoundaryMarked3(phi3(d))) +// std::cout << "phi3(d) boundary " << std::endl; +// +// if(isBoundaryMarked3(phi2(phi3(d)))) +// std::cout << "phi2(phi3(d)) boundary " << std::endl; +// +// if(isBoundaryMarked3(phi3(phi2(d)))) +// std::cout << "phi3(phi2(d)) boundary " << std::endl; +// +// if(isBoundaryMarked3(phi1(phi3(d)))) +// std::cout << "phi1(phi3(d)) boundary " << std::endl; +// +// if(isBoundaryMarked3(phi3(phi1(d)))) +// std::cout << "phi3(phi1(d)) boundary " << std::endl; +// } +// +// if(isBoundaryMarked3(d)) +// { +// +// if(isBoundaryMarked3(d)) +// std::cout << "d = " << d << std::endl; +// +// if(isBoundaryMarked3(phi3(d))) +// std::cout << "phi3(d) = " << phi3(d) << std::endl; +// +// if(isBoundaryMarked3(phi2(d))) +// std::cout << "phi2(d) = " << phi2(d) << std::endl; +// +// Dart dit = deleteVertex(phi3(d)); +// +// if(dit == NIL) +// std::cout << "NILLLLLLLLLLLLLLL" << std::endl; +// +// ++count; +// +// if(count == 5) +// return; +// } +// } + + +// TraversorW tW(*this); +// for(Dart d = tW.begin(); d != tW.end(); d = tW.next()) +// { +// if(isBoundaryMarked3(d)) +// { +// boundaryMarkOrbit(d); +// } +// } + +// unsigned int count = 0; +// for(Dart d = begin(); d != end(); next(d)) +// { +// if(isBoundaryMarked3(d)) +// { +// ++count; +// } +// } +// std::cout << "nb boundar marked = " << count << std::endl; +// +// count = 0; +// for(Dart d = begin(); d != end(); next(d)) +// { +// if(isBoundaryMarked3(d)) +// { +// ++count; +// std::cout << count << std::endl; +// //Map3::deleteVolume(d,false); +// //deleteVolume(d,false); +// } +// } + + + //std::cout << "Map closed (" << closeMap() <<" boundary faces)" << std::endl; +} + +template +Dart Map3::explodBorderTopo(Dart d) +{ + std::vector > ve; + ve.reserve(1024); + + //stocke un brin par face du bord + DartMarker me(*this); + for(Dart dit = this->begin() ; dit != this->end() ; this->next(dit)) + { + if(this->isBoundaryMarked3(dit) && !me.isMarked(dit)) + { + ve.push_back(std::make_pair(dit, this->phi2(dit))); + me.markOrbit(dit); + } + } + + //decoud chaque face + for(std::vector >::iterator it = ve.begin() ; it != ve.end() ; ++it) + { + ParentMap::unsewFaces((*it).first, false); + } + + //triangule chaque face + DartMarker mf(*this); + for(std::vector >::iterator it = ve.begin() ; it != ve.end() ; ++it) + { + Dart first = (*it).first; + Dart second = (*it).second; + + if(!mf.isMarked(first)) + { + unsigned int degf = ParentMap::faceDegree(first); + + Dart dnf = ParentMap::newFace(degf, false); + Dart dit = first; + do + { + ParentMap::sewFaces(dit, dnf, false); + this->template copyDartEmbedding(dnf, this->phi1(dit)) ; + dit = this->phi1(dit); + dnf = this->phi_1(dnf); + } while(dit != first); + + mf.markOrbit(first); + + Dart db = dnf; + Dart d1 = this->phi1(db); + ParentMap::splitFace(db, d1) ; + ParentMap::cutEdge(this->phi_1(db)) ; + + Dart x = phi2(this->phi_1(db)) ; + Dart dd = this->phi1(this->phi1(this->phi1(x))); + while(dd != x) + { + Dart next = this->phi1(dd) ; + ParentMap::splitFace(dd, this->phi1(x)) ; + dd = next ; + } + + Dart cd = this->phi_1(db); + do + { + this->template setDartEmbedding(this->phi2(cd), this->template getEmbedding(this->phi1(cd))) ; + cd = this->phi2(this->phi_1(cd)); + } while(cd != this->phi_1(db)); + } + + if(!mf.isMarked(second)) + { + mf.markOrbit(second); + unsigned int degf = ParentMap::faceDegree(second); + + Dart dnf = ParentMap::newFace(degf, false); + Dart dit = second; + do + { + ParentMap::sewFaces(dit, dnf, false); + this->template copyDartEmbedding(dnf, this->phi1(dit)); + dit = this->phi1(dit); + dnf = this->phi_1(dnf); + } while(dit != second); + + mf.markOrbit(second); + + Dart db = dnf; + Dart d1 = this->phi1(db); + ParentMap::splitFace(db, d1); + ParentMap::cutEdge(this->phi_1(db)); + + Dart x = this->phi2(this->phi_1(db)) ; + Dart dd = this->phi1(this->phi1(this->phi1(x))); + while(dd != x) + { + Dart next = this->phi1(dd) ; + ParentMap::splitFace(dd, this->phi1(x)) ; + dd = next ; + } + + Dart cd = this->phi_1(db); + do + { + this->template setDartEmbedding(this->phi2(cd), this->template getEmbedding(this->phi1(cd))) ; + cd = this->phi2(this->phi_1(cd)); + } while(cd != this->phi_1(db)); + } + } + + //close de chaque nouveau volume + for(std::vector >::iterator it = ve.begin() ; it != ve.end() ; ++it) + { + Dart dit1 = this->phi2((*it).first); + Dart dit2 = this->phi2((*it).second); + Map3::sewVolumes(dit1, dit2, false); + } + + this->template setOrbitEmbeddingOnNewCell(this->phi_1(this->phi2(ve.front().first))); + + return this->phi_1(this->phi2(ve.front().first)); +} + +template +void Map3::computeDualTest() +{ +// unsigned int count = 0; +// CellMarkerNoUnmark cv(*this); +// std::vector v; +// for(Dart d = begin(); d != end(); next(d)) +// { +// if(!cv.isMarked(d) && isBoundaryMarked3(d)) +// { +// ++count; +// v.push_back(d); +// cv.mark(d); +// } +// } +// +// cv.unmarkAll(); + +// std::cout << "boundary vertices : " << count << std::endl; + + DartAttribute old_phi1 = this->template getAttribute("phi1") ; + DartAttribute old_phi_1 = this->template getAttribute("phi_1") ; + DartAttribute new_phi1 = this->template addAttribute("new_phi1") ; + DartAttribute new_phi_1 = this->template addAttribute("new_phi_1") ; + + DartAttribute old_phi2 = this->template getAttribute("phi2") ; + DartAttribute new_phi2 = this->template addAttribute("new_phi2") ; + + for(Dart d = this->begin(); d != this->end(); this->next(d)) + { + Dart dd = this->phi2(phi3(d)) ; + new_phi1[d] = dd ; + new_phi_1[dd] = d ; + + Dart ddd = this->phi1(phi3(d)); + new_phi2[d] = ddd; + new_phi2[ddd] = d; + } + + this->template swapAttributes(old_phi1, new_phi1) ; + this->template swapAttributes(old_phi_1, new_phi_1) ; + this->template swapAttributes(old_phi2, new_phi2) ; + + this->removeAttribute(new_phi1) ; + this->removeAttribute(new_phi_1) ; + this->removeAttribute(new_phi2) ; + + this->swapEmbeddingContainers(VERTEX, VOLUME) ; + + for(Dart d = this->begin(); d != this->end(); this->next(d)) + { + if(this->isBoundaryMarked3(d)) + Map3::deleteVolume(d, false); + } + + closeMap(); + +// reverseOrientation(); +// +// for(std::vector::iterator it = v.begin() ; it != v.end() ; ++it) +// { +// boundaryUnmarkOrbit(*it); +// } +// +// for(std::vector::iterator it = v.begin() ; it != v.end() ; ++it) +// { +// Map3::deleteVolume(*it); +// } +// +// std::cout << "boundary faces : " << closeMap() << std::endl; + +// //boundary management +// for(Dart d = begin(); d != end(); next(d)) +// { +// if(isBoundaryMarked3(d)) +// { +// //Dart dit = deleteVertex(phi3(d)); +// //deleteVolume(phi3(d)); +// //if(dit == NIL) +// //{ +// // std::cout << "ploooooooooooooooooooop" << std::endl; +// // return; +// //} +// //else +// //{ +// // std::cout << "gooooooooooooooooooooood" << std::endl; +// // boundaryMarkOrbit(dit); +// // return; +// //} +// //boundaryUnmarkOrbit(d); +// //deleteVolume(d); +// } +// } + } } // namespace CGoGN diff --git a/src/Topology/generic/genericmap.cpp b/src/Topology/generic/genericmap.cpp index 43471192..96fba7a0 100644 --- a/src/Topology/generic/genericmap.cpp +++ b/src/Topology/generic/genericmap.cpp @@ -298,210 +298,6 @@ void GenericMap::removeThreadMarker(unsigned int nb) * SAVE & LOAD * ****************************************/ -bool GenericMap::saveMapBin(const std::string& filename) const -{ - CGoGNostream fs(filename.c_str(), std::ios::out|std::ios::binary); - if (!fs) - { - CGoGNerr << "Unable to open file for writing: " << filename << CGoGNendl; - return false; - } - - // Entete - char* buff = new char[256]; - for (int i = 0; i < 256; ++i) - buff[i] = char(255); - if (m_isMultiRes) - { - const char* cgogn = "CGoGN_MRMap"; - memcpy(buff, cgogn, 12); - } - else - { - const char* cgogn = "CGoGN_Map"; - memcpy(buff, cgogn, 10); - } - std::string mt = mapTypeName(); - const char* mtc = mt.c_str(); - memcpy(buff+32, mtc, mt.size()+1); - unsigned int *buffi = reinterpret_cast(buff + 64); - *buffi = NB_ORBITS; - fs.write(reinterpret_cast(buff), 256); - delete buff; - - // save all attribs - for (unsigned int i = 0; i < NB_ORBITS; ++i) - m_attribs[i].saveBin(fs, i); - - if (m_isMultiRes) - { - m_mrattribs.saveBin(fs, 00); - - fs.write(reinterpret_cast(&m_mrCurrentLevel), sizeof(unsigned int)); - - unsigned int nb = m_mrNbDarts.size(); - fs.write(reinterpret_cast(&nb), sizeof(unsigned int)); - fs.write(reinterpret_cast(&(m_mrNbDarts[0])), nb *sizeof(unsigned int)); - } - - return true; -} - -bool GenericMap::loadMapBin(const std::string& filename) -{ - - CGoGNistream fs(filename.c_str(), std::ios::in|std::ios::binary); - if (!fs) - { - CGoGNerr << "Unable to open file for loading" << CGoGNendl; - return false; - } - - GenericMap::clear(true); - - // read info - char* buff = new char[256]; - fs.read(reinterpret_cast(buff), 256); - - std::string buff_str(buff); - // Check file type - if (m_isMultiRes) - { - if (buff_str == "CGoGN_Map") - { - CGoGNerr<< "Wrong binary file format, file is not a MR-Map"<< CGoGNendl; - return false; - } - if (buff_str != "CGoGN_MRMap") - { - CGoGNerr<< "Wrong binary file format"<< CGoGNendl; - return false; - } - } - else - { - if (buff_str == "CGoGN_MRMap") - { - CGoGNerr<< "Wrong binary file format, file is a MR-Map"<< CGoGNendl; - return false; - } - if (buff_str != "CGoGN_Map") - { - CGoGNerr<< "Wrong binary file format"<< CGoGNendl; - return false; - } - } - - - // Check map type - buff_str = std::string(buff + 32); - - std::string localType = this->mapTypeName(); - - std::string fileType = buff_str; - - if (fileType != localType) - { - CGoGNerr << "Not possible to load "<< fileType << " into " << localType << " object" << CGoGNendl; - return false; - } - - // Check max nb orbit - unsigned int *ptr_nbo = reinterpret_cast(buff + 64); - unsigned int nbo = *ptr_nbo; - if (nbo != NB_ORBITS) - { - CGoGNerr << "Wrond max orbit number in file" << CGoGNendl; - return false; - } - - // load attrib container - for (unsigned int i = 0; i < NB_ORBITS; ++i) - { - unsigned int id = AttributeContainer::loadBinId(fs); - m_attribs[id].loadBin(fs); - } - - if (m_isMultiRes) - { - AttributeContainer::loadBinId(fs); // not used but need to read to skip - m_mrattribs.loadBin(fs); - - fs.read(reinterpret_cast(&m_mrCurrentLevel), sizeof(unsigned int)); - unsigned int nb; - fs.read(reinterpret_cast(&nb), sizeof(unsigned int)); - m_mrNbDarts.resize(nb); - fs.read(reinterpret_cast(&(m_mrNbDarts[0])), nb *sizeof(unsigned int)); - } - - // retrieve m_embeddings (from m_attribs) - update_m_emb_afterLoad(); - - // recursive call from real type of map (for topo relation attributes pointers) down to GenericMap (for Marker_cleaning & pointers) - update_topo_shortcuts(); - - // restore nbThreads - std::vector typeMark; - unsigned int nbatt0 = m_attribs[0].getAttributesTypes(typeMark); - m_nbThreads = 0; - for (unsigned int i = 0; i < nbatt0; ++i) - { - if (typeMark[i] == "Mark") - ++m_nbThreads; - } - - // restore quick traversals pointers if necessary (containers already ok) - for (unsigned int orb=0; orb("quick_traversal") ; - for(unsigned int j = 0; j < NB_ORBITS; ++j) - { - std::stringstream ss; - ss << "quickLocalIncidentTraversal_" << j; - m_quickLocalIncidentTraversal[orb][j] = m_attribs[orb].getDataVector< NoTypeNameAttribute > >(ss.str()) ; - std::stringstream ss2; - ss2 << "quickLocalAdjacentTraversal" << j; - m_quickLocalAdjacentTraversal[orb][j] = m_attribs[orb].getDataVector< NoTypeNameAttribute > >(ss2.str()) ; - } - } - - return true; -} - -bool GenericMap::copyFrom(const GenericMap& map) -{ - if (mapTypeName() != map.mapTypeName()) - { - CGoGNerr << "try to copy from incompatible type map" << CGoGNendl; - return false; - } - - GenericMap::clear(true); - - // load attrib container - for (unsigned int i = 0; i < NB_ORBITS; ++i) - m_attribs[i].copyFrom(map.m_attribs[i]); - - if (m_isMultiRes) - { - m_mrattribs.copyFrom(map.m_mrattribs); - m_mrCurrentLevel = map.m_mrCurrentLevel; - - unsigned int nb = map.m_mrNbDarts.size(); - m_mrNbDarts.resize(nb); - for (unsigned int i = 0; i < nb; ++i) - m_mrNbDarts[i] = map.m_mrNbDarts[i]; - } - - // retrieve m_embeddings (from m_attribs) - update_m_emb_afterLoad(); - - // recursive call from real type of map (for topo relation attributes pointers) down to GenericMap (for Marker_cleaning & pointers) - update_topo_shortcuts(); - - return true; -} - void GenericMap::update_m_emb_afterLoad() { // get container of dart orbit @@ -726,188 +522,14 @@ void GenericMap::compact() * DARTS TRAVERSALS * ****************************************/ -//bool GenericMap::foreach_dart(FunctorType& f) -//{ -// for (Dart d = begin(); d != end(); next(d)) -// { -// if (f(d)) -// return true; -// } -// return false; -//} +bool GenericMap::foreach_dart(FunctorType& f) +{ + for (Dart d = begin(); d != end(); next(d)) + { + if (f(d)) + return true; + } + return false; +} } // namespace CGoGN - -// -//bool GenericMap::saveMapXml(const std::string& filename, bool compress) -//{ -// xmlTextWriterPtr writer = xmlNewTextWriterFilename(filename.c_str(), 0); -// xmlTextWriterStartDocument(writer,NULL,NULL,NULL); -// -// // Entete -// int rc = xmlTextWriterStartElement(writer, BAD_CAST "CGoGN_Map"); -// rc = xmlTextWriterWriteAttribute(writer, BAD_CAST "type", BAD_CAST this->mapTypeName().c_str()); -// rc = xmlTextWriterWriteFormatAttribute(writer, BAD_CAST "nb_max_orbits","%u",NB_ORBITS); -// -// // save m_attribs -// for (unsigned int i=0; iname),(char*)"CGoGN_Map")!=0) -// if (!chechXmlNode(map_node,"CGoGN_Map")) -// { -// CGoGNerr << "Wrong xml format: Root node != CGoGN_Map"<< CGoGNendl; -// return false; -// } -// -// // check the file type -// xmlChar *prop = xmlGetProp(map_node, BAD_CAST "type"); -// CGoGNout << "Loading "<< prop <<" xml file"<< CGoGNendl; -// -// // check the nb max orbits -// prop = xmlGetProp(map_node, BAD_CAST "nb_max_orbits"); -// unsigned int nbo = atoi((char*)prop); -// if (nbo != NB_ORBITS) -// { -// CGoGNerr << "Wrong nb max orbits in xml map"<< CGoGNendl; -// return false; -// } -// -// /*********************************************** -// * load attributs -// ************************************************/ -// for (xmlNode* cur_node = map_node->children; cur_node; cur_node = cur_node->next) -// { -// // for each attribute -//// if (strcmp((char*)(cur_node->name),(char*)"Attributes_Container")==0) -// if (chechXmlNode(cur_node, "Attributes_Container")) -// { -// CGoGNout << "LOAD ATTRIBUT"<< CGoGNendl; -// // get the orbit id -// unsigned int id = AttributeContainer::getIdXmlNode(cur_node); -// // and load container -// unsigned int nba = m_attribs[id].getNbAttributes(); -// -// -// CGoGNout << "attribut "<& amv = contDart.getDataVector(i) ; -//// -//// std::string orbitname = name.substr(4, name.size()-4); -//// std::istringstream iss(orbitname); -//// unsigned int orbit; -//// iss >> orbit; -//// -//// m_embeddings[orbit] = &amv ; -//// } -//// } -//// -//// -// update_m_emb_afterLoad(); -// -// /*********************************************** -// * load Orbit_MarkerSet & BoundaryMarker -// ************************************************/ -// xmlNode* cur_node = map_node->children; -// bool read1=false; -// bool read2=false; -// while (!(read1 || read2) && cur_node)// scan nodes to find the one with right name -// { -//// if (strcmp((char*)(cur_node->name),(char*)"Orbit_MarkerSet") == 0) -// if (chechXmlNode(cur_node, "Orbit_MarkerSet")) -// { -// for (xmlNode* mark_node = cur_node->children; mark_node; mark_node = mark_node->next) -// { -// xmlChar* prop = xmlGetProp(mark_node, BAD_CAST "orbit"); -// unsigned int orb = atoi((char*)prop); -// prop = xmlGetProp(mark_node, BAD_CAST "val"); -// unsigned int val = atoi((char*)prop); -// m_marksets[orb][0].setMarkVal(val); -// } -// read1 =true; -// } -// else -// { -//// if (strcmp((char*)(cur_node->name),(char*)"Boundary_Marker") == 0) -// CGoGNout << "Orbit_MarkerSet"<next; -// } -// -// if (!(read1 && read2)) -// { -// CGoGNerr <<"Error reading Marker in xml node"<(buff + 64); + *buffi = NB_ORBITS; + fs.write(reinterpret_cast(buff), 256); + delete buff; + + // save all attribs + for (unsigned int i = 0; i < NB_ORBITS; ++i) + m_attribs[i].saveBin(fs, i); + + return true; +} + +bool MapMono::loadMapBin(const std::string& filename) +{ + CGoGNistream fs(filename.c_str(), std::ios::in|std::ios::binary); + if (!fs) + { + CGoGNerr << "Unable to open file for loading" << CGoGNendl; + return false; + } + + GenericMap::clear(true); + + // read info + char* buff = new char[256]; + fs.read(reinterpret_cast(buff), 256); + + std::string buff_str(buff); + // Check file type + if (buff_str == "CGoGN_MRMap") + { + CGoGNerr<< "Wrong binary file format, file is a MR-Map"<< CGoGNendl; + return false; + } + if (buff_str != "CGoGN_Map") + { + CGoGNerr<< "Wrong binary file format"<< CGoGNendl; + return false; + } + + // Check map type + buff_str = std::string(buff + 32); + + std::string localType = this->mapTypeName(); + + std::string fileType = buff_str; + + if (fileType != localType) + { + CGoGNerr << "Not possible to load "<< fileType << " into " << localType << " object" << CGoGNendl; + return false; + } + + // Check max nb orbit + unsigned int *ptr_nbo = reinterpret_cast(buff + 64); + unsigned int nbo = *ptr_nbo; + if (nbo != NB_ORBITS) + { + CGoGNerr << "Wrond max orbit number in file" << CGoGNendl; + return false; + } + + // load attrib container + for (unsigned int i = 0; i < NB_ORBITS; ++i) + { + unsigned int id = AttributeContainer::loadBinId(fs); + m_attribs[id].loadBin(fs); + } + + // retrieve m_embeddings (from m_attribs) + update_m_emb_afterLoad(); + + // recursive call from real type of map (for topo relation attributes pointers) down to GenericMap (for Marker_cleaning & pointers) + update_topo_shortcuts(); + + // restore nbThreads + std::vector typeMark; + unsigned int nbatt0 = m_attribs[0].getAttributesTypes(typeMark); + m_nbThreads = 0; + for (unsigned int i = 0; i < nbatt0; ++i) + { + if (typeMark[i] == "Mark") + ++m_nbThreads; + } + + // restore quick traversals pointers if necessary (containers already ok) + for (unsigned int orb=0; orb("quick_traversal") ; + for(unsigned int j = 0; j < NB_ORBITS; ++j) + { + std::stringstream ss; + ss << "quickLocalIncidentTraversal_" << j; + m_quickLocalIncidentTraversal[orb][j] = m_attribs[orb].getDataVector< NoTypeNameAttribute > >(ss.str()) ; + std::stringstream ss2; + ss2 << "quickLocalAdjacentTraversal" << j; + m_quickLocalAdjacentTraversal[orb][j] = m_attribs[orb].getDataVector< NoTypeNameAttribute > >(ss2.str()) ; + } + } + + return true; +} + +bool MapMono::copyFrom(const GenericMap& map) +{ + const MapMono& mapM = reinterpret_cast(map); + + if (mapTypeName() != map.mapTypeName()) + { + CGoGNerr << "try to copy from incompatible type map" << CGoGNendl; + return false; + } + + GenericMap::clear(true); + + // load attrib container + for (unsigned int i = 0; i < NB_ORBITS; ++i) + m_attribs[i].copyFrom(mapM.m_attribs[i]); + + // retrieve m_embeddings (from m_attribs) + update_m_emb_afterLoad(); + + // recursive call from real type of map (for topo relation attributes pointers) down to GenericMap (for Marker_cleaning & pointers) + update_topo_shortcuts(); + + return true; +} + +} //namespace CGoGN diff --git a/src/Topology/generic/mapMulti.cpp b/src/Topology/generic/mapMulti.cpp index eecd6c15..aabfaaf8 100644 --- a/src/Topology/generic/mapMulti.cpp +++ b/src/Topology/generic/mapMulti.cpp @@ -24,6 +24,9 @@ #include "Topology/generic/mapMulti.h" +namespace CGoGN +{ + /**************************************** * RESOLUTION LEVELS MANAGEMENT * ****************************************/ @@ -193,3 +196,181 @@ void MapMulti::duplicateDarts(unsigned int newlevel) (*attrib)[i] = copyDartLine(oldi) ; // copy the dart and affect it to the new level } } + +/**************************************** + * SAVE & LOAD * + ****************************************/ + +bool MapMulti::saveMapBin(const std::string& filename) const +{ + CGoGNostream fs(filename.c_str(), std::ios::out|std::ios::binary); + if (!fs) + { + CGoGNerr << "Unable to open file for writing: " << filename << CGoGNendl; + return false; + } + + // Entete + char* buff = new char[256]; + for (int i = 0; i < 256; ++i) + buff[i] = char(255); + + memcpy(buff, "CGoGN_MRMap", 12); + + std::string mt = mapTypeName(); + const char* mtc = mt.c_str(); + memcpy(buff+32, mtc, mt.size()+1); + unsigned int *buffi = reinterpret_cast(buff + 64); + *buffi = NB_ORBITS; + fs.write(reinterpret_cast(buff), 256); + delete buff; + + // save all attribs + for (unsigned int i = 0; i < NB_ORBITS; ++i) + m_attribs[i].saveBin(fs, i); + + m_mrattribs.saveBin(fs, 00); + + fs.write(reinterpret_cast(&m_mrCurrentLevel), sizeof(unsigned int)); + + unsigned int nb = m_mrNbDarts.size(); + fs.write(reinterpret_cast(&nb), sizeof(unsigned int)); + fs.write(reinterpret_cast(&(m_mrNbDarts[0])), nb *sizeof(unsigned int)); + + return true; +} + +bool MapMulti::loadMapBin(const std::string& filename) +{ + CGoGNistream fs(filename.c_str(), std::ios::in|std::ios::binary); + if (!fs) + { + CGoGNerr << "Unable to open file for loading" << CGoGNendl; + return false; + } + + GenericMap::clear(true); + + // read info + char* buff = new char[256]; + fs.read(reinterpret_cast(buff), 256); + + std::string buff_str(buff); + // Check file type + if (buff_str == "CGoGN_Map") + { + CGoGNerr << "Wrong binary file format, file is not a MR-Map" << CGoGNendl; + return false; + } + if (buff_str != "CGoGN_MRMap") + { + CGoGNerr << "Wrong binary file format" << CGoGNendl; + return false; + } + + // Check map type + buff_str = std::string(buff + 32); + + std::string localType = this->mapTypeName(); + + std::string fileType = buff_str; + + if (fileType != localType) + { + CGoGNerr << "Not possible to load "<< fileType << " into " << localType << " object" << CGoGNendl; + return false; + } + + // Check max nb orbit + unsigned int *ptr_nbo = reinterpret_cast(buff + 64); + unsigned int nbo = *ptr_nbo; + if (nbo != NB_ORBITS) + { + CGoGNerr << "Wrond max orbit number in file" << CGoGNendl; + return false; + } + + // load attrib container + for (unsigned int i = 0; i < NB_ORBITS; ++i) + { + unsigned int id = AttributeContainer::loadBinId(fs); + m_attribs[id].loadBin(fs); + } + + AttributeContainer::loadBinId(fs); // not used but need to read to skip + m_mrattribs.loadBin(fs); + + fs.read(reinterpret_cast(&m_mrCurrentLevel), sizeof(unsigned int)); + unsigned int nb; + fs.read(reinterpret_cast(&nb), sizeof(unsigned int)); + m_mrNbDarts.resize(nb); + fs.read(reinterpret_cast(&(m_mrNbDarts[0])), nb *sizeof(unsigned int)); + + // retrieve m_embeddings (from m_attribs) + update_m_emb_afterLoad(); + + // recursive call from real type of map (for topo relation attributes pointers) down to GenericMap (for Marker_cleaning & pointers) + update_topo_shortcuts(); + + // restore nbThreads + std::vector typeMark; + unsigned int nbatt0 = m_attribs[0].getAttributesTypes(typeMark); + m_nbThreads = 0; + for (unsigned int i = 0; i < nbatt0; ++i) + { + if (typeMark[i] == "Mark") + ++m_nbThreads; + } + + // restore quick traversals pointers if necessary (containers already ok) + for (unsigned int orb=0; orb("quick_traversal") ; + for(unsigned int j = 0; j < NB_ORBITS; ++j) + { + std::stringstream ss; + ss << "quickLocalIncidentTraversal_" << j; + m_quickLocalIncidentTraversal[orb][j] = m_attribs[orb].getDataVector< NoTypeNameAttribute > >(ss.str()) ; + std::stringstream ss2; + ss2 << "quickLocalAdjacentTraversal" << j; + m_quickLocalAdjacentTraversal[orb][j] = m_attribs[orb].getDataVector< NoTypeNameAttribute > >(ss2.str()) ; + } + } + + return true; +} + +bool MapMulti::copyFrom(const GenericMap& map) +{ + const MapMulti& mapMR = reinterpret_cast(map); + + if (mapTypeName() != map.mapTypeName()) + { + CGoGNerr << "try to copy from incompatible type map" << CGoGNendl; + return false; + } + + GenericMap::clear(true); + + // load attrib container + for (unsigned int i = 0; i < NB_ORBITS; ++i) + m_attribs[i].copyFrom(mapMR.m_attribs[i]); + + m_mrattribs.copyFrom(mapMR.m_mrattribs); + m_mrCurrentLevel = mapMR.m_mrCurrentLevel; + + unsigned int nb = mapMR.m_mrNbDarts.size(); + m_mrNbDarts.resize(nb); + for (unsigned int i = 0; i < nb; ++i) + m_mrNbDarts[i] = mapMR.m_mrNbDarts[i]; + + // retrieve m_embeddings (from m_attribs) + update_m_emb_afterLoad(); + + // recursive call from real type of map (for topo relation attributes pointers) down to GenericMap (for Marker_cleaning & pointers) + update_topo_shortcuts(); + + return true; +} + +} //namespace CGoGN diff --git a/src/Topology/map/embeddedMap2.cpp b/src/Topology/map/embeddedMap2.cpp index ccd406c9..0bf210c1 100644 --- a/src/Topology/map/embeddedMap2.cpp +++ b/src/Topology/map/embeddedMap2.cpp @@ -706,6 +706,18 @@ bool EmbeddedMap2::check() CGoGNout << "Check: embedding ok" << CGoGNendl ; + std::cout << "nb vertex orbits : " << getNbOrbits() << std::endl ; + if (isOrbitEmbedded()) + std::cout << "nb vertex cells : " << m_attribs[VERTEX].size() << std::endl ; + + std::cout << "nb edge orbits : " << getNbOrbits() << std::endl ; + if (isOrbitEmbedded()) + std::cout << "nb edge cells : " << m_attribs[EDGE].size() << std::endl ; + + std::cout << "nb face orbits : " << getNbOrbits() << std::endl ; + if (isOrbitEmbedded()) + std::cout << "nb face cells : " << m_attribs[FACE].size() << std::endl ; + return true ; } diff --git a/src/Topology/map/embeddedMap3.cpp b/src/Topology/map/embeddedMap3.cpp index f932ba84..b49ae40b 100644 --- a/src/Topology/map/embeddedMap3.cpp +++ b/src/Topology/map/embeddedMap3.cpp @@ -606,16 +606,16 @@ unsigned int EmbeddedMap3::closeHole(Dart d, bool forboundary) bool EmbeddedMap3::check() { - std::cout << "nb vertex orbits : " << getNbOrbits() << std::endl ; + std::cout << "nb vertex orbits : " << getNbOrbits() << std::endl ; std::cout << "nb vertex cells : " << m_attribs[VERTEX].size() << std::endl ; - std::cout << "nb edge orbits : " << getNbOrbits() << std::endl ; + std::cout << "nb edge orbits : " << getNbOrbits() << std::endl ; std::cout << "nb edge cells : " << m_attribs[EDGE].size() << std::endl ; - std::cout << "nb face orbits : " << getNbOrbits() << std::endl ; + std::cout << "nb face orbits : " << getNbOrbits() << std::endl ; std::cout << "nb face cells : " << m_attribs[FACE].size() << std::endl ; - std::cout << "nb volume orbits : " << getNbOrbits() << std::endl ; + std::cout << "nb volume orbits : " << getNbOrbits() << std::endl ; std::cout << "nb volume cells : " << m_attribs[VOLUME].size() << std::endl ; diff --git a/src/Topology/map/map1.cpp b/src/Topology/map/map1.cpp deleted file mode 100644 index 7acd0407..00000000 --- a/src/Topology/map/map1.cpp +++ /dev/null @@ -1,30 +0,0 @@ -/******************************************************************************* -* CGoGN: Combinatorial and Geometric modeling with Generic N-dimensional Maps * -* version 0.1 * -* Copyright (C) 2009-2012, IGG Team, LSIIT, University of Strasbourg * -* * -* This library is free software; you can redistribute it and/or modify it * -* under the terms of the GNU Lesser General Public License as published by the * -* Free Software Foundation; either version 2.1 of the License, or (at your * -* option) any later version. * -* * -* This library is distributed in the hope that it will be useful, but WITHOUT * -* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * -* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License * -* for more details. * -* * -* You should have received a copy of the GNU Lesser General Public License * -* along with this library; if not, write to the Free Software Foundation, * -* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * -* * -* Web site: http://cgogn.unistra.fr/ * -* Contact information: cgogn@unistra.fr * -* * -*******************************************************************************/ - -#include "Topology/map/map1.h" - -namespace CGoGN -{ - -} // namespace CGoGN diff --git a/src/Topology/map/map2.cpp b/src/Topology/map/map2.cpp deleted file mode 100644 index 65ae9594..00000000 --- a/src/Topology/map/map2.cpp +++ /dev/null @@ -1,69 +0,0 @@ -/******************************************************************************* -* CGoGN: Combinatorial and Geometric modeling with Generic N-dimensional Maps * -* version 0.1 * -* Copyright (C) 2009-2012, IGG Team, LSIIT, University of Strasbourg * -* * -* This library is free software; you can redistribute it and/or modify it * -* under the terms of the GNU Lesser General Public License as published by the * -* Free Software Foundation; either version 2.1 of the License, or (at your * -* option) any later version. * -* * -* This library is distributed in the hope that it will be useful, but WITHOUT * -* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * -* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License * -* for more details. * -* * -* You should have received a copy of the GNU Lesser General Public License * -* along with this library; if not, write to the Free Software Foundation, * -* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * -* * -* Web site: http://cgogn.unistra.fr/ * -* Contact information: cgogn@unistra.fr * -* * -*******************************************************************************/ - -#include "Topology/map/map2.h" -#include "Topology/generic/traversorCell.h" -#include "Topology/generic/dartmarker.h" - -namespace CGoGN -{ - -//void Map2::rdfi(Dart t, DartMarker& m1, DartMarker& m2) -//{ -// Dart p = NIL; -// while (!(p == NIL && (t == NIL || (m1.isMarked(t) || m2.isMarked(t)) ) ) ) -// { -// if (t == NIL || (m1.isMarked(t) || m2.isMarked(t))) -// { -// if (m2.isMarked(p)) // pop -// { -// Dart q = phi2(p); // q = p->s1; -// unsigned int pi=dartIndex(p); -// (*m_phi2)[pi]=t; // p->s1 = t; -// t = p; -// p = q; -// } -// else // swing -// { -// m2.mark(p); // p->val = 2; -// Dart q = phi1(p); // q = p->s0; -// unsigned int pi=dartIndex(p); -// (*m_phi1)[pi]=t; // p->s0 = t; -// t = phi2(p); // t = p->s1; -// (*m_phi2)[pi]=q; // p->s1 = q; -// } -// } -// else // push -// { -// m1.mark(t); // t->val = 1; -// Dart q = phi1(t); // q = t->s0; -// unsigned int ti=dartIndex(t); -// (*m_phi1)[ti]=p; // t->s0 = p; -// p = t; -// t = q; -// } -// } -//} - -} // namespace CGoGN diff --git a/src/Topology/map/map3.cpp b/src/Topology/map/map3.cpp deleted file mode 100644 index a7a2992c..00000000 --- a/src/Topology/map/map3.cpp +++ /dev/null @@ -1,1727 +0,0 @@ -/******************************************************************************* -* CGoGN: Combinatorial and Geometric modeling with Generic N-dimensional Maps * -* version 0.1 * -* Copyright (C) 2009-2012, IGG Team, LSIIT, University of Strasbourg * -* * -* This library is free software; you can redistribute it and/or modify it * -* under the terms of the GNU Lesser General Public License as published by the * -* Free Software Foundation; either version 2.1 of the License, or (at your * -* option) any later version. * -* * -* This library is distributed in the hope that it will be useful, but WITHOUT * -* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * -* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License * -* for more details. * -* * -* You should have received a copy of the GNU Lesser General Public License * -* along with this library; if not, write to the Free Software Foundation, * -* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. * -* * -* Web site: http://cgogn.unistra.fr/ * -* Contact information: cgogn@unistra.fr * -* * -*******************************************************************************/ - -#include "Topology/map/map3.h" -#include "Topology/generic/traversor3.h" - -namespace CGoGN -{ - -void Map3::compactTopoRelations(const std::vector& oldnew) -{ - for (unsigned int i = m_attribs[DART].begin(); i != m_attribs[DART].end(); m_attribs[DART].next(i)) - { - unsigned int d_index = dartIndex(m_phi1->operator[](i)); - if (d_index != oldnew[d_index]) - m_phi1->operator[](i) = Dart(oldnew[d_index]); - - d_index = dartIndex(m_phi_1->operator[](i)); - if (d_index != oldnew[d_index]) - m_phi_1->operator[](i) = Dart(oldnew[d_index]); - - d_index = dartIndex(m_phi2->operator[](i)); - if (d_index != oldnew[d_index]) - m_phi2->operator[](i) = Dart(oldnew[d_index]); - - d_index = dartIndex(m_phi3->operator[](i)); - if (d_index != oldnew[d_index]) - m_phi3->operator[](i) = Dart(oldnew[d_index]); -// -// { -// Dart& d = m_phi1->operator [](i); -// Dart e = Dart(oldnew[d.index]); -// if (d != e) -// d = e; -// } -// { -// Dart& d = m_phi_1->operator [](i); -// Dart e = Dart(oldnew[d.index]); -// if (d != e) -// d = e; -// } -// { -// Dart& d = m_phi2->operator [](i); -// Dart e = Dart(oldnew[d.index]); -// if (d != e) -// d = e; -// } -// { -// Dart& d = m_phi3->operator [](i); -// Dart e = Dart(oldnew[d.index]); -// if (d != e) -// d = e; -// } - } -} - -/*! @name Generator and Deletor - * To generate or delete volumes in a 3-map - *************************************************************************/ - -void Map3::deleteVolume(Dart d, bool withBoundary) -{ - if(withBoundary) - { - DartMarkerStore mark(*this); // Lock a marker - - std::vector visitedFaces; // Faces that are traversed - visitedFaces.reserve(512); - visitedFaces.push_back(d); // Start with the face of d - - mark.markOrbit(d) ; - - for(unsigned int i = 0; i < visitedFaces.size(); ++i) - { - Dart e = visitedFaces[i] ; - - if(!isBoundaryFace(e)) - unsewVolumes(e) ; - - do // add all face neighbours to the table - { - Dart ee = phi2(e) ; - if(!mark.isMarked(ee)) // not already marked - { - visitedFaces.push_back(ee) ; - mark.markOrbit(ee) ; - } - e = phi1(e) ; - } while(e != visitedFaces[i]) ; - } - - Dart dd = phi3(d) ; - Map2::deleteCC(d) ; //deleting the volume - Map2::deleteCC(dd) ; //deleting its border (created from the unsew operation) - - return; - } - - //else remove the CC and create fixed points - DartMarkerStore mark(*this); // Lock a marker - - std::vector visitedFaces; // Faces that are traversed - visitedFaces.reserve(512); - visitedFaces.push_back(d); // Start with the face of d - - mark.markOrbit(d) ; - - for(unsigned int i = 0; i < visitedFaces.size(); ++i) - { - Dart e = visitedFaces[i] ; - - Dart it = e ; - do - { - phi3unsew(it); - it = phi1(it) ; - } while(it != e) ; - - do // add all face neighbours to the table - { - Dart ee = phi2(e) ; - if(!mark.isMarked(ee)) // not already marked - { - visitedFaces.push_back(ee) ; - mark.markOrbit(ee) ; - } - e = phi1(e) ; - } while(e != visitedFaces[i]) ; - } - - Map2::deleteCC(d) ; //deleting the volume -} - -void Map3::fillHole(Dart d) -{ - assert(isBoundaryFace(d)) ; - Dart dd = d ; - if(!isBoundaryMarked3(dd)) - dd = phi3(dd) ; - boundaryUnmarkOrbit(dd) ; -} - -void Map3::createHole(Dart d) -{ - assert(!isBoundaryFace(d)) ; - boundaryMarkOrbit(d) ; -} - -/*! @name Topological Operators - * Topological operations on 3-maps - *************************************************************************/ - -Dart Map3::splitVertex(std::vector& vd) -{ - //assert(checkPathAroundVertex(vd)) ; - - //bool boundE = false; - - Dart prev = vd.front(); //elt 0 - - Dart db1 = NIL; - if(isBoundaryFace(phi2(prev))) - { - db1 = phi2(phi3(phi1(phi2(prev)))); - } - - Dart fs = phi_1(phi2(phi_1(prev))); //first side - - Map2::splitVertex(prev, phi2(fs)); - - for(unsigned int i = 1; i < vd.size(); ++i) - { - prev = vd[i]; - - Dart fs = phi_1(phi2(phi_1(prev))); //first side - - Map2::splitVertex(prev, phi2(fs)); - - Dart d1 = phi_1(phi2(phi_1(vd[i-1]))); - Dart d2 = phi1(phi2(vd[i])); - - phi3sew(d1, d2); - } - - Dart db2 = NIL; - if(isBoundaryFace(phi2(phi_1(prev)))) - { - db2 = phi2(phi3(phi2(phi_1(prev)))); - } - - if(db1 != NIL && db2 != NIL) - { - Map2::splitVertex(db1, db2); - phi3sew(phi1(phi2(db2)), phi_1(phi3(phi2(db2)))); - phi3sew(phi1(phi2(db1)), phi_1(phi3(phi2(db1)))); - } - else - { - Dart dbegin = phi1(phi2(vd.front())); - Dart dend = phi_1(phi2(phi_1(vd.back()))); - phi3sew(dbegin, dend); - } - - return phi_1(phi2(phi_1(prev))); -} - -// //unsew the face path -// for(std::vector::iterator it = vd.begin() ; it != vd.end() ; ++it) -// { -// Dart dit = *it; -// -// Map1::cutEdge(phi_1(phi2(phi_1(dit)))); //comme un vertexSplit -// Map1::cutEdge(phi2(phi1(phi2(dit)))); -// Map2::sewFaces(phi1(phi2(phi1(phi2(dit)))), phi_1(phi2(phi_1(dit))), false); -// -// -// -// Dart dit3 = phi3(dit); -// unsewVolumes(dit); - -// Dart f1 = newFace(3,false); -// Dart f2 = newFace(3,false); -// Dart f3 = newFace(3,false); -// Dart f4 = newFace(3,false); -// -// sewFaces(f1,f2,false); -// sewFaces(phi_1(f1), f3, false); -// sewFaces(phi1(f1), f4, false); -// sewFaces(phi_1(f2), phi1(f4), false); -// sewFaces(phi_1(f3), phi1(f2), false); -// sewFaces(phi1(f3), phi_1(f4), false); -// -// sewVolumes(dit,f3); -// sewVolumes(dit3,f4); -// } - -/* - if(isBoundaryVertex(d)) - { - unsewVolumes(d); - unsewVolumes(e); - - Dart dc = phi1(phi2(d)); - - //unsewVolumes(phi2(dc)); - Map2::splitVertex(d, phi1(phi2(dc))); - - -// Map2::splitFace(d, phi2(dc)); - -// Dart ec = phi_1(phi2(e)); -// Map2::splitVertex(e, ec); -// //Map2::splitFace(e, phi2(ec)); - } -*/ - - -Dart Map3::deleteVertex(Dart d) -{ - //if(isBoundaryVertex(d)) - // return NIL ; - - // Save the darts around the vertex - // (one dart per face should be enough) - std::vector fstoretmp; - fstoretmp.reserve(128); - FunctorStore fs(fstoretmp); - foreach_dart_of_vertex(d, fs); - - // just one dart per face - std::vector fstore; - fstore.reserve(128); - DartMarker mf(*this); - for(unsigned int i = 0; i < fstoretmp.size(); ++i) - { - if(!mf.isMarked(fstoretmp[i])) - { - mf.markOrbit(fstoretmp[i]); - fstore.push_back(fstoretmp[i]); - } - } - - std::cout << "nb faces " << fstore.size() << std::endl; - - Dart res = NIL ; - for(std::vector::iterator it = fstore.begin() ; it != fstore.end() ; ++it) - { - Dart fit = *it ; - Dart end = phi_1(fit) ; - fit = phi1(fit) ; - - if(fit == end) - { - std::cout << " mmmmmmmmmmmmmmmmmmmmmerrrrrrrrrrrrrrrrrde !!!!!!!!!!!! " << std::endl; - -// Dart d2 = phi2(fit) ; -// Dart d23 = phi3(d2) ; -// Dart d3 = phi3(fit) ; -// Dart d32 = phi2(d3) ; -// -// //phi3unsew() -// phi3sew(d3,23); -// -// fit = phi_1(fit); -// -// d2 = phi2(fit) ; -// d23 = phi3(d2) ; -// d3 = phi3(fit) ; -// d32 = phi2(d3) ; -// phi3sew(d3,23); - -// Map2::deleteCC(fit); - } - else - { - while(fit != end) - { - Dart d2 = phi2(fit) ; - Dart d3 = phi3(fit) ; - Dart d32 = phi2(d3) ; - - if(res == NIL) - res = d2 ; - - phi2unsew(d2) ; - phi2unsew(d32) ; - phi2sew(d2, d32) ; - phi2sew(fit, d3) ; - - fit = phi1(fit) ; - } - } - } - - Map2::deleteCC(d) ; - - return res ; -} - -Dart Map3::cutEdge(Dart d) -{ - Dart prev = d; - Dart dd = alpha2(d); - Dart nd = Map2::cutEdge(d); - - while (dd != d) - { - prev = dd; - dd = alpha2(dd); - - Map2::cutEdge(prev); - - Dart d3 = phi3(prev); - phi3unsew(prev); - phi3sew(prev, phi1(d3)); - phi3sew(d3, phi1(prev)); - } - - Dart d3 = phi3(d); - phi3unsew(d); - phi3sew(d, phi1(d3)); - phi3sew(d3, phi1(d)); - - return nd; -} - -bool Map3::uncutEdge(Dart d) -{ - if(vertexDegree(phi1(d)) == 2) - { - Dart prev = d ; - phi3unsew(phi1(prev)) ; - - Dart dd = d; - do - { - prev = dd; - dd = alpha2(dd); - - phi3unsew(phi2(prev)) ; - phi3unsew(phi2(phi1(prev))) ; - Map2::uncutEdge(prev); - phi3sew(dd, phi2(prev)); - } while (dd != d) ; - - return true; - } - return false; -} - -bool Map3::deleteEdgePreCond(Dart d) -{ - unsigned int nb1 = vertexDegree(d); - unsigned int nb2 = vertexDegree(phi1(d)); - return (nb1!=2) && (nb2!=2); -} - -Dart Map3::deleteEdge(Dart d) -{ - assert(deleteEdgePreCond(d)); - - if(isBoundaryEdge(d)) - return NIL ; - - Dart res = NIL ; - Dart dit = d ; - do - { - Dart fit = dit ; - Dart end = fit ; - fit = phi1(fit) ; - while(fit != end) - { - Dart d2 = phi2(fit) ; - Dart d3 = phi3(fit) ; - Dart d32 = phi2(d3) ; - - if(res == NIL) - res = d2 ; - - phi2unsew(d2) ; - phi2unsew(d32) ; - phi2sew(d2, d32) ; - phi2sew(fit, d3) ; - - fit = phi1(fit) ; - } - dit = alpha2(dit) ; - } while(dit != d) ; - - Map2::deleteCC(d) ; - - return res ; -} - -//Dart Map3::collapseEdge(Dart d, bool delDegenerateVolumes) -//{ -// Dart resV = NIL; -// -// Dart dit = d; -// -// do -// { -// Dart e = dit; -// dit = alpha2(dit); -// -// //test si un seul polyedre autour de l'arete -// if(e == dit) -// resV == phi3(phi2(phi1(e))); -// -// if(delDegenerateVolumes) -// { -// Map2::collapseEdge(e, true); -// collapseDegeneretedVolume(e); -// } -// else -// Map2::collapseEdge(e, false); -// -// if(resV == NIL) -// { -// -// } -// -// }while(d != dit); -// -// return resV; -//} - -Dart Map3::collapseEdge(Dart d, bool delDegenerateVolumes) -{ - Dart resV = NIL; - Dart dit = d; - - std::vector darts; - do - { - darts.push_back(dit); - dit = alpha2(dit); - }while(dit != d); - - for (std::vector::iterator it = darts.begin(); it != darts.end(); ++it) - { - Dart x = phi2(phi_1(*it)); - - Dart resCV = NIL; - - if(!isBoundaryFace(phi2(phi1(*it)))) - resCV = phi3(phi2(phi1(*it))); - else if(!isBoundaryFace(phi2(phi_1(*it)))) - resCV = phi3(phi2(phi_1(*it))); - - resV = Map2::collapseEdge(*it, true); - if (delDegenerateVolumes) - if(collapseDegeneretedVolume(x) && resCV != NIL) - resV = resCV; - } - - return resV; -} - - -bool Map3::splitFacePreCond(Dart d, Dart e) -{ - return (d != e && sameOrientedFace(d, e)) ; -} - -void Map3::splitFace(Dart d, Dart e) -{ -// assert(d != e && sameOrientedFace(d, e)) ; - assert(splitFacePreCond(d,e)); - - Dart dd = phi1(phi3(d)); - Dart ee = phi1(phi3(e)); - - Map2::splitFace(d, e); - Map2::splitFace(dd, ee); - - phi3sew(phi_1(d), phi_1(ee)); - phi3sew(phi_1(e), phi_1(dd)); -} - -bool Map3::mergeFaces(Dart d) -{ - assert(edgeDegree(d)==2); - - Dart dd = phi3(d); - - phi3unsew(d); - phi3unsew(dd); - - //use code of mergesFaces to override the if(isBoundaryEdge) - //we have to merge the faces if the face is linked to a border also -// Map2::mergeFaces(d); - Dart e = phi2(d) ; - phi2unsew(d) ; - Map1::mergeCycles(d, phi1(e)) ; - Map1::splitCycle(e, phi1(d)) ; - Map1::deleteCycle(d) ; -// Map2::mergeFaces(dd); - e = phi2(dd) ; - phi2unsew(dd) ; - Map1::mergeCycles(dd, phi1(e)) ; - Map1::splitCycle(e, phi1(dd)) ; - Map1::deleteCycle(dd); - - return true; -} - -Dart Map3::collapseFace(Dart d, bool delDegenerateVolumes) -{ - Dart resV = NIL; - Dart stop = phi_1(d); - Dart dit = d; - std::vector vd; - vd.reserve(32); - - do - { - vd.push_back(alpha2(dit)); - dit = phi1(dit); - } - while(dit != stop); - - for(std::vector::iterator it = vd.begin() ; it != vd.end() ; ++it) - resV = Map3::collapseEdge(*it, delDegenerateVolumes); - - return resV; -} - -//bool Map3::collapseDegeneretedVolume(Dart d) -//{ -// Dart e1 = phi2(d); -// Dart e2 = phi2(phi1(d)); -// -// //Si les deux faces ne sont pas du bord -// if(!isBoundaryFace(e1) && !isBoundaryFace(e2)) -// { -// sewVolumes(phi3(e1),phi3(e2)); -// deleteVolume(d); -// return true; -// } -// else -// { -// //alors simple suppression du volume degenere -// deleteVolume(d); -// return true; -// } -// -// return false; -//} - -bool Map3::collapseDegeneretedVolume(Dart d) -{ - Dart e1 = d; - Dart e2 = phi2(d); - - do - { - if (e1 != phi2(e2)) - return false; - e1 = phi1(e1); - e2 = phi_1(e2); - }while (e1 != d); - - if (e2 != phi2(d)) - return false; - - // degenerated: - do - { - Dart f1 = phi3(e1); - Dart f2 = phi3(e2); - phi3unsew(e1); - phi3unsew(e2); - phi3sew(f1,f2); - e1 = phi1(e1); - e2 = phi_1(e2); - }while (e1 != d); - - Map2::deleteCC(d) ; - return true; -} - - -bool Map3::sewVolumesPreCond(Dart d, Dart e) -{ - return (faceDegree(d) == faceDegree(e)); -} - -void Map3::sewVolumes(Dart d, Dart e, bool withBoundary) -{ - assert(sewVolumesPreCond(d,e)); - - // if sewing with fixed points - if (!withBoundary) - { - assert(phi3(d) == d && phi3(e) == e) ; - Dart fitD = d ; - Dart fitE = e ; - do - { - phi3sew(fitD, fitE) ; - fitD = phi1(fitD) ; - fitE = phi_1(fitE) ; - } while(fitD != d) ; - return ; - } - - Dart dd = phi3(d) ; - Dart ee = phi3(e) ; - - Dart fitD = dd ; - Dart fitE = ee ; - do - { - Dart fitD2 = phi2(fitD) ; - Dart fitE2 = phi2(fitE) ; - if(fitD2 != fitE) - { - phi2unsew(fitD) ; - phi2unsew(fitE) ; - phi2sew(fitD2, fitE2) ; - phi2sew(fitD, fitE) ; - } - phi3unsew(fitD) ; - phi3unsew(fitE) ; - fitD = phi1(fitD) ; - fitE = phi_1(fitE) ; - } while(fitD != dd) ; - Map2::deleteCC(dd) ; - - fitD = d ; - fitE = e ; - do - { - phi3sew(fitD, fitE) ; - fitD = phi1(fitD) ; - fitE = phi_1(fitE) ; - } while(fitD != d) ; -} - -bool Map3::unsewVolumesPreCond(Dart d) -{ - return (!isBoundaryFace(d)) ; -} - - -void Map3::unsewVolumes(Dart d, bool withBoundary) -{ - assert(unsewVolumesPreCond(d)) ; - - if (!withBoundary) - { - Dart fitD = d ; - do - { - phi3unsew(fitD) ; - fitD = phi1(fitD) ; - } while(fitD != d) ; - return ; - } - - unsigned int nbE = faceDegree(d) ; - Dart d3 = phi3(d); - - Dart b1 = newBoundaryCycle(nbE) ; - Dart b2 = newBoundaryCycle(nbE) ; - - Dart fit1 = d ; - Dart fit2 = d3 ; - Dart fitB1 = b1 ; - Dart fitB2 = b2 ; - do - { - Dart f = findBoundaryFaceOfEdge(fit1) ; - if(f != NIL) - { - Dart f2 = phi2(f) ; - phi2unsew(f) ; - phi2sew(fitB1, f) ; - phi2sew(fitB2, f2) ; - } - else - phi2sew(fitB1, fitB2) ; - - phi3unsew(fit1) ; - phi3sew(fit1, fitB1) ; - phi3sew(fit2, fitB2) ; - - fit1 = phi1(fit1) ; - fit2 = phi_1(fit2) ; - fitB1 = phi_1(fitB1) ; - fitB2 = phi1(fitB2) ; - } while(fitB1 != b1) ; -} - -bool Map3::mergeVolumes(Dart d, bool deleteFace) -{ - if(!Map3::isBoundaryFace(d)) - { - Map2::mergeVolumes(d, phi3(d), deleteFace); // merge the two volumes along common face - return true ; - } - return false ; -} - -void Map3::splitVolume(std::vector& vd) -{ - //assert(checkSimpleOrientedPath(vd)) ; - - Dart e = vd.front(); - Dart e2 = phi2(e); - - Map2::splitSurface(vd,true,true); - - //sew the two connected components - Map3::sewVolumes(phi2(e), phi2(e2), false); -} - -void Map3::splitVolumeWithFace(std::vector& vd, Dart d) -{ - assert(vd.size() == faceDegree(d)); - - // deconnect edges around the path - // sew the given face into the paths - Dart dit = d; - for(std::vector::iterator it = vd.begin() ; it != vd.end() ; ++it) - { - Dart it2 = phi2(*it); - unsewFaces(*it, false) ; - - sewFaces(*it,dit,false); - sewFaces(it2, phi3(dit),false); - - dit = phi_1(dit); - - } -} - -Dart Map3::collapseVolume(Dart d, bool delDegenerateVolumes) -{ - Dart resV = NIL; - std::vector vd; - vd.reserve(32); - - vd.push_back(d); - vd.push_back(alpha2(phi1(d))); - vd.push_back(alpha2(phi_1(phi2(phi1(d))))); - -// Traversor3WF tra(*this, phi1(d)); -// for(Dart dit = tra.begin() ; dit != tra.end() ; dit = tra.next()) -// { -// vd.push_back(alpha2(dit)); -// } -// vd.pop_back(); - - for(std::vector::iterator it = vd.begin() ; it != vd.end() ; ++it) - resV = Map3::collapseEdge(*it, delDegenerateVolumes); - - return resV; -} - - -Dart Map3::faceToEdge(Dart d) -{ - Dart dc = phi2(phi1(d)); - Dart dc1 = phi_1(d); - Dart dc2 = phi1(phi2(dc)); - - unsewFaces(dc,false); - unsewFaces(dc1,false); - unsewFaces(dc2,false); - - unsewFaces(phi3(dc),false); - unsewFaces(phi3(dc1),false); - unsewFaces(phi3(dc2),false); - - - - return dc; -} - -/*! @name Topological Queries - * Return or set various topological information - *************************************************************************/ - -bool Map3::sameVertex(Dart d, Dart e) const -{ - DartMarkerStore mv(*this); // Lock a marker - - std::vector darts; // Darts that are traversed - darts.reserve(256); - darts.push_back(d); // Start with the dart d - mv.mark(d); - - for(unsigned int i = 0; i < darts.size(); ++i) - { - if(darts[i] == e) - return true; - - // add phi21 and phi23 successor if they are not marked yet - Dart d2 = phi2(darts[i]); - Dart d21 = phi1(d2); // turn in volume - Dart d23 = phi3(d2); // change volume - - if(!mv.isMarked(d21)) - { - darts.push_back(d21); - mv.mark(d21); - } - if(!mv.isMarked(d23)) - { - darts.push_back(d23); - mv.mark(d23); - } - } - return false; -} - -unsigned int Map3::vertexDegree(Dart d) const -{ - unsigned int count = 0; - - Traversor3VE trav3VE(*this, d); - for(Dart dit = trav3VE.begin() ; dit != trav3VE.end() ; dit = trav3VE.next()) - { - ++count; - } - - return count; -} - - -int Map3::checkVertexDegree(Dart d, unsigned int vd) const -{ - unsigned int count = 0; - - Traversor3VE trav3VE(*this, d); - Dart dit = trav3VE.begin(); - for( ; (count<=vd) && (dit != trav3VE.end()) ; dit = trav3VE.next()) - { - ++count; - } - - return count - vd; -} - - -unsigned int Map3::vertexDegreeOnBoundary(Dart d) const -{ - assert(Map3::isBoundaryVertex(d)); - - return Map2::vertexDegree(d); -} - -bool Map3::isBoundaryVertex(Dart d) const -{ - DartMarkerStore mv(*this); // Lock a marker - - std::vector darts; // Darts that are traversed - darts.reserve(256); - darts.push_back(d); // Start with the dart d - mv.mark(d); - - for(unsigned int i = 0; i < darts.size(); ++i) - { - if(isBoundaryMarked3(darts[i])) - return true ; - - //add phi21 and phi23 successor if they are not marked yet - Dart d2 = phi2(darts[i]); - Dart d21 = phi1(d2); // turn in volume - Dart d23 = phi3(d2); // change volume - - if(!mv.isMarked(d21)) - { - darts.push_back(d21); - mv.mark(d21); - } - if(!mv.isMarked(d23)) - { - darts.push_back(d23); - mv.mark(d23); - } - } - return false ; -} - -Dart Map3::findBoundaryFaceOfVertex(Dart d) const -{ - DartMarkerStore mv(*this); // Lock a marker - - std::vector darts; // Darts that are traversed - darts.reserve(256); - darts.push_back(d); // Start with the dart d - mv.mark(d); - - for(unsigned int i = 0; i < darts.size(); ++i) - { - if(isBoundaryMarked3(darts[i])) - return darts[i]; - - //add phi21 and phi23 successor if they are not marked yet - Dart d2 = phi2(darts[i]); - Dart d21 = phi1(d2); // turn in volume - Dart d23 = phi3(d2); // change volume - - if(!mv.isMarked(d21)) - { - darts.push_back(d21); - mv.mark(d21); - } - if(!mv.isMarked(d23)) - { - darts.push_back(d23); - mv.mark(d23); - } - } - return NIL ; -} - -bool Map3::sameOrientedEdge(Dart d, Dart e) const -{ - Dart it = d; - do - { - if(it == e) - return true; - it = alpha2(it); - } while (it != d); - return false; -} - -unsigned int Map3::edgeDegree(Dart d) const -{ - unsigned int deg = 0; - Dart it = d; - do - { - if(!isBoundaryMarked3(it)) - ++deg; - it = alpha2(it); - } while(it != d); - return deg; -} - -bool Map3::isBoundaryEdge(Dart d) const -{ - Dart it = d; - do - { - if(isBoundaryMarked3(it)) - return true ; - it = alpha2(it); - } while(it != d); - return false; -} - -Dart Map3::findBoundaryFaceOfEdge(Dart d) const -{ - Dart it = d; - do - { - if (isBoundaryMarked3(it)) - return it ; - it = alpha2(it); - } while(it != d); - return NIL ; -} - -bool Map3::isBoundaryVolume(Dart d) const -{ - Traversor3WF tra(*this, d); - for(Dart dit = tra.begin() ; dit != tra.end() ; dit = tra.next()) - { - if(isBoundaryMarked3(phi3(dit))) - return true ; - } - return false; -} - -bool Map3::hasBoundaryEdge(Dart d) const -{ - Traversor3WE tra(*this, d); - for(Dart dit = tra.begin() ; dit != tra.end() ; dit = tra.next()) - { - if(isBoundaryEdge(dit)) - return true; - } - - return false; -} - -bool Map3::check() const -{ - std::cout << "Check: topology begin" << std::endl; - DartMarkerStore m(*this); - for(Dart d = Map3::begin(); d != Map3::end(); Map3::next(d)) - { - Dart d3 = phi3(d); - if (phi3(d3) != d) // phi3 involution ? - { - std::cout << "Check: phi3 is not an involution" << std::endl; - return false; - } - - if(phi1(d3) != phi3(phi_1(d))) - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - Check: phi3 , faces are not entirely sewn" << std::endl; - else - std::cout << "Check: phi3 , faces are not entirely sewn" << std::endl; - std::cout << "face : " << phi1(d3) << " and face = " << phi3(phi_1(d)) << std::endl; - return false; - } - - Dart d2 = phi2(d); - if (phi2(d2) != d) // phi2 involution ? - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - "; - - std::cout << "Check: phi2 is not an involution" << std::endl; - return false; - } - - Dart d1 = phi1(d); - if (phi_1(d1) != d) // phi1 a une image correcte ? - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - "; - - std::cout << "Check: unconsistent phi_1 link" << std::endl; - return false; - } - - if (m.isMarked(d1)) // phi1 a un seul antécédent ? - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - "; - - std::cout << "Check: dart with two phi1 predecessors" << std::endl; - return false; - } - m.mark(d1); - - if (d1 == d) - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - "; - - std::cout << "Check: (warning) face loop (one edge)" << std::endl; - } - - if (phi1(d1) == d) - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - "; - - std::cout << "Check: (warning) face with only two edges" << std::endl; - } - - if (phi2(d1) == d) - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - "; - - std::cout << "Check: (warning) dandling edge (phi2)" << std::endl; - } - - if (phi3(d1) == d) - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - "; - - std::cout << "Check: (warning) dandling edge (phi3)" << std::endl; - } - } - - for(Dart d = this->begin(); d != this->end(); this->next(d)) - { - if (!m.isMarked(d)) // phi1 a au moins un antécédent ? - { - if(isBoundaryMarked3(d)) - std::cout << "Boundary case - "; - - std::cout << "Check: dart with no phi1 predecessor" << std::endl; - return false; - } - } - - std::cout << "Check: topology ok" << std::endl; - - return true; -} - -/*! @name Cell Functors - * Apply functors to all darts of a cell - *************************************************************************/ - -bool Map3::foreach_dart_of_vertex(Dart d, FunctorType& f, unsigned int thread) const -{ - DartMarkerStore mv(*this, thread); // Lock a marker - bool found = false; // Last functor return value - - std::vector darts; // Darts that are traversed - darts.reserve(256); - darts.push_back(d); // Start with the dart d - mv.mark(d); - - for(unsigned int i = 0; !found && i < darts.size(); ++i) - { - // add phi21 and phi23 successor if they are not marked yet - Dart d2 = phi2(darts[i]); - Dart d21 = phi1(d2); // turn in volume - Dart d23 = phi3(d2); // change volume - - if(!mv.isMarked(d21)) - { - darts.push_back(d21); - mv.mark(d21); - } - if(!mv.isMarked(d23)) - { - darts.push_back(d23); - mv.mark(d23); - } - - found = f(darts[i]); - } - return found; -} - -bool Map3::foreach_dart_of_edge(Dart d, FunctorType& f, unsigned int thread) const -{ - Dart it = d; - do - { - if (Map2::foreach_dart_of_edge(it, f, thread)) - return true; - it = alpha2(it); - } while (it != d); - return false; -} - -bool Map3::foreach_dart_of_cc(Dart d, FunctorType& f, unsigned int thread) const -{ - DartMarkerStore mv(*this,thread); // Lock a marker - bool found = false; // Last functor return value - - std::vector darts; // Darts that are traversed - darts.reserve(1024); - darts.push_back(d); // Start with the dart d - mv.mark(d); - - for(unsigned int i = 0; !found && i < darts.size(); ++i) - { - // add all successors if they are not marked yet - Dart d2 = phi1(darts[i]); // turn in face - Dart d3 = phi2(darts[i]); // change face - Dart d4 = phi3(darts[i]); // change volume - - if (!mv.isMarked(d2)) - { - darts.push_back(d2); - mv.mark(d2); - } - if (!mv.isMarked(d3)) - { - darts.push_back(d2); - mv.mark(d2); - } - if (!mv.isMarked(d4)) - { - darts.push_back(d4); - mv.mark(d4); - } - - found = f(darts[i]); - } - return found; -} - -/*! @name Close map after import or creation - * These functions must be used with care, generally only by import/creation algorithms - *************************************************************************/ - -Dart Map3::newBoundaryCycle(unsigned int nbE) -{ - Dart d = Map1::newCycle(nbE); - boundaryMarkOrbit(d); - return d; -} - -unsigned int Map3::closeHole(Dart d, bool forboundary) -{ - assert(phi3(d) == d); // Nothing to close - DartMarkerStore m(*this) ; - - std::vector visitedFaces; // Faces that are traversed - visitedFaces.reserve(1024) ; - visitedFaces.push_back(d); // Start with the face of d - m.markOrbit(d) ; - - unsigned int count = 0 ; - - // For every face added to the list - for(unsigned int i = 0; i < visitedFaces.size(); ++i) - { - Dart it = visitedFaces[i] ; - Dart f = it ; - - unsigned int degree = faceDegree(f) ; - Dart b = newBoundaryCycle(degree) ; - ++count ; - - Dart bit = b ; - do - { - Dart e = alpha2(f) ; - bool found = false ; - do - { - if(phi3(e) == e) - { - found = true ; - if(!m.isMarked(e)) - { - visitedFaces.push_back(e) ; - m.markOrbit(e) ; - } - } - else if(isBoundaryMarked3(e)) - { - found = true ; - phi2sew(e, bit) ; - } - else - e = alpha2(e) ; - } while(!found) ; - - phi3sew(f, bit) ; - bit = phi_1(bit) ; - f = phi1(f); - } while(f != it) ; - } - - return count ; -} - -unsigned int Map3::closeMap() -{ - // Search the map for topological holes (fix points of phi3) - unsigned int nb = 0 ; - for (Dart d = begin(); d != end(); next(d)) - { - if (phi3(d) == d) - { - ++nb ; - closeHole(d); - } - } - return nb ; -} - -/*! @name Compute dual - * These functions compute the dual mesh - *************************************************************************/ - -void Map3::reverseOrientation() -{ - -} - -void Map3::computeDual() -{ - DartAttribute old_phi1 = getAttribute("phi1") ; - DartAttribute old_phi_1 = getAttribute("phi_1") ; - DartAttribute new_phi1 = addAttribute("new_phi1") ; - DartAttribute new_phi_1 = addAttribute("new_phi_1") ; - - DartAttribute old_phi2 = getAttribute("phi2") ; - DartAttribute new_phi2 = addAttribute("new_phi2") ; - - for(Dart d = begin(); d != end(); next(d)) - { - Dart dd = phi2(phi3(d)) ; - new_phi1[d] = dd ; - new_phi_1[dd] = d ; - - Dart ddd = phi1(phi3(d)); - new_phi2[d] = ddd; - new_phi2[ddd] = d; - } - - swapAttributes(old_phi1, new_phi1) ; - swapAttributes(old_phi_1, new_phi_1) ; - swapAttributes(old_phi2, new_phi2) ; - - removeAttribute(new_phi1) ; - removeAttribute(new_phi_1) ; - removeAttribute(new_phi2) ; - - swapEmbeddingContainers(VERTEX, VOLUME) ; - -// unsigned int count = 0; - -// std::vector vbound; - -// //std::cout << "nb faces : " << closeMap() << std::endl; - -// for(Dart d = begin(); d != end(); next(d)) -// { -// if(isBoundaryMarked3(d) && !isBoundaryMarked3(phi3(d))) -// { -// vbound.push_back(d); -// } -// } -// -// std::cout << "vbound size = " << vbound.size() << std::endl; -// -// for(std::vector::iterator it = vbound.begin() ; it != vbound.end() ; ++it) -// { -// Dart d = *it; -// //Dart d3 = phi3(d); -// phi3unsew(d); -// //phi3unsew(d3); -// } -// -// //std::cout << "nb faces : " << closeMap() << std::endl; -// -// if(d == 14208) -// { -// std::cout << "yeahhhhhhhh" << std::endl; -// std::cout << "isBoundaryMarked ? " << isBoundaryMarked3(phi3(phi2(14208))) << std::endl; -// -// } -// -// //boundaryUnmark<3>(d); -// -// } -// if(d == 1569) -// { -// std::cout << "d " << std::endl; -// -// Traversor3WE t(*this,d); -// for(Dart dit = t.begin() ; dit != t.end() ; dit = t.next()) -// { -// Dart temp = dit; -// do -// { -// if(isBoundaryMarked3(d)) -// std::cout << "d boundary " << std::endl; -// -// temp = alpha2(temp); -// }while(temp != dit); -// } -// -// if(isBoundaryMarked3(d)) -// std::cout << "d boundary " << std::endl; -// -// if(isBoundaryMarked3(phi1(d))) -// std::cout << "phi1(d) boundary " << std::endl; -// -// if(isBoundaryMarked3(phi_1(d))) -// std::cout << "phi_1(d) boundary " << std::endl; -// -// if(isBoundaryMarked3(phi2(d))) -// std::cout << "phi2(d) boundary " << std::endl; -// -// if(isBoundaryMarked3(phi3(d))) -// std::cout << "phi3(d) boundary " << std::endl; -// -// if(isBoundaryMarked3(phi2(phi3(d)))) -// std::cout << "phi2(phi3(d)) boundary " << std::endl; -// -// if(isBoundaryMarked3(phi3(phi2(d)))) -// std::cout << "phi3(phi2(d)) boundary " << std::endl; -// -// if(isBoundaryMarked3(phi1(phi3(d)))) -// std::cout << "phi1(phi3(d)) boundary " << std::endl; -// -// if(isBoundaryMarked3(phi3(phi1(d)))) -// std::cout << "phi3(phi1(d)) boundary " << std::endl; -// } -// -// if(isBoundaryMarked3(d)) -// { -// -// if(isBoundaryMarked3(d)) -// std::cout << "d = " << d << std::endl; -// -// if(isBoundaryMarked3(phi3(d))) -// std::cout << "phi3(d) = " << phi3(d) << std::endl; -// -// if(isBoundaryMarked3(phi2(d))) -// std::cout << "phi2(d) = " << phi2(d) << std::endl; -// -// Dart dit = deleteVertex(phi3(d)); -// -// if(dit == NIL) -// std::cout << "NILLLLLLLLLLLLLLL" << std::endl; -// -// ++count; -// -// if(count == 5) -// return; -// } -// } - - -// TraversorW tW(*this); -// for(Dart d = tW.begin(); d != tW.end(); d = tW.next()) -// { -// if(isBoundaryMarked3(d)) -// { -// boundaryMarkOrbit(d); -// } -// } - -// unsigned int count = 0; -// for(Dart d = begin(); d != end(); next(d)) -// { -// if(isBoundaryMarked3(d)) -// { -// ++count; -// } -// } -// std::cout << "nb boundar marked = " << count << std::endl; -// -// count = 0; -// for(Dart d = begin(); d != end(); next(d)) -// { -// if(isBoundaryMarked3(d)) -// { -// ++count; -// std::cout << count << std::endl; -// //Map3::deleteVolume(d,false); -// //deleteVolume(d,false); -// } -// } - - - //std::cout << "Map closed (" << closeMap() <<" boundary faces)" << std::endl; -} - -Dart Map3::explodBorderTopo(Dart d) -{ - std::vector > ve; - ve.reserve(1024); - - //stocke un brin par face du bord - DartMarker me(*this); - for(Dart dit = begin() ; dit != end() ; next(dit)) - { - if(isBoundaryMarked3(dit) && !me.isMarked(dit)) - { - ve.push_back(std::make_pair(dit,phi2(dit))); - me.markOrbit(dit); - } - } - - //decoud chaque face - for(std::vector >::iterator it = ve.begin() ; it != ve.end() ; ++it) - { - Map2::unsewFaces((*it).first,false); - } - - //triangule chaque face - DartMarker mf(*this); - for(std::vector >::iterator it = ve.begin() ; it != ve.end() ; ++it) - { - Dart first = (*it).first; - Dart second = (*it).second; - - if(!mf.isMarked(first)) - { - unsigned int degf = Map2::faceDegree(first); - - Dart dnf = Map2::newFace(degf,false); - Dart dit = first; - do - { - Map2::sewFaces(dit,dnf,false); - copyDartEmbedding(dnf, phi1(dit)) ; - dit = phi1(dit); - dnf = phi_1(dnf); - }while(dit != first); - - mf.markOrbit(first); - - Dart db = dnf; - Dart d1 = phi1(db); - Map2::splitFace(db, d1) ; - Map2::cutEdge(phi_1(db)) ; - - Dart x = phi2(phi_1(db)) ; - Dart dd = phi1(phi1(phi1(x))); - while(dd != x) - { - Dart next = phi1(dd) ; - Map2::splitFace(dd, phi1(x)) ; - dd = next ; - } - - Dart cd = phi_1(db); - do - { - setDartEmbedding(phi2(cd), getEmbedding(phi1(cd))) ; - cd = phi2(phi_1(cd)); - }while(cd != phi_1(db)); - - } - - if(!mf.isMarked(second)) - { - mf.markOrbit(second); - unsigned int degf = Map2::faceDegree(second); - - Dart dnf = Map2::newFace(degf,false); - Dart dit = second; - do - { - Map2::sewFaces(dit,dnf,false); - copyDartEmbedding(dnf, phi1(dit)) ; - dit = phi1(dit); - dnf = phi_1(dnf); - }while(dit != second); - - mf.markOrbit(second); - - Dart db = dnf; - Dart d1 = phi1(db); - Map2::splitFace(db, d1) ; - Map2::cutEdge(phi_1(db)) ; - - Dart x = phi2(phi_1(db)) ; - Dart dd = phi1(phi1(phi1(x))); - while(dd != x) - { - Dart next = phi1(dd) ; - Map2::splitFace(dd, phi1(x)) ; - dd = next ; - } - - Dart cd = phi_1(db); - do - { - setDartEmbedding(phi2(cd), getEmbedding(phi1(cd))) ; - cd = phi2(phi_1(cd)); - }while(cd != phi_1(db)); - } - - } - - //close de chaque nouveau volume - for(std::vector >::iterator it = ve.begin() ; it != ve.end() ; ++it) - { - Dart dit1 = phi2((*it).first); - Dart dit2 = phi2((*it).second); - Map3::sewVolumes(dit1, dit2, false); - } - - setOrbitEmbeddingOnNewCell(phi_1(phi2(ve.front().first))); - - return phi_1(phi2(ve.front().first)); -} - -void Map3::computeDualTest() -{ -// unsigned int count = 0; -// CellMarkerNoUnmark cv(*this); -// std::vector v; -// for(Dart d = begin(); d != end(); next(d)) -// { -// if(!cv.isMarked(d) && isBoundaryMarked3(d)) -// { -// ++count; -// v.push_back(d); -// cv.mark(d); -// } -// } -// -// cv.unmarkAll(); - -// std::cout << "boundary vertices : " << count << std::endl; - - DartAttribute old_phi1 = getAttribute("phi1") ; - DartAttribute old_phi_1 = getAttribute("phi_1") ; - DartAttribute new_phi1 = addAttribute("new_phi1") ; - DartAttribute new_phi_1 = addAttribute("new_phi_1") ; - - DartAttribute old_phi2 = getAttribute("phi2") ; - DartAttribute new_phi2 = addAttribute("new_phi2") ; - - for(Dart d = begin(); d != end(); next(d)) - { - Dart dd = phi2(phi3(d)) ; - new_phi1[d] = dd ; - new_phi_1[dd] = d ; - - Dart ddd = phi1(phi3(d)); - new_phi2[d] = ddd; - new_phi2[ddd] = d; - } - - swapAttributes(old_phi1, new_phi1) ; - swapAttributes(old_phi_1, new_phi_1) ; - swapAttributes(old_phi2, new_phi2) ; - - removeAttribute(new_phi1) ; - removeAttribute(new_phi_1) ; - removeAttribute(new_phi2) ; - - swapEmbeddingContainers(VERTEX, VOLUME) ; - - for(Dart d = begin(); d != end(); next(d)) - { - if(isBoundaryMarked3(d)) - { - Map3::deleteVolume(d,false); - } - } - - closeMap(); - -// reverseOrientation(); -// -// for(std::vector::iterator it = v.begin() ; it != v.end() ; ++it) -// { -// boundaryUnmarkOrbit(*it); -// } -// -// for(std::vector::iterator it = v.begin() ; it != v.end() ; ++it) -// { -// Map3::deleteVolume(*it); -// } -// -// std::cout << "boundary faces : " << closeMap() << std::endl; - -// //boundary management -// for(Dart d = begin(); d != end(); next(d)) -// { -// if(isBoundaryMarked3(d)) -// { -// //Dart dit = deleteVertex(phi3(d)); -// //deleteVolume(phi3(d)); -// //if(dit == NIL) -// //{ -// // std::cout << "ploooooooooooooooooooop" << std::endl; -// // return; -// //} -// //else -// //{ -// // std::cout << "gooooooooooooooooooooood" << std::endl; -// // boundaryMarkOrbit(dit); -// // return; -// //} -// //boundaryUnmarkOrbit(d); -// //deleteVolume(d); -// } -// } - -} - -} // namespace CGoGN -- GitLab