Developer Documentation
TriangleBSPT.hh
1/*===========================================================================*\
2* *
3* OpenFlipper *
4 * Copyright (c) 2001-2015, RWTH-Aachen University *
5 * Department of Computer Graphics and Multimedia *
6 * All rights reserved. *
7 * www.openflipper.org *
8 * *
9 *---------------------------------------------------------------------------*
10 * This file is part of OpenFlipper. *
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//=============================================================================
45//
46// CLASS TriangleBSPT
47//
48//=============================================================================
49
50#pragma once
51
52
53//== INCLUDES =================================================================
54
55#include "BSPTreeNode.hh"
56#include "TriangleBSPCoreT.hh"
57#include "BSPImplT.hh"
58
59#include <list>
60//== CLASS DEFINITION =========================================================
61
62template <class BSPTraits>
63class TriangleBSPT : public BSPImplT< TriangleBSPCoreT<BSPTraits> >
64{
65public:
67 typedef typename Base::Scalar Scalar;
68 TriangleBSPT(const BSPTraits& _traits,
69 const Scalar& _infinity = std::numeric_limits<Scalar>::infinity()) : Base(_traits, _infinity) {}
70};
71
72//== CLASS DEFINITION =========================================================
73
74template <class Mesh, class SpecificTraits>
75class OVMOMCommonTriangleBSPTraits : public SpecificTraits
76{
77public:
78
79 typedef typename SpecificTraits::Point Point;
80 typedef typename SpecificTraits::Handle Handle;
81 typedef typename Point::value_type Scalar;
82 typedef std::vector<Handle> Handles;
83 typedef typename Handles::iterator HandleIter;
85
86 explicit OVMOMCommonTriangleBSPTraits(const Mesh& _mesh) : SpecificTraits(_mesh) {}
87
88 Scalar sqrdist(const Handle _h, const Point& _p) const
89 {
90 Point p0, p1, p2, q;
91 this->points(_h, p0, p1, p2);
92 return ACG::Geometry::distPointTriangleSquaredStable(_p, p0, p1, p2, q);
93 }
94
95 void calculateBoundingBox(Node* _node, Point& median, int& axis)
96 {
97 //determine splitting axis
98 HandleIter it_h;
99 Point p0, p1, p2, bb_min, bb_max;
100 bb_min.vectorize(std::numeric_limits<typename Point::value_type>::infinity());
101 bb_max.vectorize(-std::numeric_limits<typename Point::value_type>::infinity());
102 std::list<Point> vertices;
103
104 for (it_h = _node->begin(); it_h != _node->end(); ++it_h) {
105 this->points(*it_h, p0, p1, p2);
106 /*
107 bb_min.minimize(p0);
108 bb_min.minimize(p1);
109 bb_min.minimize(p2);
110 bb_max.maximize(p0);
111 bb_max.maximize(p1);
112 bb_max.maximize(p2);*/
113
114 vertices.push_back(p0);
115 vertices.push_back(p1);
116 vertices.push_back(p2);
117 }
118 bb_min = _node->bb_min;
119 bb_max = _node->bb_max;
120
121 // split longest side of bounding box
122 Point bb = bb_max - bb_min;
123 Scalar length = bb[0];
124 axis = 0;
125 if (bb[1] > length)
126 length = bb[(axis = 1)];
127 if (bb[2] > length)
128 length = bb[(axis = 2)];
129
130 //calculate the median value in axis-direction
131 switch (axis) {
132 case 0:
133 vertices.sort(x_sort());
134 break;
135 case 1:
136 vertices.sort(y_sort());
137 break;
138 case 2:
139 vertices.sort(z_sort());
140 break;
141 }
142 vertices.unique();
143
144 size_t size = vertices.size();
145 typename std::list<Point>::iterator it_v;
146 it_v = vertices.begin();
147 std::advance(it_v, size / 2);
148 median = *it_v;
149
150 }
151
152 void calculateBoundingBoxRoot(Node* _node)
153 {
154 HandleIter it;
155 Point p0, p1, p2, bb_min, bb_max;
156 bb_min.vectorize(FLT_MAX);
157 bb_max.vectorize(-FLT_MAX);
158 for (it = _node->begin(); it != _node->end(); ++it) {
159 this->points(*it, p0, p1, p2);
160 bb_min.minimize(p0);
161 bb_min.minimize(p1);
162 bb_min.minimize(p2);
163 bb_max.maximize(p0);
164 bb_max.maximize(p1);
165 bb_max.maximize(p2);
166 }
167 _node->bb_min = bb_min;
168 _node->bb_max = bb_max;
169 }
170
171private:
172 //functors for sorting in different directions
173 struct x_sort { bool operator()(const Point& first, const Point& second) { return (first[0] < second[0]); } };
174 struct y_sort { bool operator()(const Point& first, const Point& second) { return (first[1] < second[1]); } };
175 struct z_sort { bool operator()(const Point& first, const Point& second) { return (first[2] < second[2]); } };
176};
177
178
179//== CLASS DEFINITION =========================================================
180
181template <class Mesh>
183{
184public:
185 typedef typename Mesh::Point Point;
186 typedef typename Mesh::FaceHandle Handle;
187 typedef typename Mesh::VertexHandle VertexHandle;
188 explicit OMSpecificTriangleBSPTraits(const Mesh& _mesh) : mesh_(_mesh) {}
189
191 inline void points(const Handle &_h, Point& _p0, Point& _p1, Point& _p2) const
192 {
193 const auto &mesh = this->mesh_;
194 typename Mesh::CFVIter fv_it(mesh.cfv_iter(_h));
195 _p0 = mesh.point(*fv_it);
196 ++fv_it;
197 _p1 = mesh.point(*fv_it);
198 ++fv_it;
199 _p2 = mesh.point(*fv_it);
200 }
201protected:
202 const Mesh& mesh_;
203};
204
205template<class Mesh>
207
208
209//== CLASS DEFINITION =========================================================
210template <class Mesh>
212 : public TriangleBSPT<OpenMeshTriangleBSPTraits<Mesh> >
213{
214public:
217 typedef typename Traits::Scalar Scalar;
218 OpenMeshTriangleBSPT(const Mesh& _mesh,
219 const Scalar& _infinity = std::numeric_limits<Scalar>::infinity())
220 : Base(Traits(_mesh), _infinity) {}
221};
222
223
224#if (defined ENABLE_POLYHEDRALMESH_SUPPORT) \
225 || (defined ENABLE_HEXAHEDRALMESH_SUPPORT) \
226 || (defined ENABLE_TETRAHEDRALMESH_SUPPORT)
227
228#include <OpenVolumeMesh/Core/Handles.hh>
229//== CLASS DEFINITION =========================================================
230
231// Make sure all faces of the mesh have valence 3.
232template <class Mesh>
233class OVMSpecificTriangleBSPTraits
234{
235public:
236 typedef typename Mesh::PointT Point;
237 typedef OpenVolumeMesh::FaceHandle Handle;
238 typedef OpenVolumeMesh::VertexHandle VertexHandle;
239 explicit OVMSpecificTriangleBSPTraits(const Mesh& _mesh) : mesh_(_mesh) {}
240
242 inline void points(const Handle &_h, Point& _p0, Point& _p1, Point& _p2) const
243 {
244 const auto &mesh = this->mesh_;
245 assert(mesh.valence(_h) == 3);
246 auto hfv_it (mesh.hfv_iter(mesh.halfface_handle(_h, 0)));
247 _p0 = mesh.vertex(*hfv_it++);
248 _p1 = mesh.vertex(*hfv_it++);
249 _p2 = mesh.vertex(*hfv_it++);
250 }
251protected:
252 const Mesh& mesh_;
253};
254
255
256template<class Mesh>
257using OpenVolumeMeshTriangleBSPTraits = OVMOMCommonTriangleBSPTraits<Mesh, OVMSpecificTriangleBSPTraits<Mesh>>;
258
259//== CLASS DEFINITION =========================================================
260template <class Mesh>
261class OpenVolumeMeshTriangleBSPT
262 : public TriangleBSPT<OpenVolumeMeshTriangleBSPTraits<Mesh> >
263{
264public:
265 typedef OpenVolumeMeshTriangleBSPTraits<Mesh> Traits;
266 typedef TriangleBSPT<Traits> Base;
267 typedef typename Traits::Scalar Scalar;
268 OpenVolumeMeshTriangleBSPT(const Mesh& _mesh,
269 const Scalar& _infinity = std::numeric_limits<Scalar>::infinity())
270 : Base(Traits(_mesh), _infinity) {}
271};
272
273#endif
274
void points(const Handle &_h, Point &_p0, Point &_p1, Point &_p2) const
Returns the points belonging to the face handle _h.
void calculateBoundingBox(Node *_node, Point &median, int &axis)
Definition: TriangleBSPT.hh:95
Kernel::VertexHandle VertexHandle
Handle for referencing the corresponding item.
Definition: PolyMeshT.hh:136
Kernel::FaceHandle FaceHandle
Scalar type.
Definition: PolyMeshT.hh:139
Kernel::Point Point
Coordinate type.
Definition: PolyMeshT.hh:112
Vec::value_type distPointTriangleSquaredStable(const Vec &_p, const Vec &_v0, const Vec &_v1, const Vec &_v2, Vec &_nearestPoint)
squared distance from point _p to triangle (_v0, _v1, _v2)
Definition: Algorithms.cc:466