57 #ifndef OPENMESH_ARRAY_KERNEL_HH 58 #define OPENMESH_ARRAY_KERNEL_HH 64 #include <OpenMesh/Core/System/config.h> 65 #include <OpenMesh/Core/Utils/GenProg.hh> 67 #include <OpenMesh/Core/Mesh/ArrayItems.hh> 68 #include <OpenMesh/Core/Mesh/BaseKernel.hh> 69 #include <OpenMesh/Core/Mesh/Status.hh> 119 void assign_connectivity(
const ArrayKernel& _other);
122 VertexHandle handle(
const Vertex& _v)
const;
124 HalfedgeHandle handle(
const Halfedge& _he)
const;
126 EdgeHandle handle(
const Edge& _e)
const;
128 FaceHandle handle(
const Face& _f)
const;
132 bool is_valid_handle(VertexHandle _vh)
const;
135 bool is_valid_handle(HalfedgeHandle _heh)
const;
138 bool is_valid_handle(EdgeHandle _eh)
const;
141 bool is_valid_handle(FaceHandle _fh)
const;
145 const Vertex& vertex(VertexHandle _vh)
const 147 assert(is_valid_handle(_vh));
148 return vertices_[_vh.
idx()];
151 Vertex& vertex(VertexHandle _vh)
153 assert(is_valid_handle(_vh));
154 return vertices_[_vh.
idx()];
157 const Halfedge& halfedge(HalfedgeHandle _heh)
const 159 assert(is_valid_handle(_heh));
160 return edges_[_heh.
idx() >> 1].halfedges_[_heh.
idx() & 1];
163 Halfedge& halfedge(HalfedgeHandle _heh)
165 assert(is_valid_handle(_heh));
166 return edges_[_heh.
idx() >> 1].halfedges_[_heh.
idx() & 1];
169 const Edge& edge(EdgeHandle _eh)
const 171 assert(is_valid_handle(_eh));
172 return edges_[_eh.
idx()];
175 Edge& edge(EdgeHandle _eh)
177 assert(is_valid_handle(_eh));
178 return edges_[_eh.
idx()];
181 const Face& face(FaceHandle _fh)
const 183 assert(is_valid_handle(_fh));
184 return faces_[_fh.
idx()];
187 Face& face(FaceHandle _fh)
189 assert(is_valid_handle(_fh));
190 return faces_[_fh.
idx()];
195 VertexHandle vertex_handle(
unsigned int _i)
const 196 {
return (_i < n_vertices()) ? handle( vertices_[_i] ) : VertexHandle(); }
198 HalfedgeHandle halfedge_handle(
unsigned int _i)
const 200 return (_i < n_halfedges()) ?
201 halfedge_handle(edge_handle(_i/2), _i%2) : HalfedgeHandle();
204 EdgeHandle edge_handle(
unsigned int _i)
const 205 {
return (_i < n_edges()) ? handle(edges_[_i]) : EdgeHandle(); }
207 FaceHandle face_handle(
unsigned int _i)
const 208 {
return (_i < n_faces()) ? handle(faces_[_i]) : FaceHandle(); }
223 vertices_.push_back(Vertex());
224 vprops_resize(n_vertices());
226 return handle(vertices_.back());
241 vertices_.push_back(Vertex());
242 vprops_resize_if_smaller(n_vertices());
244 return handle(vertices_.back());
247 inline HalfedgeHandle new_edge(VertexHandle _start_vh, VertexHandle _end_vh)
250 edges_.push_back(Edge());
251 eprops_resize(n_edges());
252 hprops_resize(n_halfedges());
254 EdgeHandle eh(handle(edges_.back()));
255 HalfedgeHandle heh0(halfedge_handle(eh, 0));
256 HalfedgeHandle heh1(halfedge_handle(eh, 1));
257 set_vertex_handle(heh0, _end_vh);
258 set_vertex_handle(heh1, _start_vh);
262 inline FaceHandle new_face()
264 faces_.push_back(Face());
265 fprops_resize(n_faces());
266 return handle(faces_.back());
269 inline FaceHandle new_face(
const Face& _f)
271 faces_.push_back(_f);
272 fprops_resize(n_faces());
273 return handle(faces_.back());
278 void resize(
size_t _n_vertices,
size_t _n_edges,
size_t _n_faces );
279 void reserve(
size_t _n_vertices,
size_t _n_edges,
size_t _n_faces );
297 void garbage_collection(
bool _v=
true,
bool _e=
true,
bool _f=
true);
316 template<
typename std_API_Container_VHandlePointer,
317 typename std_API_Container_HHandlePointer,
318 typename std_API_Container_FHandlePointer>
319 void garbage_collection(std_API_Container_VHandlePointer& vh_to_update,
320 std_API_Container_HHandlePointer& hh_to_update,
321 std_API_Container_FHandlePointer& fh_to_update,
322 bool _v=
true,
bool _e=
true,
bool _f=
true);
345 void clean_keep_reservation();
348 size_t n_vertices()
const {
return vertices_.size(); }
349 size_t n_halfedges()
const {
return 2*edges_.size(); }
350 size_t n_edges()
const {
return edges_.size(); }
351 size_t n_faces()
const {
return faces_.size(); }
353 bool vertices_empty()
const {
return vertices_.empty(); }
354 bool halfedges_empty()
const {
return edges_.empty(); }
355 bool edges_empty()
const {
return edges_.empty(); }
356 bool faces_empty()
const {
return faces_.empty(); }
360 HalfedgeHandle halfedge_handle(VertexHandle _vh)
const 361 {
return vertex(_vh).halfedge_handle_; }
363 void set_halfedge_handle(VertexHandle _vh, HalfedgeHandle _heh)
366 vertex(_vh).halfedge_handle_ = _heh;
369 bool is_isolated(VertexHandle _vh)
const 370 {
return !halfedge_handle(_vh).
is_valid(); }
372 void set_isolated(VertexHandle _vh)
373 { vertex(_vh).halfedge_handle_.invalidate(); }
375 unsigned int delete_isolated_vertices();
378 VertexHandle to_vertex_handle(HalfedgeHandle _heh)
const 379 {
return halfedge(_heh).vertex_handle_; }
381 VertexHandle from_vertex_handle(HalfedgeHandle _heh)
const 382 {
return to_vertex_handle(opposite_halfedge_handle(_heh)); }
384 void set_vertex_handle(HalfedgeHandle _heh, VertexHandle _vh)
387 halfedge(_heh).vertex_handle_ = _vh;
390 FaceHandle face_handle(HalfedgeHandle _heh)
const 391 {
return halfedge(_heh).face_handle_; }
393 void set_face_handle(HalfedgeHandle _heh, FaceHandle _fh)
396 halfedge(_heh).face_handle_ = _fh;
399 void set_boundary(HalfedgeHandle _heh)
404 {
return !face_handle(_heh).is_valid(); }
406 HalfedgeHandle next_halfedge_handle(HalfedgeHandle _heh)
const 407 {
return halfedge(_heh).next_halfedge_handle_; }
409 void set_next_halfedge_handle(HalfedgeHandle _heh, HalfedgeHandle _nheh)
411 assert(is_valid_handle(_nheh));
413 halfedge(_heh).next_halfedge_handle_ = _nheh;
414 set_prev_halfedge_handle(_nheh, _heh);
418 void set_prev_halfedge_handle(HalfedgeHandle _heh, HalfedgeHandle _pheh)
420 assert(is_valid_handle(_pheh));
421 set_prev_halfedge_handle(_heh, _pheh, HasPrevHalfedge());
424 void set_prev_halfedge_handle(HalfedgeHandle _heh, HalfedgeHandle _pheh,
426 { halfedge(_heh).prev_halfedge_handle_ = _pheh; }
428 void set_prev_halfedge_handle(HalfedgeHandle , HalfedgeHandle ,
432 HalfedgeHandle prev_halfedge_handle(HalfedgeHandle _heh)
const 433 {
return prev_halfedge_handle(_heh, HasPrevHalfedge() ); }
435 HalfedgeHandle prev_halfedge_handle(HalfedgeHandle _heh, GenProg::TrueType)
const 436 {
return halfedge(_heh).prev_halfedge_handle_; }
438 HalfedgeHandle prev_halfedge_handle(HalfedgeHandle _heh, GenProg::FalseType)
const 440 if (is_boundary(_heh))
442 HalfedgeHandle curr_heh(opposite_halfedge_handle(_heh));
443 HalfedgeHandle next_heh(next_halfedge_handle(curr_heh));
446 curr_heh = opposite_halfedge_handle(next_heh);
447 next_heh = next_halfedge_handle(curr_heh);
449 while (next_heh != _heh);
454 HalfedgeHandle heh(_heh);
455 HalfedgeHandle next_heh(next_halfedge_handle(heh));
456 while (next_heh != _heh) {
458 next_heh = next_halfedge_handle(next_heh);
465 HalfedgeHandle opposite_halfedge_handle(HalfedgeHandle _heh)
const 466 {
return HalfedgeHandle(_heh.
idx() ^ 1); }
469 HalfedgeHandle ccw_rotated_halfedge_handle(HalfedgeHandle _heh)
const 470 {
return opposite_halfedge_handle(prev_halfedge_handle(_heh)); }
473 HalfedgeHandle cw_rotated_halfedge_handle(HalfedgeHandle _heh)
const 474 {
return next_halfedge_handle(opposite_halfedge_handle(_heh)); }
477 static HalfedgeHandle s_halfedge_handle(EdgeHandle _eh,
unsigned int _i)
480 return HalfedgeHandle((_eh.
idx() << 1) + _i);
483 static EdgeHandle s_edge_handle(HalfedgeHandle _heh)
484 {
return EdgeHandle(_heh.
idx() >> 1); }
486 HalfedgeHandle halfedge_handle(EdgeHandle _eh,
unsigned int _i)
const 488 return s_halfedge_handle(_eh, _i);
491 EdgeHandle edge_handle(HalfedgeHandle _heh)
const 492 {
return s_edge_handle(_heh); }
495 HalfedgeHandle halfedge_handle(FaceHandle _fh)
const 496 {
return face(_fh).halfedge_handle_; }
498 void set_halfedge_handle(FaceHandle _fh, HalfedgeHandle _heh)
501 face(_fh).halfedge_handle_ = _heh;
506 const StatusInfo&
status(VertexHandle _vh)
const 507 {
return property(vertex_status_, _vh); }
509 StatusInfo& status(VertexHandle _vh)
510 {
return property(vertex_status_, _vh); }
518 PropertyT<StatusInfo>::vector_type &sprop_v = status_prop.
data_vector();
519 std::fill(sprop_v.begin(), sprop_v.begin() + n_vertices(), StatusInfo());
523 const StatusInfo& status(HalfedgeHandle _hh)
const 524 {
return property(halfedge_status_, _hh); }
526 StatusInfo& status(HalfedgeHandle _hh)
527 {
return property(halfedge_status_, _hh); }
530 const StatusInfo& status(EdgeHandle _eh)
const 531 {
return property(edge_status_, _eh); }
533 StatusInfo& status(EdgeHandle _eh)
534 {
return property(edge_status_, _eh); }
537 const StatusInfo& status(FaceHandle _fh)
const 538 {
return property(face_status_, _fh); }
540 StatusInfo& status(FaceHandle _fh)
541 {
return property(face_status_, _fh); }
543 inline bool has_vertex_status()
const 544 {
return vertex_status_.is_valid(); }
546 inline bool has_halfedge_status()
const 547 {
return halfedge_status_.is_valid(); }
549 inline bool has_edge_status()
const 550 {
return edge_status_.is_valid(); }
552 inline bool has_face_status()
const 553 {
return face_status_.is_valid(); }
555 inline VertexStatusPropertyHandle vertex_status_pph()
const 556 {
return vertex_status_; }
558 inline HalfedgeStatusPropertyHandle halfedge_status_pph()
const 559 {
return halfedge_status_; }
561 inline EdgeStatusPropertyHandle edge_status_pph()
const 562 {
return edge_status_; }
564 inline FaceStatusPropertyHandle face_status_pph()
const 565 {
return face_status_; }
568 inline VertexStatusPropertyHandle
status_pph(VertexHandle )
const 569 {
return vertex_status_pph(); }
571 inline HalfedgeStatusPropertyHandle status_pph(HalfedgeHandle )
const 572 {
return halfedge_status_pph(); }
574 inline EdgeStatusPropertyHandle status_pph(EdgeHandle )
const 575 {
return edge_status_pph(); }
577 inline FaceStatusPropertyHandle status_pph(FaceHandle )
const 578 {
return face_status_pph(); }
583 if (!refcount_vstatus_++)
584 add_property( vertex_status_,
"v:status" );
587 void request_halfedge_status()
589 if (!refcount_hstatus_++)
590 add_property( halfedge_status_,
"h:status" );
593 void request_edge_status()
595 if (!refcount_estatus_++)
596 add_property( edge_status_,
"e:status" );
599 void request_face_status()
601 if (!refcount_fstatus_++)
602 add_property( face_status_,
"f:status" );
608 if ((refcount_vstatus_ > 0) && (! --refcount_vstatus_))
609 remove_property(vertex_status_);
612 void release_halfedge_status()
614 if ((refcount_hstatus_ > 0) && (! --refcount_hstatus_))
615 remove_property(halfedge_status_);
618 void release_edge_status()
620 if ((refcount_estatus_ > 0) && (! --refcount_estatus_))
621 remove_property(edge_status_);
624 void release_face_status()
626 if ((refcount_fstatus_ > 0) && (! --refcount_fstatus_))
627 remove_property(face_status_);
639 template <
class HandleT>
643 typedef HandleT Handle;
649 const unsigned int bit_mask_;
653 : kernel_(_kernel), bit_mask_(_bit_mask)
659 inline bool is_in(Handle _hnd)
const 662 inline void insert(Handle _hnd)
665 inline void erase(Handle _hnd)
675 for (
int i = 0; i < n; ++i)
676 sz += (
size_t)is_in(Handle(i));
686 for (
int i = 0; i < n; ++i)
697 template <
class HandleT>
701 typedef HandleT Handle;
712 Base::kernel_.push_bit_mask(Handle(), Base::bit_mask_);
727 template <
class HandleT>
731 typedef HandleT Handle;
735 typedef std::vector<Handle> HandleContainer;
736 HandleContainer handles_;
739 typedef typename HandleContainer::iterator
741 typedef typename HandleContainer::const_iterator
746 { handles_.reserve(_capacity_hint); }
752 inline void insert(Handle _hnd)
757 handles_.push_back(_hnd);
766 iterator it = std::find(begin(), end(), _hnd);
774 assert(_it != end() && is_in(*_it));
776 *_it = handles_.back();
782 for (iterator it = begin(); it != end(); ++it)
791 inline unsigned int size()
const 792 {
return handles_.size(); }
793 inline bool empty()
const 794 {
return handles_.empty(); }
797 inline iterator begin()
798 {
return handles_.begin(); }
799 inline const_iterator begin()
const 800 {
return handles_.begin(); }
802 inline iterator end()
803 {
return handles_.end(); }
804 inline const_iterator end()
const 805 {
return handles_.end(); }
807 inline Handle& front()
808 {
return handles_.front(); }
809 inline const Handle& front()
const 810 {
return handles_.front(); }
812 inline Handle& back()
813 {
return handles_.back(); }
814 inline const Handle& back()
const 815 {
return handles_.back(); }
825 typedef std::vector<Vertex> VertexContainer;
826 typedef std::vector<Edge> EdgeContainer;
827 typedef std::vector<Face> FaceContainer;
828 typedef VertexContainer::iterator KernelVertexIter;
829 typedef VertexContainer::const_iterator KernelConstVertexIter;
830 typedef EdgeContainer::iterator KernelEdgeIter;
831 typedef EdgeContainer::const_iterator KernelConstEdgeIter;
832 typedef FaceContainer::iterator KernelFaceIter;
833 typedef FaceContainer::const_iterator KernelConstFaceIter;
834 typedef std::vector<unsigned int> BitMaskContainer;
837 KernelVertexIter vertices_begin() {
return vertices_.begin(); }
838 KernelConstVertexIter vertices_begin()
const {
return vertices_.begin(); }
839 KernelVertexIter vertices_end() {
return vertices_.end(); }
840 KernelConstVertexIter vertices_end()
const {
return vertices_.end(); }
842 KernelEdgeIter edges_begin() {
return edges_.begin(); }
843 KernelConstEdgeIter edges_begin()
const {
return edges_.begin(); }
844 KernelEdgeIter edges_end() {
return edges_.end(); }
845 KernelConstEdgeIter edges_end()
const {
return edges_.end(); }
847 KernelFaceIter faces_begin() {
return faces_.begin(); }
848 KernelConstFaceIter faces_begin()
const {
return faces_.begin(); }
849 KernelFaceIter faces_end() {
return faces_.end(); }
850 KernelConstFaceIter faces_end()
const {
return faces_.end(); }
853 inline BitMaskContainer& bit_masks(VertexHandle )
854 {
return vertex_bit_masks_; }
855 inline BitMaskContainer& bit_masks(EdgeHandle )
856 {
return edge_bit_masks_; }
857 inline BitMaskContainer& bit_masks(FaceHandle )
858 {
return face_bit_masks_; }
859 inline BitMaskContainer& bit_masks(HalfedgeHandle )
860 {
return halfedge_bit_masks_; }
862 template <
class Handle>
863 unsigned int pop_bit_mask(Handle _hnd)
865 assert(!bit_masks(_hnd).empty());
866 unsigned int bit_mask = bit_masks(_hnd).back();
867 bit_masks(_hnd).pop_back();
871 template <
class Handle>
872 void push_bit_mask(Handle _hnd,
unsigned int _bit_mask)
874 assert(std::find(bit_masks(_hnd).begin(), bit_masks(_hnd).end(), _bit_mask) ==
875 bit_masks(_hnd).end());
876 bit_masks(_hnd).push_back(_bit_mask);
879 void init_bit_masks(BitMaskContainer& _bmc);
880 void init_bit_masks();
883 VertexContainer vertices_;
884 EdgeContainer edges_;
885 FaceContainer faces_;
887 VertexStatusPropertyHandle vertex_status_;
888 HalfedgeStatusPropertyHandle halfedge_status_;
889 EdgeStatusPropertyHandle edge_status_;
890 FaceStatusPropertyHandle face_status_;
892 unsigned int refcount_vstatus_;
893 unsigned int refcount_hstatus_;
894 unsigned int refcount_estatus_;
895 unsigned int refcount_fstatus_;
897 BitMaskContainer halfedge_bit_masks_;
898 BitMaskContainer edge_bit_masks_;
899 BitMaskContainer vertex_bit_masks_;
900 BitMaskContainer face_bit_masks_;
907 #if defined(OM_INCLUDE_TEMPLATES) && !defined(OPENMESH_ARRAY_KERNEL_C) 908 # define OPENMESH_ARRAY_KERNEL_TEMPLATES 909 # include "ArrayKernelT.cc" 912 #endif // OPENMESH_ARRAY_KERNEL_HH defined VertexHandle new_vertex()
Add a new vertex.
Definition: ArrayKernel.hh:221
void clear()
Note: O(n) complexity.
Definition: ArrayKernel.hh:681
void erase(Handle _hnd)
Complexity: O(k), (k - number of the elements in the set)
Definition: ArrayKernel.hh:762
— StatusSet API —
Definition: ArrayKernel.hh:640
ExtStatusSet: A status set augmented with an array.
Definition: ArrayKernel.hh:728
void request_vertex_status()
Status Request API.
Definition: ArrayKernel.hh:581
Default property class for any type T.
Definition: Property.hh:94
Handle for a vertex entity.
Definition: Handles.hh:125
bool is_valid() const
The handle is valid iff the index is not equal to -1.
Definition: Handles.hh:77
bool is_boundary(HalfedgeHandle _heh) const
Is halfedge _heh a boundary halfedge (is its face handle invalid) ?
Definition: ArrayKernel.hh:403
This class provides low-level property management like adding/removing properties and access to prope...
Definition: BaseKernel.hh:102
Add status information to a base class.
Definition: Status.hh:99
void release_vertex_status()
Status Release API.
Definition: ArrayKernel.hh:606
void reset_status()
Reinitializes the status of all vertices using the StatusInfo default constructor, i.e.
Definition: ArrayKernel.hh:516
PropertyT< T > & property(VPropHandleT< T > _ph)
In most cases you should use the convenient PropertyManager wrapper and use of this function should n...
Definition: BaseKernel.hh:315
int idx() const
Get the underlying index of this handle.
Definition: Handles.hh:74
void erase(iterator _it)
Complexity: O(1)
Definition: ArrayKernel.hh:772
Mesh kernel using arrays for mesh item storage.
Definition: ArrayKernel.hh:92
size_t size() const
Note: 0(n) complexity.
Definition: ArrayKernel.hh:669
unsigned int size() const
Complexity: 0(1)
Definition: ArrayKernel.hh:791
bool is_bit_set(unsigned int _s) const
is a certain bit set ?
Definition: Status.hh:162
AutoStatusSetT: A status set that automatically picks a status bit.
Definition: ArrayKernel.hh:698
const StatusInfo & status(VertexHandle _vh) const
Status Query API.
Definition: ArrayKernel.hh:506
void set_bit(unsigned int _s)
set a certain bit
Definition: Status.hh:164
Handle for a face entity.
Definition: Handles.hh:146
void unset_bit(unsigned int _s)
unset a certain bit
Definition: Status.hh:166
VertexStatusPropertyHandle status_pph(VertexHandle) const
status property by handle
Definition: ArrayKernel.hh:568
Handle for a edge entity.
Definition: Handles.hh:139
Contains all the mesh ingredients like the polygonal mesh, the triangle mesh, different mesh kernels ...
Definition: MeshItems.hh:64
Handle for a halfedge entity.
Definition: Handles.hh:132
VertexHandle new_vertex_dirty()
Same as new_vertex() but uses PropertyContainer::resize_if_smaller() to resize the vertex property co...
Definition: ArrayKernel.hh:239
vector_type & data_vector()
Get reference to property vector (be careful, improper usage, e.g. resizing, may crash OpenMesh!!!) ...
Definition: Property.hh:183
void invalidate()
reset handle to be invalid
Definition: Handles.hh:82