OpenMesh
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Modules Pages
ModNormalDeviationT.hh
Go to the documentation of this file.
1 /*===========================================================================*\
2  * *
3  * OpenMesh *
4  * Copyright (C) 2001-2014 by Computer Graphics Group, RWTH Aachen *
5  * www.openmesh.org *
6  * *
7  *---------------------------------------------------------------------------*
8  * This file is part of OpenMesh. *
9  * *
10  * OpenMesh is free software: you can redistribute it and/or modify *
11  * it under the terms of the GNU Lesser General Public License as *
12  * published by the Free Software Foundation, either version 3 of *
13  * the License, or (at your option) any later version with the *
14  * following exceptions: *
15  * *
16  * If other files instantiate templates or use macros *
17  * or inline functions from this file, or you compile this file and *
18  * link it with other files to produce an executable, this file does *
19  * not by itself cause the resulting executable to be covered by the *
20  * GNU Lesser General Public License. This exception does not however *
21  * invalidate any other reasons why the executable file might be *
22  * covered by the GNU Lesser General Public License. *
23  * *
24  * OpenMesh is distributed in the hope that it will be useful, *
25  * but WITHOUT ANY WARRANTY; without even the implied warranty of *
26  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
27  * GNU Lesser General Public License for more details. *
28  * *
29  * You should have received a copy of the GNU LesserGeneral Public *
30  * License along with OpenMesh. If not, *
31  * see <http://www.gnu.org/licenses/>. *
32  * *
33 \*===========================================================================*/
34 
35 /*===========================================================================*\
36  * *
37  * $Revision: 1049 $ *
38  * $Date: 2014-05-09 10:12:17 +0200 (Fr, 09 Mai 2014) $ *
39  * *
40 \*===========================================================================*/
41 
45 //=============================================================================
46 //
47 // CLASS ModNormalDeviationT
48 //
49 //=============================================================================
50 
51 
52 #ifndef OPENMESH_DECIMATER_MODNORMALDEVIATIONT_HH
53 #define OPENMESH_DECIMATER_MODNORMALDEVIATIONT_HH
54 
55 
56 //== INCLUDES =================================================================
57 
59 #include <OpenMesh/Core/Utils/Property.hh>
60 #include <OpenMesh/Core/Geometry/NormalConeT.hh>
61 
62 
63 //== NAMESPACES ===============================================================
64 
65 namespace OpenMesh {
66 namespace Decimater {
67 
68 
69 //== CLASS DEFINITION =========================================================
70 
71 
86 template <class MeshT>
87 class ModNormalDeviationT : public ModBaseT< MeshT >
88 {
89 public:
90 
91  DECIMATING_MODULE( ModNormalDeviationT, MeshT, NormalDeviation );
92 
93  typedef typename Mesh::Scalar Scalar;
94  typedef typename Mesh::Point Point;
95  typedef typename Mesh::Normal Normal;
96  typedef typename Mesh::VertexHandle VertexHandle;
97  typedef typename Mesh::FaceHandle FaceHandle;
98  typedef typename Mesh::EdgeHandle EdgeHandle;
100 
101 
102 
103 public:
104 
106  ModNormalDeviationT(MeshT& _mesh, float _max_dev = 180.0)
107  : Base(_mesh, true), mesh_(Base::mesh())
108  {
109  set_normal_deviation(_max_dev);
110  mesh_.add_property(normal_cones_);
111 
112  const bool mesh_has_normals = _mesh.has_face_normals();
113  _mesh.request_face_normals();
114 
115  if (!mesh_has_normals)
116  {
117  std::cerr << "Mesh has no face normals. Compute them automatically." << std::endl;
118  _mesh.update_face_normals();
119  }
120  }
121 
122 
125  mesh_.remove_property(normal_cones_);
126  mesh_.release_face_normals();
127  }
128 
129 
131  Scalar normal_deviation() const {
132  return normal_deviation_ / M_PI * 180.0;
133  }
134 
136  void set_normal_deviation(Scalar _s) {
137  normal_deviation_ = _s / 180.0 * M_PI;
138  }
139 
140 
142  void initialize() {
143  if (!normal_cones_.is_valid())
144  mesh_.add_property(normal_cones_);
145 
146  typename Mesh::FaceIter f_it = mesh_.faces_begin(),
147  f_end = mesh_.faces_end();
148 
149  for (; f_it != f_end; ++f_it)
150  mesh_.property(normal_cones_, *f_it) = NormalCone(mesh_.normal(*f_it));
151  }
152 
167  float collapse_priority(const CollapseInfo& _ci) {
168  // simulate collapse
169  mesh_.set_point(_ci.v0, _ci.p1);
170 
171 
172  typename Mesh::Scalar max_angle(0.0);
173  typename Mesh::ConstVertexFaceIter vf_it(mesh_, _ci.v0);
174  typename Mesh::FaceHandle fh, fhl, fhr;
175 
176  if (_ci.v0vl.is_valid()) fhl = mesh_.face_handle(_ci.v0vl);
177  if (_ci.vrv0.is_valid()) fhr = mesh_.face_handle(_ci.vrv0);
178 
179  for (; vf_it.is_valid(); ++vf_it) {
180  fh = *vf_it;
181  if (fh != _ci.fl && fh != _ci.fr) {
182  NormalCone nc = mesh_.property(normal_cones_, fh);
183 
184  nc.merge(NormalCone(mesh_.calc_face_normal(fh)));
185  if (fh == fhl) nc.merge(mesh_.property(normal_cones_, _ci.fl));
186  if (fh == fhr) nc.merge(mesh_.property(normal_cones_, _ci.fr));
187 
188  if (nc.angle() > max_angle) {
189  max_angle = nc.angle();
190  if (max_angle > 0.5 * normal_deviation_)
191  break;
192  }
193  }
194  }
195 
196 
197  // undo simulation changes
198  mesh_.set_point(_ci.v0, _ci.p0);
199 
200 
201  return (max_angle < 0.5 * normal_deviation_ ? max_angle : float( Base::ILLEGAL_COLLAPSE ));
202  }
203 
205  void set_error_tolerance_factor(double _factor) {
206  if (_factor >= 0.0 && _factor <= 1.0) {
207  // the smaller the factor, the smaller normal_deviation_ gets
208  // thus creating a stricter constraint
209  // division by error_tolerance_factor_ is for normalization
210  Scalar normal_deviation = (normal_deviation_ * 180.0/M_PI) * _factor / this->error_tolerance_factor_;
211  set_normal_deviation(normal_deviation);
212  this->error_tolerance_factor_ = _factor;
213  }
214  }
215 
216 
218  // account for changed normals
219  typename Mesh::VertexFaceIter vf_it(mesh_, _ci.v1);
220  for (; vf_it.is_valid(); ++vf_it)
221  mesh_.property(normal_cones_, *vf_it).
222  merge(NormalCone(mesh_.normal(*vf_it)));
223 
224 
225  // normal cones of deleted triangles
226  typename Mesh::FaceHandle fh;
227 
228  if (_ci.vlv1.is_valid()) {
229  fh = mesh_.face_handle(mesh_.opposite_halfedge_handle(_ci.vlv1));
230  if (fh.is_valid())
231  mesh_.property(normal_cones_, fh).
232  merge(mesh_.property(normal_cones_, _ci.fl));
233  }
234 
235  if (_ci.v1vr.is_valid()) {
236  fh = mesh_.face_handle(mesh_.opposite_halfedge_handle(_ci.v1vr));
237  if (fh.is_valid())
238  mesh_.property(normal_cones_, fh).
239  merge(mesh_.property(normal_cones_, _ci.fr));
240  }
241  }
242 
243 
244 
245 private:
246 
247  Mesh& mesh_;
248  Scalar normal_deviation_;
250 };
251 
252 
253 //=============================================================================
254 } // END_NS_DECIMATER
255 } // END_NS_OPENMESH
256 //=============================================================================
257 #endif // OPENMESH_DECIMATER_MODNORMALDEVIATIONT_HH defined
258 //=============================================================================
259 
~ModNormalDeviationT()
Destructor.
Definition: ModNormalDeviationT.hh:124
ModNormalDeviationT(MeshT &_mesh, float _max_dev=180.0)
Constructor.
Definition: ModNormalDeviationT.hh:106
void merge(const NormalConeT &)
merge _cone; this instance will then enclose both former cones
Definition: NormalConeT.cc:120
#define DECIMATING_MODULE(Classname, MeshT, Name)
Convenience macro, to be used in derived modules The macro defines the types.
Definition: ModBaseT.hh:147
Stores information about a halfedge collapse.
Definition: CollapseInfoT.hh:73
Mesh::HalfedgeHandle vlv1
Outer remaining halfedge of diamond spanned by v0, v1, vl, and vr.
Definition: CollapseInfoT.hh:102
Base class for all decimation modules.
Definition: ModBaseT.hh:190
Mesh::Point p0
Position of removed vertex.
Definition: CollapseInfoT.hh:92
Mesh::HalfedgeHandle vrv0
Outer remaining halfedge of diamond spanned by v0, v1, vl, and vr.
Definition: CollapseInfoT.hh:102
Contains all the mesh ingredients like the polygonal mesh, the triangle mesh, different mesh kernels ...
Definition: MeshItems.hh:56
MeshT & mesh()
Access the mesh associated with the decimater.
Definition: ModBaseT.hh:275
Mesh::VertexHandle v0
Vertex to be removed.
Definition: CollapseInfoT.hh:90
Mesh::FaceHandle fr
Right face.
Definition: CollapseInfoT.hh:95
void postprocess_collapse(const CollapseInfo &_ci)
After _from_vh has been collapsed into _to_vh, this method will be called.
Definition: ModNormalDeviationT.hh:217
void initialize()
Allocate and init normal cones.
Definition: ModNormalDeviationT.hh:142
/class NormalCone NormalCone.hh
Definition: NormalConeT.hh:78
Handle representing a face property.
Definition: Property.hh:518
void set_normal_deviation(Scalar _s)
Set normal deviation ( 0 .. 360 )
Definition: ModNormalDeviationT.hh:136
void set_error_tolerance_factor(double _factor)
set the percentage of normal deviation
Definition: ModNormalDeviationT.hh:205
Scalar normal_deviation() const
Get normal deviation ( 0 .. 360 )
Definition: ModNormalDeviationT.hh:131
Mesh::HalfedgeHandle v0vl
Outer remaining halfedge of diamond spanned by v0, v1, vl, and vr.
Definition: CollapseInfoT.hh:102
Mesh::HalfedgeHandle v1vr
Outer remaining halfedge of diamond spanned by v0, v1, vl, and vr.
Definition: CollapseInfoT.hh:102
Scalar angle() const
returns size of cone (radius in radians)
Definition: NormalConeT.hh:105
Base class for all decimation modules.
Mesh::Point p1
Positions of remaining vertex.
Definition: CollapseInfoT.hh:93
Mesh::VertexHandle v1
Remaining vertex.
Definition: CollapseInfoT.hh:91
Mesh::FaceHandle fl
Left face.
Definition: CollapseInfoT.hh:94
Add normals to mesh item (vertices/faces)
Definition: Attributes.hh:80
float collapse_priority(const CollapseInfo &_ci)
Control normals when Decimating.
Definition: ModNormalDeviationT.hh:167
Use Normal deviation to control decimation.
Definition: ModNormalDeviationT.hh:87

acg pic Project OpenMesh, ©  Computer Graphics Group, RWTH Aachen. Documentation generated using doxygen .