ug4
Loading...
Searching...
No Matches
manifold_smoothing.h
Go to the documentation of this file.
1/*
2 * Copyright (c) 2013-2015: G-CSC, Goethe University Frankfurt
3 * Author: Sebastian Reiter
4 *
5 * This file is part of UG4.
6 *
7 * UG4 is free software: you can redistribute it and/or modify it under the
8 * terms of the GNU Lesser General Public License version 3 (as published by the
9 * Free Software Foundation) with the following additional attribution
10 * requirements (according to LGPL/GPL v3 §7):
11 *
12 * (1) The following notice must be displayed in the Appropriate Legal Notices
13 * of covered and combined works: "Based on UG4 (www.ug4.org/license)".
14 *
15 * (2) The following notice must be displayed at a prominent place in the
16 * terminal output of covered works: "Based on UG4 (www.ug4.org/license)".
17 *
18 * (3) The following bibliography is recommended for citation and must be
19 * preserved in all covered files:
20 * "Reiter, S., Vogel, A., Heppner, I., Rupp, M., and Wittum, G. A massively
21 * parallel geometric multigrid solver on hierarchically distributed grids.
22 * Computing and visualization in science 16, 4 (2013), 151-164"
23 * "Vogel, A., Reiter, S., Rupp, M., Nägel, A., and Wittum, G. UG4 -- a novel
24 * flexible software system for simulating pde based models on high performance
25 * computers. Computing and visualization in science 16, 4 (2013), 165-179"
26 *
27 * This program is distributed in the hope that it will be useful,
28 * but WITHOUT ANY WARRANTY; without even the implied warranty of
29 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
30 * GNU Lesser General Public License for more details.
31 */
32
33#ifndef __H__UG__manifold_smoothing__
34#define __H__UG__manifold_smoothing__
35
36#include "common/types.h"
38#include "../volume_calculation.h"
39
40namespace ug{
41
43template <class TIterator, class AAPosVRT>
44void LaplacianSmooth(Grid& grid, TIterator vrtsBegin,
45 TIterator vrtsEnd, AAPosVRT& aaPos,
46 number alpha, int numIterations)
47{
51
52 bool gotFaces = grid.num<Face>() > 0;
53 bool gotVols = grid.num<Volume>() > 0;
54
55 for(int iteration = 0; iteration < numIterations; ++iteration){
56 // iterate through all vertices
57 for(TIterator iter = vrtsBegin; iter != vrtsEnd; ++iter){
58 // smooth each one
59 Vertex* vrt = *iter;
60 vector3 v;
61 VecSet(v, 0);
62 number weight = 0;
63
64 // calculate smoothing vector relative to neighbors
65 grid.associated_elements(edges, vrt);
66 for(size_t i = 0; i < edges.size(); ++i){
67 // number w = EdgeLength(edges[i], aaPos);
68 number w = 1;
69 VecScaleAdd(v, 1, v, w, aaPos[GetConnectedVertex(edges[i], vrt)]);
70 weight += w;
71 }
72
73 if(gotFaces){
74 grid.associated_elements(faces, vrt);
75 for(size_t i = 0; i < faces.size(); ++i){
76 Face* f = faces[i];
77 // number a = CalculateVolume(f, aaPos);
78 number a = 1;
79 VecScaleAdd(v, 1, v, a,
81 grid.get_opposing_object(vrt, f),
82 aaPos));
83
84 weight += a;
85 }
86 }
87
88 if(gotVols){
89 grid.associated_elements(vols, vrt);
90 for(size_t i = 0; i < vols.size(); ++i){
91 Volume* vol = vols[i];
92 // number a = CalculateVolume(vol, aaPos);
93 number a = 1;
94 VecScaleAdd(v, 1, v, a,
96 grid.get_opposing_object(vrt, vol),
97 aaPos));
98
99 weight += a;
100 }
101 }
102
103 if(weight > 0){
104 VecScale(v, v, 1. / weight);
105 VecSubtract(v, v, aaPos[vrt]);
106 VecScale(v, v, alpha);
107 VecAdd(aaPos[vrt], aaPos[vrt], v);
108 }
109 }
110 }
111}
112
115
116template <class TVrtIter, class TAAPos3>
117void TangentialSmoothSimple(Grid& g, TVrtIter vrtsBegin, TVrtIter vrtsEnd,
118 TAAPos3 aaPos, number alpha, size_t numIterations)
119{
121 for(size_t iteration = 0; iteration < numIterations; ++iteration){
122 for(TVrtIter iter = vrtsBegin; iter != vrtsEnd; ++iter){
123 Vertex* vrt = *iter;
124 g.associated_elements(faces, vrt);
125 if(faces.empty())
126 continue;
127
128 // calculate the normal at the current vertex
129 vector3 n(0, 0, 0);
130 for(size_t i = 0; i < faces.size(); ++i){
131 vector3 tn;
132 CalculateNormal(tn, faces[i], aaPos);
133 VecAdd(n, n, tn);
134 }
135
136 // calculate the center of connected vertices
137 vector3 c(0, 0, 0);
138 size_t numConnected = 0;
139 g.begin_marking();
140 for(size_t i_face = 0; i_face < faces.size(); ++i_face){
141 Face::ConstVertexArray vrts = faces[i_face]->vertices();
142 const size_t numVrts = faces[i_face]->num_vertices();
143 for(size_t i_vrt = 0; i_vrt < numVrts; ++i_vrt){
144 Vertex* v = vrts[i_vrt];
145 if((v != vrt) && (!g.is_marked(v))){
146 g.mark(v);
147 VecAdd(c, c, aaPos[v]);
148 ++numConnected;
149 }
150 }
151 }
152 g.end_marking();
153 if(numConnected == 0)
154 continue;
155
156 VecScale(c, c, 1. / (number)numConnected);
157
158 // project the center of connected vertices to the plane through vrt
159 vector3 cp;
160 ProjectPointToPlane(cp, c, aaPos[vrt], n);
161
162 // move the vertex
163 VecScaleAdd(aaPos[vrt], (1. - alpha), aaPos[vrt], alpha, cp);
164 }
165 }
166}
167
170
174template <class TVrtIter, class TAAPos3>
175void TangentialSmooth(Grid& g, TVrtIter vrtsBegin, TVrtIter vrtsEnd,
176 TAAPos3 aaPos, number alpha, size_t numIterations)
177{
178// attach an integer index to all vertices
179 AInt aInt;
180 g.attach_to_vertices_dv(aInt, -1);
182
183 int counter = 0;
184 std::vector<vector3*> vrtPos;
185 for(TVrtIter iter = vrtsBegin; iter != vrtsEnd; ++iter){
186 aaInt[*iter] = counter++;
187 vrtPos.push_back(&aaPos[*iter]);
188 }
189
190 std::vector<int> adjVrtInds;
191 std::vector<int> adjVrtOffsets;
192 std::vector<Face*> adjFaces;
193 std::vector<int> adjFaceOffsets;
194
195 adjVrtInds.reserve(counter * 7);//just a guess
196 adjVrtOffsets.reserve(counter + 1);
197 vrtPos.reserve(counter);
198 adjFaces.reserve(counter * 7);//just a guess
199 adjFaceOffsets.reserve(counter + 1);
200
201// build adjacency graph
203 for(TVrtIter iter = vrtsBegin; iter != vrtsEnd; ++iter){
204 Vertex* vrt = *iter;
205 adjVrtOffsets.push_back(adjVrtInds.size());
206 adjFaceOffsets.push_back(adjFaces.size());
207
208 g.associated_elements(faces, vrt);
209 if(faces.empty())
210 continue;
211
212 // create adjacencies
213 g.begin_marking();
214 for(size_t i_face = 0; i_face < faces.size(); ++i_face){
215 adjFaces.push_back(faces[i_face]);
216 Face::ConstVertexArray vrts = faces[i_face]->vertices();
217 const size_t numVrts = faces[i_face]->num_vertices();
218 for(size_t i_vrt = 0; i_vrt < numVrts; ++i_vrt){
219 Vertex* v = vrts[i_vrt];
220 if((v != vrt) && (!g.is_marked(v))){
221 g.mark(v);
222 if(aaInt[v] == -1){
223 // positions of vertices which are not to be smoothed but which are
224 // adjacent to smoothed ones, are inserted on the fly.
225 aaInt[v] = (int)vrtPos.size();
226 vrtPos.push_back(&aaPos[v]);
227 }
228 adjVrtInds.push_back(aaInt[v]);
229 }
230 }
231 }
232 g.end_marking();
233 }
234
235 adjVrtOffsets.push_back(adjVrtInds.size());
236 adjFaceOffsets.push_back(adjFaces.size());
237 g.detach_from_vertices(aInt);
238
239 std::vector<vector3> offsets(vrtPos.size());
240 std::vector<vector3> newOffsets(vrtPos.size());
241
242 for(size_t iteration = 0; iteration < numIterations; ++iteration){
243 // calculate the initial offset vectors for each vertex
244 for(size_t i_vrt = 0; i_vrt + 1 < adjVrtOffsets.size(); ++i_vrt){
245 // calculate plane normal
246 int adjFacesBegin = adjFaceOffsets[i_vrt];
247 int adjFacesEnd = adjFaceOffsets[i_vrt+1];
248
249 if(adjFacesBegin == adjFacesEnd){
250 offsets[i_vrt] = vector3(0, 0, 0);
251 continue;
252 }
253
254 vector3 n(0, 0, 0);
255 for(int i_adj = adjFacesBegin; i_adj < adjFacesEnd; ++i_adj){
256 vector3 tn;
257 CalculateNormal(tn, adjFaces[i_adj], aaPos);
258 VecAdd(n, n, tn);
259 }
260
261 // calculate center of adjacent vertices
262 int adjVrtsBegin = adjVrtOffsets[i_vrt];
263 int adjVrtsEnd = adjVrtOffsets[i_vrt+1];
264
265 if(adjVrtsBegin == adjVrtsEnd){
266 offsets[i_vrt] = vector3(0, 0, 0);
267 continue;
268 }
269
270 vector3 c(0, 0, 0);
271 for(int i_adj = adjVrtsBegin; i_adj < adjVrtsEnd; ++i_adj){
272 int adjVrt = adjVrtInds[i_adj];
273 VecAdd(c, c, *vrtPos[adjVrt]);
274 }
275 VecScale(c, c, 1. / number(adjVrtsEnd - adjVrtsBegin));
276
277 // project center to plane and calculate the offset
278 vector3 cp;
279 ProjectPointToPlane(cp, c, *vrtPos[i_vrt], n);
280 VecSubtract(offsets[i_vrt], cp, *vrtPos[i_vrt]);
281 }
282
283 // now smooth the offset vectors by repeatedly taking the average of
284 // neighbored vectors
285 const size_t numOffsetSmoothSteps = 1;
286 for(size_t i_step = 0; i_step < numOffsetSmoothSteps; ++i_step){
287 for(size_t i_vrt = 0; i_vrt + 1 < adjVrtOffsets.size(); ++i_vrt){
288 int adjVrtsBegin = adjVrtOffsets[i_vrt];
289 int adjVrtsEnd = adjVrtOffsets[i_vrt+1];
290
291 if(adjVrtsBegin == adjVrtsEnd)
292 continue;
293
294 int numAdj = adjVrtsEnd - adjVrtsBegin;
295 //vector3 o = offsets[i_vrt];
296 vector3 o;
297 VecScale(o, offsets[i_vrt], numAdj);
298 for(int i_adj = adjVrtsBegin; i_adj < adjVrtsEnd; ++i_adj){
299 int adjVrt = adjVrtInds[i_adj];
300 VecAdd(o, o, offsets[adjVrt]);
301 }
302 VecScale(newOffsets[i_vrt], o, 1. / number(2 * numAdj));
303
304 // restrict offset to plane
305 int adjFacesBegin = adjFaceOffsets[i_vrt];
306 int adjFacesEnd = adjFaceOffsets[i_vrt+1];
307
308 if(adjFacesBegin == adjFacesEnd){
309 offsets[i_vrt] = vector3(0, 0, 0);
310 continue;
311 }
312
313 vector3 n(0, 0, 0);
314 for(int i_adj = adjFacesBegin; i_adj < adjFacesEnd; ++i_adj){
315 vector3 tn;
316 CalculateNormal(tn, adjFaces[i_adj], aaPos);
317 VecAdd(n, n, tn);
318 }
319
320 VecNormalize(n, n);
321 number dot = VecDot(n, newOffsets[i_vrt]);
322 VecScale(n, n, dot);
323 VecSubtract(newOffsets[i_vrt], newOffsets[i_vrt], n);
324 }
325 offsets.swap(newOffsets);
326 }
327
328 // and now move the vertices by their smoothed offset vectors
329 for(size_t i_vrt = 0; i_vrt + 1 < adjVrtOffsets.size(); ++i_vrt){
330 VecScaleAdd(*vrtPos[i_vrt], 1, *vrtPos[i_vrt], alpha, offsets[i_vrt]);
331 }
332 }
333}
334
335
337
343template <class TIterator, class AAPosVRT>
344void WeightedEdgeSmooth(Grid& grid, TIterator vrtsBegin,
345 TIterator vrtsEnd, AAPosVRT& aaPos,
346 number alpha, int numIterations,
347 Grid::vertex_traits::callback cbSmoothVertex)
348{
349 typedef typename AAPosVRT::ValueType vector_t;
350
352
353 for(int iteration = 0; iteration < numIterations; ++iteration){
354 // iterate through all vertices
355 for(TIterator iter = vrtsBegin; iter != vrtsEnd; ++iter){
356 // smooth each one
357 Vertex* vrt = *iter;
358 vector_t vrtPos = aaPos[vrt];
359 vector_t avDir;
360 VecSet(avDir, 0);
361 number weight = 0;
362
363 // calculate smoothing vector relative to neighbors
364 grid.associated_elements(edges, vrt);
365 number numNonSmooth = 0;
366 for(size_t i = 0; i < edges.size(); ++i){
367 Vertex* connVrt = GetConnectedVertex(edges[i], vrt);
368 if(!cbSmoothVertex(connVrt))
369 numNonSmooth += 1;
370 }
371
372 number nonSmoothWeight = 1. / std::max<number>(1, numNonSmooth);
373
374 for(size_t i = 0; i < edges.size(); ++i){
375 Vertex* connVrt = GetConnectedVertex(edges[i], vrt);
376 number w = 1;
377 if(!cbSmoothVertex(connVrt))
378 w = nonSmoothWeight;
379
380 vector_t dir;
381 VecSubtract(dir, aaPos[connVrt], vrtPos);
382 w *= VecLengthSq(dir);
383 dir *= w;
384 VecAdd(avDir, avDir, dir);
385 weight += w;
386 }
387
388 if(weight > 0){
389 avDir *= alpha / weight;
390 VecAdd(aaPos[vrt], vrtPos, avDir);
391 }
392 }
393 }
394}
395
397
403template <class TIterator, class AAPosVRT>
404void WeightedFaceSmooth(Grid& grid, TIterator vrtsBegin,
405 TIterator vrtsEnd, AAPosVRT& aaPos,
406 number alpha, int numIterations,
407 Grid::vertex_traits::callback cbSmoothVertex)
408{
409 typedef typename AAPosVRT::ValueType vector_t;
410
412
413 for(int iteration = 0; iteration < numIterations; ++iteration){
414 // iterate through all vertices
415 for(TIterator iter = vrtsBegin; iter != vrtsEnd; ++iter){
416 // smooth each one
417 Vertex* vrt = *iter;
418 vector_t vrtPos = aaPos[vrt];
419 vector_t avDir;
420 VecSet(avDir, 0);
421 number weight = 0;
422
423 // calculate smoothing vector relative to neighbors
424 grid.associated_elements(faces, vrt);
425
426 for(size_t i = 0; i < faces.size(); ++i){
427 Face* f = faces[i];
428 if(f->num_vertices() != 3)
429 continue;
430
431 number w = 1;
432 Edge* e = GetConnectedEdge(grid, vrt, f);
433 Vertex* v0 = e->vertex(0);
434 Vertex* v1 = e->vertex(1);
435 vector_t edgeCenter;
436 if(cbSmoothVertex(v0)){
437 if(cbSmoothVertex(v1))
438 VecScaleAdd(edgeCenter, 0.5, aaPos[v0], 0.5, aaPos[v1]);
439 else
440 VecScaleAdd(edgeCenter, 0.75, aaPos[v0], 0.25, aaPos[v1]);
441 }
442 else if(cbSmoothVertex(v1))
443 VecScaleAdd(edgeCenter, 0.25, aaPos[v0], 0.75, aaPos[v1]);
444 else{
445 VecScaleAdd(edgeCenter, 0.5, aaPos[v0], 0.5, aaPos[v1]);
446 w = 0.5;
447 }
448
449 vector_t dir;
450 VecSubtract(dir, edgeCenter, vrtPos);
451 w *= CalculateVolume(f, aaPos);
452 dir *= w;
453 VecAdd(avDir, avDir, dir);
454 weight += w;
455 }
456
457 if(weight > 0){
458 avDir *= alpha / weight;
459 VecAdd(aaPos[vrt], vrtPos, avDir);
460 }
461 }
462 }
463}
464
465
467
470template <class TIterator, class AAPosVRT>
471void WeightedNormalSmooth(Grid& grid, TIterator vrtsBegin,
472 TIterator vrtsEnd, AAPosVRT& aaPos,
473 number alpha, number dotThreshold,
474 int numIterations)
475{
476 using std::min;
477 using std::max;
478
479 typedef typename AAPosVRT::ValueType vector_t;
480
482
483 for(int iteration = 0; iteration < numIterations; ++iteration){
484 // iterate through all vertices
485 for(TIterator iter = vrtsBegin; iter != vrtsEnd; ++iter){
486 // smooth each one
487 Vertex* vrt = *iter;
488 vector_t vrtPos = aaPos[vrt];
489 vector_t vrtNorm;
490 CalculateVertexNormal(vrtNorm, grid, vrt, aaPos);
491
492 vector_t avDir;
493 VecSet(avDir, 0);
494
495 grid.associated_elements(edges, vrt);
496 number nbrs = 0;
497 for(size_t i = 0; i < edges.size(); ++i){
498 Vertex* connVrt = GetConnectedVertex(edges[i], vrt);
499 vector_t dir = aaPos[connVrt];
500 dir -= vrtPos;
501 vector_t ndir;
502 VecNormalize(ndir, dir);
503 number dot = VecDot(vrtNorm, ndir);
504 if(dot >= dotThreshold){
505 dir *= 0.5 * (dot + 1);
506 avDir += dir;
507 ++nbrs;
508 }
509 }
510
511 if(nbrs > 0){
512 avDir *= alpha / nbrs;
513 aaPos[vrt] += avDir;
514 }
515 }
516 }
517}
518
519
521
522template <class TIterator, class AAPosVRT>
523void SlopeSmooth(Grid& grid, TIterator vrtsBegin,
524 TIterator vrtsEnd, AAPosVRT& aaPos,
525 number alpha, const vector3& up,
526 int numIterations)
527{
528 using std::min;
529 using std::max;
530
531 typedef typename AAPosVRT::ValueType vector_t;
532
533 vector3 upN;
534 VecNormalize(upN, up);
535
536// we'll approximate the gradient by finding the path between the intersections
537// of connected edges and the plane through the center-vertex, spanned by the normal-
538// and up-vectors
541
542 for(int iteration = 0; iteration < numIterations; ++iteration){
543 // iterate through all vertices
544 for(TIterator iter = vrtsBegin; iter != vrtsEnd; ++iter){
545 // smooth each one
546 Vertex* vrt = *iter;
547 vector_t vrtPos = aaPos[vrt];
548 vector_t vrtNorm;
549
550 // check if the vertex is a boundary vertex. If so, we'll only consider
551 // the connected boundary vertices
552 if(LiesOnBoundary(grid, vrt)){
553 grid.associated_elements(edges, vrt);
554
555 vector3 target(0, 0, 0);
556 number numBndEdges = 0;
557
558 for(size_t i = 0; i < edges.size(); ++i){
559 if(IsBoundaryEdge2D(grid, edges[i])){
560 target += aaPos[GetConnectedVertex(edges[i], vrt)];
561 ++numBndEdges;
562 }
563 }
564
565 if(numBndEdges > 0)
566 VecScaleAdd(aaPos[vrt], alpha/numBndEdges, target, 1. - alpha, vrtPos);
567 }
568 else{
569 CalculateVertexNormal(vrtNorm, grid, vrt, aaPos);
570
571 //todo: one could think about performing laplacian smoothing in this case
572 if(fabs(VecDot(vrtNorm, upN)) > 1. - SMALL)
573 continue;
574
575 vector3 planeNormal;
576 VecCross(planeNormal, vrtNorm, upN);
577
578 vector3 inters[2];
579 int numInters = 0;
580
581 grid.associated_elements(faces, vrt);
582 for(size_t i = 0; i < faces.size(); ++i){
583 Edge* e = GetConnectedEdge(grid, vrt, faces[i]);
584 vector3 v0 = aaPos[e->vertex(0)];
585 vector3 dir = aaPos[e->vertex(1)];
586 dir -= v0;
587
588 vector3 vi;
589 number t;
590 if(RayPlaneIntersection(vi, t, v0, dir, vrtPos, planeNormal)){
591 if(t >= -SMALL && t <= 1 + SMALL){
592 if((numInters > 1) &&
593 (VecDistanceSq(vi, inters[0]) > VecDistanceSq(inters[1], inters[0])))
594 {
595 inters[1] = vi;
596 }
597 else{
598 inters[numInters] = vi;
599 ++numInters;
600 }
601 }
602 }
603 }
604
605 if(numInters == 2){
606 vector3 target;
607 VecScaleAdd(target, 0.5, inters[0], 0.5, inters[1]);
608 VecScaleAdd(aaPos[vrt], alpha, target, 1. - alpha, vrtPos);
609 }
610 }
611 }
612 }
613}
614
615
616}// end of namespace
617
618#endif
Base-class for edges.
Definition grid_base_objects.h:397
virtual Vertex * vertex(size_t index) const
Definition grid_base_objects.h:366
Faces are 2-dimensional objects.
Definition grid_base_objects.h:510
virtual size_t num_vertices() const
Definition grid_base_objects.h:488
Manages the elements of a grid and their interconnection.
Definition grid.h:132
void end_marking()
ends a marking sequence. Call this method when you're done with marking.
Definition grid.cpp:1285
void attach_to_vertices_dv(TAttachment &attachment, const typename TAttachment::ValueType &defaultValue)
Definition grid.h:754
bool is_marked(GridObject *obj) const
returns true if the object is marked, false if not.
Definition grid_impl.hpp:843
size_t num() const
Definition grid_impl.hpp:230
void mark(GridObject *obj)
marks the object. Calls are only valid between calls to Grid::begin_marking and Grid::end_marking.
Definition grid_impl.hpp:773
void begin_marking()
begin marking.
Definition grid.cpp:1262
void detach_from_vertices(IAttachment &attachment)
Definition grid.h:787
GridObject * get_opposing_object(Vertex *vrt, Face *elem)
returns the geometric object on the opposing side of the given vertex regarding the given element.
Definition grid.cpp:631
void associated_elements(traits< Vertex >::secure_container &elemsOut, TElem *e)
Puts all elements of type TAss which are contained in 'e' or which contain 'e' into elemsOut.
Definition grid_impl.hpp:466
Vertex *const * ConstVertexArray
Definition grid_base_objects.h:319
Base-class for all vertex-types.
Definition grid_base_objects.h:231
Volumes are 3-dimensional objects.
Definition grid_base_objects.h:754
bool LiesOnBoundary(Grid &grid, Edge *e)
returns true, if the edge lies on a 2d or 3d boundary
Definition edge_util.cpp:169
int CalculateNormal(vector3 &vNormOut, Grid &grid, Edge *e, Grid::AttachmentAccessor< Vertex, APosition > &aaPos, Grid::AttachmentAccessor< Face, ANormal > *paaNormFACE)
Calculates the normal of the given edge.
Definition edge_util.cpp:314
bool IsBoundaryEdge2D(Grid &grid, Edge *e)
returns whether an edge lies on the boundary of a 2D grid.
Definition edge_util.cpp:112
UG_API TAAPosVRT::ValueType CalculateGridObjectCenter(const GridObject *o, TAAPosVRT &aaPosVRT)
calculates the center for arbitrary geometric object
Definition misc_util_impl.hpp:81
Edge * GetConnectedEdge(Grid &g, Vertex *vrt, Face *tri)
returns the edge in the triangle tri, which does not contain vrt.
Definition vertex_util.cpp:121
UG_API void CalculateVertexNormal(vector3 &nOut, Grid &grid, Vertex *vrt, TAAPosVRT &aaPos)
calculates the normal of a vertex using associated faces
Definition vertex_util_impl.hpp:61
Vertex * GetConnectedVertex(Edge *e, Vertex *v)
returns the vertex that is connected to v via e.
Definition vertex_util.cpp:78
number CalculateVolume(Volume *elem, TAAPos aaPos)
Calculates the volume of the given element.
Definition volume_calculation_impl.hpp:43
double number
Definition types.h:124
bool RayPlaneIntersection(vector_t &vOut, number &tOut, const vector_t &rayFrom, const vector_t &rayDir, const vector_t &p, const vector_t &n)
calculates the intersection of the ray rayFrom+t*rayDir and the plane (x-p)*n=0.
Definition math_util_impl.hpp:360
void ProjectPointToPlane(vector_t &vOut, const vector_t &v, const vector_t &p, const vector_t &n)
projects v onto the plane defined by the point p and the planes normal n.
Definition math_util_impl.hpp:342
void VecSet(vector_t &vInOut, typename vector_t::value_type s)
Set each vector component to scalar (componentwise)
Definition math_vector_functions_common_impl.hpp:539
void VecScaleAdd(vector_t &vOut, typename vector_t::value_type s1, const vector_t &v1, typename vector_t::value_type s2, const vector_t &v2)
Scales two Vectors, adds them and returns the sum in a third vector.
Definition math_vector_functions_common_impl.hpp:265
void VecNormalize(vector_t &vOut, const vector_t &v)
scales a vector_t to unit length
Definition math_vector_functions_common_impl.hpp:501
void VecSubtract(vector_t &vOut, const vector_t &v1, const vector_t &v2)
subtracts v2 from v1 and stores the result in a vOut
Definition math_vector_functions_common_impl.hpp:226
vector_t::value_type VecDistanceSq(const vector_t &v1, const vector_t &v2)
returns the squared distance of two vector_ts.
Definition math_vector_functions_common_impl.hpp:351
MathVector< 3, number > vector3
a 3d vector
Definition ugmath_types.h:72
vector_t::value_type VecLengthSq(const vector_t &v)
returns the squared length of v. Faster than VecLength.
Definition math_vector_functions_common_impl.hpp:324
void VecAdd(vector_t &vOut, const vector_t &v1, const vector_t &v2)
adds two MathVector<N>s and stores the result in a third one
Definition math_vector_functions_common_impl.hpp:185
void VecScale(vector_t &vOut, const vector_t &v, typename vector_t::value_type s)
scales a MathVector<N>
Definition math_vector_functions_common_impl.hpp:252
void VecCross(vector_t &vOut, const vector_t &v1, const vector_t &v2)
calculates the cross product of two Vectors of dimension 3. It makes no sense to use VecCross for vec...
Definition math_vector_functions_common_impl.hpp:437
vector_t::value_type VecDot(const vector_t &v1, const vector_t &v2)
returns the dot-product of two vector_ts
Definition math_vector_functions_common_impl.hpp:385
the ug namespace
void TangentialSmooth(Grid &g, TVrtIter vrtsBegin, TVrtIter vrtsEnd, TAAPos3 aaPos, number alpha, size_t numIterations)
Definition manifold_smoothing.h:175
void SlopeSmooth(Grid &grid, TIterator vrtsBegin, TIterator vrtsEnd, AAPosVRT &aaPos, number alpha, const vector3 &up, int numIterations)
Definition manifold_smoothing.h:523
const number SMALL
Definition math_constants.h:41
void WeightedEdgeSmooth(Grid &grid, TIterator vrtsBegin, TIterator vrtsEnd, AAPosVRT &aaPos, number alpha, int numIterations, Grid::vertex_traits::callback cbSmoothVertex)
Definition manifold_smoothing.h:344
void WeightedNormalSmooth(Grid &grid, TIterator vrtsBegin, TIterator vrtsEnd, AAPosVRT &aaPos, number alpha, number dotThreshold, int numIterations)
Definition manifold_smoothing.h:471
void TangentialSmoothSimple(Grid &g, TVrtIter vrtsBegin, TVrtIter vrtsEnd, TAAPos3 aaPos, number alpha, size_t numIterations)
Definition manifold_smoothing.h:117
void WeightedFaceSmooth(Grid &grid, TIterator vrtsBegin, TIterator vrtsEnd, AAPosVRT &aaPos, number alpha, int numIterations, Grid::vertex_traits::callback cbSmoothVertex)
Definition manifold_smoothing.h:404
void LaplacianSmooth(Grid &grid, TIterator vrtsBegin, TIterator vrtsEnd, AAPosVRT &aaPos, number alpha, int numIterations)
Definition manifold_smoothing.h:44
boost::function< bool(base_object *)> callback
callback type for the elements base type.
Definition grid.h:150
PointerConstArray< Edge * > secure_container
Definition grid.h:146