| OpenMesh

- Main Page
- Related Pages
- Modules
- Namespaces
- Classes
- Files

- File List
- File Members

All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
PropertyManager.hh
1 /* ========================================================================= *
2 * *
3 * OpenMesh *
4 * Copyright (c) 2001-2015, RWTH-Aachen University *
5 * Department of Computer Graphics and Multimedia *
6 * All rights reserved. *
7 * www.openmesh.org *
8 * *
9 *---------------------------------------------------------------------------*
10 * This file is part of OpenMesh. *
11 *---------------------------------------------------------------------------*
12 * *
13 * Redistribution and use in source and binary forms, with or without *
14 * modification, are permitted provided that the following conditions *
15 * are met: *
16 * *
17 * 1. Redistributions of source code must retain the above copyright notice, *
18 * this list of conditions and the following disclaimer. *
19 * *
20 * 2. Redistributions in binary form must reproduce the above copyright *
21 * notice, this list of conditions and the following disclaimer in the *
22 * documentation and/or other materials provided with the distribution. *
23 * *
24 * 3. Neither the name of the copyright holder nor the names of its *
25 * contributors may be used to endorse or promote products derived from *
26 * this software without specific prior written permission. *
27 * *
28 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS *
29 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED *
30 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A *
31 * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER *
32 * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, *
33 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, *
34 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR *
35 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF *
36 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING *
37 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS *
38 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. *
39 * *
40 * ========================================================================= */
41
42 /*===========================================================================*\
43 * *
44 * $Revision$ *
45 * $Date$ *
46 * *
47 \*===========================================================================*/
48
49 #ifndef PROPERTYMANAGER_HH_
50 #define PROPERTYMANAGER_HH_
51
52 #include <sstream>
53 #include <stdexcept>
54 #include <string>
55
56 namespace OpenMesh {
57
93 template<typename PROPTYPE, typename MeshT>
94 class PropertyManager {
95 #if _MSC_VER >= 1900 || __cplusplus > 199711L || defined(__GXX_EXPERIMENTAL_CXX0X__)
96 public:
97 PropertyManager(const PropertyManager&) = delete;
98 PropertyManager& operator=(const PropertyManager&) = delete;
99 #else
100 private:
104 PropertyManager(const PropertyManager&);
105
109 PropertyManager& operator=(const PropertyManager&);
110 #endif
111
112 public:
130 PropertyManager(MeshT &mesh, const char *propname, bool existing = false) : mesh_(&mesh), retain_(existing), name_(propname) {
131 if (existing) {
132 if (!mesh_->get_property_handle(prop_, propname)) {
133 std::ostringstream oss;
134 oss << "Requested property handle \"" << propname << "\" does not exist.";
135 throw std::runtime_error(oss.str());
136 }
137 } else {
138 mesh_->add_property(prop_, propname);
139 }
140 }
141
142 PropertyManager() : mesh_(0), retain_(false) {
143 }
144
145 ~PropertyManager() {
146 deleteProperty();
147 }
148
149 void swap(PropertyManager &rhs) {
150 std::swap(mesh_, rhs.mesh_);
151 std::swap(prop_, rhs.prop_);
152 std::swap(retain_, rhs.retain_);
153 std::swap(name_, rhs.name_);
154 }
155
156 static bool propertyExists(MeshT &mesh, const char *propname) {
157 PROPTYPE dummy;
158 return mesh.get_property_handle(dummy, propname);
159 }
160
161 bool isValid() const { return mesh_ != 0; }
162 operator bool() const { return isValid(); }
163
164 const PROPTYPE &getRawProperty() const { return prop_; }
165
166 const std::string &getName() const { return name_; }
167
168 MeshT &getMesh() const { return *mesh_; }
169
170 #if _MSC_VER >= 1900 || __cplusplus > 199711L || defined(__GXX_EXPERIMENTAL_CXX0X__)
171
173 typedef PropertyManager<PROPTYPE, MeshT> Proxy;
174
178 PropertyManager(PropertyManager &&rhs) : mesh_(rhs.mesh_), prop_(rhs.prop_), retain_(rhs.retain_), name_(rhs.name_) {
179 rhs.retain_ = true;
180 }
181
185 PropertyManager &operator=(PropertyManager &&rhs) {
186 if (&rhs != this) {
187 deleteProperty();
188 mesh_ = rhs.mesh_;
189 prop_ = rhs.prop_;
190 retain_ = rhs.retain_;
191 name_ = rhs.name_;
192 rhs.retain_ = true;
193 }
194 return *this;
195 }
196
204 static PropertyManager createIfNotExists(MeshT &mesh, const char *propname) {
205 PROPTYPE dummy_prop;
206 PropertyManager pm(mesh, propname, mesh.get_property_handle(dummy_prop, propname));
207 pm.retain();
208 return std::move(pm);
209 }
210
211
212 PropertyManager duplicate(const char *clone_name) {
213 PropertyManager pm(*mesh_, clone_name, false);
214 pm.mesh_->property(pm.prop_) = mesh_->property(prop_);
215 return pm;
216 }
217
221 PropertyManager move() {
222 return std::move(*this);
223 }
224
225 #else
226 class Proxy {
227 private:
228 Proxy(MeshT *mesh_, PROPTYPE prop_, bool retain_, const std::string &name_) :
229 mesh_(mesh_), prop_(prop_), retain_(retain_), name_(name_) {}
230 MeshT *mesh_;
231 PROPTYPE prop_;
232 bool retain_;
233 std::string name_;
234
235 friend class PropertyManager;
236 };
237
238 operator Proxy() {
239 Proxy p(mesh_, prop_, retain_, name_);
240 mesh_ = 0;
241 retain_ = true;
242 return p;
243 }
244
245 Proxy move() {
246 return (Proxy)*this;
247 }
248
249 PropertyManager(Proxy p) : mesh_(p.mesh_), prop_(p.prop_), retain_(p.retain_), name_(p.name_) {}
250
251 PropertyManager &operator=(Proxy p) {
252 PropertyManager(p).swap(*this);
253 return *this;
254 }
255
263 static Proxy createIfNotExists(MeshT &mesh, const char *propname) {
264 PROPTYPE dummy_prop;
265 PropertyManager pm(mesh, propname, mesh.get_property_handle(dummy_prop, propname));
266 pm.retain();
267 return (Proxy)pm;
268 }
269
270 Proxy duplicate(const char *clone_name) {
271 PropertyManager pm(*mesh_, clone_name, false);
272 pm.mesh_->property(pm.prop_) = mesh_->property(prop_);
273 return (Proxy)pm;
274 }
275 #endif
276
283 inline void retain(bool doRetain = true) {
284 retain_ = doRetain;
285 }
286
290 inline PROPTYPE &operator* () {
291 return prop_;
292 }
293
297 inline const PROPTYPE &operator* () const {
298 return prop_;
299 }
300
308 template<typename HandleType>
309 inline typename PROPTYPE::reference operator[] (const HandleType &handle) {
310 return mesh_->property(prop_, handle);
311 }
312
320 template<typename HandleType>
321 inline typename PROPTYPE::const_reference operator[] (const HandleType &handle) const {
322 return mesh_->property(prop_, handle);
323 }
324
349 template<typename HandleTypeIterator, typename PROP_VALUE>
350 void set_range(HandleTypeIterator begin, HandleTypeIterator end,
351 const PROP_VALUE &value) {
352 for (; begin != end; ++begin)
353 (*this)[*begin] = value;
354 }
355
370 template<typename HandleTypeIterator, typename PROPTYPE_2,
371 typename MeshT_2, typename HandleTypeIterator_2>
372 void copy_to(HandleTypeIterator begin, HandleTypeIterator end,
373 PropertyManager<PROPTYPE_2, MeshT_2> &dst_propmanager,
374 HandleTypeIterator_2 dst_begin, HandleTypeIterator_2 dst_end) const {
375
376 for (; begin != end && dst_begin != dst_end; ++begin, ++dst_begin) {
377 dst_propmanager[*dst_begin] = (*this)[*begin];
378 }
379 }
380
381 template<typename RangeType, typename PROPTYPE_2,
382 typename MeshT_2, typename RangeType_2>
383 void copy_to(const RangeType &range,
384 PropertyManager<PROPTYPE_2, MeshT_2> &dst_propmanager,
385 const RangeType_2 &dst_range) const {
386 copy_to(range.begin(), range.end(), dst_propmanager,
387 dst_range.begin(), dst_range.end());
388 }
389
404 template<typename RangeType, typename MeshT_2, typename RangeType_2>
405 static void copy(const char *prop_name,
406 MeshT &src_mesh, const RangeType &src_range,
407 MeshT_2 &dst_mesh, const RangeType_2 &dst_range) {
408
409 typedef OpenMesh::PropertyManager<PROPTYPE, MeshT> DstPM;
410 DstPM dst(DstPM::createIfNotExists(dst_mesh, prop_name));
411
412 typedef OpenMesh::PropertyManager<PROPTYPE, MeshT_2> SrcPM;
413 SrcPM src(src_mesh, prop_name, true);
414
415 src.copy_to(src_range, dst, dst_range);
416 }
417
418 private:
419 void deleteProperty() {
420 if (!retain_)
421 mesh_->remove_property(prop_);
422 }
423
424 private:
425 MeshT *mesh_;
426 PROPTYPE prop_;
427 bool retain_;
428 std::string name_;
429 };
430
438 template<typename PROPTYPE, typename MeshT>
439 PropertyManager<PROPTYPE, MeshT> makePropertyManagerFromNew(MeshT &mesh, const char *propname) {
440 return PropertyManager<PROPTYPE, MeshT>(mesh, propname, false);
441 }
442
453 template<typename PROPTYPE, typename MeshT>
454 PropertyManager<PROPTYPE, MeshT> makePropertyManagerFromExisting(MeshT &mesh, const char *propname) {
455 return PropertyManager<PROPTYPE, MeshT>(mesh, propname, true);
456 }
457
464 template<typename PROPTYPE, typename MeshT>
465 PropertyManager<PROPTYPE, MeshT> makePropertyManagerFromExistingOrNew(MeshT &mesh, const char *propname) {
466 return PropertyManager<PROPTYPE, MeshT>::createIfNotExists(mesh, propname);
467 }
468
469 } /* namespace OpenMesh */
470 #endif /* PROPERTYMANAGER_HH_ */
OpenMesh::makePropertyManagerFromExisting
PropertyManager< PROPTYPE, MeshT > makePropertyManagerFromExisting(MeshT &mesh, const char *propname)
Creates a non-owning wrapper for an existing mesh property (no lifecycle management).
Definition: PropertyManager.hh:454
OpenMesh::PropertyManager::copy
static void copy(const char *prop_name, MeshT &src_mesh, const RangeType &src_range, MeshT_2 &dst_mesh, const RangeType_2 &dst_range)
Copy the values of a property from a source range to a target range.
Definition: PropertyManager.hh:405
OpenMesh::makePropertyManagerFromNew
PropertyManager< PROPTYPE, MeshT > makePropertyManagerFromNew(MeshT &mesh, const char *propname)
Creates a new property whose lifecycle is managed by the returned PropertyManager.
Definition: PropertyManager.hh:439
OpenMesh::PropertyManager::operator*
PROPTYPE & operator*()
Access the encapsulated property.
Definition: PropertyManager.hh:290
OpenMesh::PropertyManager::createIfNotExists
static Proxy createIfNotExists(MeshT &mesh, const char *propname)
Create a property manager for the supplied property and mesh.
Definition: PropertyManager.hh:263
OpenMesh::PropertyManager::operator[]
PROPTYPE::reference operator[](const HandleType &handle)
Enables convenient access to the encapsulated property.
Definition: PropertyManager.hh:309
OpenMesh::PropertyManager::set_range
void set_range(HandleTypeIterator begin, HandleTypeIterator end, const PROP_VALUE &value)
Conveniently set the property for an entire range of values.
Definition: PropertyManager.hh:350
OpenMesh::PropertyManager::PropertyManager
PropertyManager(MeshT &mesh, const char *propname, bool existing=false)
Constructor.
Definition: PropertyManager.hh:130
OpenMesh
Contains all the mesh ingredients like the polygonal mesh, the triangle mesh, different mesh kernels ...
Definition: MeshItems.hh:64
OpenMesh::PropertyManager
This class is intended to manage the lifecycle of properties.
Definition: PropertyManager.hh:94
OpenMesh::PropertyManager::copy_to
void copy_to(HandleTypeIterator begin, HandleTypeIterator end, PropertyManager< PROPTYPE_2, MeshT_2 > &dst_propmanager, HandleTypeIterator_2 dst_begin, HandleTypeIterator_2 dst_end) const
Conveniently transfer the values managed by one property manager onto the values managed by a differe...
Definition: PropertyManager.hh:372
OpenMesh::PropertyManager::retain
void retain(bool doRetain=true)
Disable lifecycle management for this property.
Definition: PropertyManager.hh:283
OpenMesh::makePropertyManagerFromExistingOrNew
PropertyManager< PROPTYPE, MeshT > makePropertyManagerFromExistingOrNew(MeshT &mesh, const char *propname)
Creates a non-owning wrapper for a mesh property (no lifecycle management).
Definition: PropertyManager.hh:465