preCICE v3.1.1
Loading...
Searching...
No Matches
RTreeTests.cpp
Go to the documentation of this file.
1#include <Eigen/Core>
2#include <algorithm>
3#include <iterator>
4#include <limits>
5#include <list>
6#include <memory>
7#include <set>
8#include <utility>
9#include <vector>
10
11#include "logging/Logger.hpp"
12#include "math/geometry.hpp"
13#include "mesh/Data.hpp"
14#include "mesh/Edge.hpp"
15#include "mesh/Mesh.hpp"
17#include "mesh/Triangle.hpp"
18#include "mesh/Vertex.hpp"
19#include "query/Index.hpp"
21#include "testing/Testing.hpp"
22
23using namespace precice;
24using namespace precice::mesh;
25using namespace precice::query;
26
27namespace {
28PtrMesh fullMesh()
29{
30 PtrMesh ptr(new Mesh("MyMesh", 3, testing::nextMeshID()));
31 auto & mesh = *ptr;
32 auto & v1 = mesh.createVertex(Eigen::Vector3d(0, 2, 0));
33 auto & v2 = mesh.createVertex(Eigen::Vector3d(2, 1, 0));
34 auto & v3 = mesh.createVertex(Eigen::Vector3d(3, 0, 0));
35 auto & v4 = mesh.createVertex(Eigen::Vector3d(1, 0, 0));
36 // Quad Borders
37 auto &e1 = mesh.createEdge(v1, v2);
38 auto &e2 = mesh.createEdge(v2, v3);
39 auto &e3 = mesh.createEdge(v3, v4);
40 auto &e4 = mesh.createEdge(v4, v1);
41 // Diagonal
42 auto &e5 = mesh.createEdge(v2, v4);
43 // Triangles
44 mesh.createTriangle(e1, e5, e4);
45 mesh.createTriangle(e2, e3, e5);
46 return ptr;
47}
48
49PtrMesh edgeMesh3D()
50{
52 mesh->createVertex(Eigen::Vector3d(0, 0, 0));
53 mesh->createVertex(Eigen::Vector3d(0, 0, 1));
54 mesh->createVertex(Eigen::Vector3d(0, 1, 0));
55 mesh->createVertex(Eigen::Vector3d(0, 1, 1));
56 mesh->createVertex(Eigen::Vector3d(1, 0, 0));
57 mesh->createVertex(Eigen::Vector3d(1, 0, 1));
58 auto &v1 = mesh->createVertex(Eigen::Vector3d(1, 1, 0));
59 auto &v2 = mesh->createVertex(Eigen::Vector3d(1, 1, 1));
60 mesh->createEdge(v1, v2);
61 return mesh;
62}
63
64PtrMesh edgeMesh2D()
65{
66 PtrMesh mesh(new precice::mesh::Mesh("MyMesh", 2, testing::nextMeshID()));
67 mesh->createVertex(Eigen::Vector2d(0, 0));
68 mesh->createVertex(Eigen::Vector2d(0, 1));
69 auto &v1 = mesh->createVertex(Eigen::Vector2d(1, 0));
70 auto &v2 = mesh->createVertex(Eigen::Vector2d(1, 1));
71 mesh->createEdge(v1, v2);
72 return mesh;
73}
74
75PtrMesh vertexMesh3D()
76{
78 mesh->createVertex(Eigen::Vector3d(0, 0, 0));
79 mesh->createVertex(Eigen::Vector3d(0, 0, 1));
80 mesh->createVertex(Eigen::Vector3d(0, 1, 0));
81 mesh->createVertex(Eigen::Vector3d(0, 1, 1));
82 mesh->createVertex(Eigen::Vector3d(1, 0, 0));
83 mesh->createVertex(Eigen::Vector3d(1, 0, 1));
84 mesh->createVertex(Eigen::Vector3d(1, 1, 0));
85 mesh->createVertex(Eigen::Vector3d(1, 1, 1));
86 mesh->computeBoundingBox();
87 return mesh;
88}
89} // namespace
90
91BOOST_AUTO_TEST_SUITE(QueryTests)
92BOOST_AUTO_TEST_SUITE(MeshTests)
94
96{
97 PRECICE_TEST(1_rank);
98 auto mesh = edgeMesh2D();
99 Index indexTree(mesh);
100 Eigen::Vector2d location(0.2, 0.8);
101
102 auto result = indexTree.getClosestVertex(location);
103 BOOST_TEST(mesh->vertex(result.index).getCoords() == Eigen::Vector2d(0, 1));
104}
105
107{
108 PRECICE_TEST(1_rank);
109 auto mesh = edgeMesh3D();
110 Index indexTree(mesh);
111 Eigen::Vector3d location(0.8, 0.0, 0.8);
112
113 auto result = indexTree.getClosestVertex(location);
114 BOOST_TEST(mesh->vertex(result.index).getCoords() == Eigen::Vector3d(1, 0, 1));
115}
116
117BOOST_AUTO_TEST_CASE(Query3DFullVertex)
118{
119 PRECICE_TEST(1_rank);
121 const double z1 = 0.1;
122 const double z2 = -0.1;
123 auto & v00 = mesh->createVertex(Eigen::Vector3d(0, 0, 0));
124 auto & v01 = mesh->createVertex(Eigen::Vector3d(0, 1, 0));
125 auto & v10 = mesh->createVertex(Eigen::Vector3d(1, 0, z1));
126 auto & v11 = mesh->createVertex(Eigen::Vector3d(1, 1, z1));
127 auto & v20 = mesh->createVertex(Eigen::Vector3d(2, 0, z2));
128 auto & v21 = mesh->createVertex(Eigen::Vector3d(2, 1, z2));
129 auto & v30 = mesh->createVertex(Eigen::Vector3d(3, 0, z2));
130 auto & v31 = mesh->createVertex(Eigen::Vector3d(3, 1, z2));
131 auto & ell = mesh->createEdge(v00, v01);
132 auto & elt = mesh->createEdge(v01, v11);
133 auto & elr = mesh->createEdge(v11, v10);
134 auto & elb = mesh->createEdge(v10, v00);
135 auto & eld = mesh->createEdge(v00, v11);
136 auto & erl = elr;
137 auto & ert = mesh->createEdge(v11, v21);
138 auto & err = mesh->createEdge(v21, v20);
139 auto & erb = mesh->createEdge(v20, v10);
140 auto & erd = mesh->createEdge(v10, v21);
141 mesh->createTriangle(ell, elt, eld);
142 mesh->createTriangle(eld, elb, elr);
143 mesh->createTriangle(erl, ert, erd);
144 mesh->createTriangle(erd, erb, err);
145
146 Index indexTree(mesh);
147 {
148 Eigen::Vector3d location(0.8, 0.0, 0.8);
149 auto result = indexTree.getClosestVertex(location);
150
151 BOOST_TEST(mesh->vertex(result.index).getID() == v10.getID());
152 }
153 {
154 Eigen::Vector3d location(0.8, 0.0, 0.8);
155 int nVertices = 2;
156 std::vector<VertexID> expectedResult({v00.getID(), v10.getID()});
157 auto result = indexTree.getClosestVertices(location, nVertices);
158
159 BOOST_TEST(result.size() == nVertices);
160 BOOST_TEST(std::is_permutation(result.begin(), result.end(), expectedResult.begin()));
161 }
162 {
163 Eigen::Vector3d location(3.5, 3.5, 0.0);
164 int nVertices = 4;
165 std::vector<VertexID> expectedResult({v11.getID(), v30.getID(), v21.getID(), v31.getID()});
166 auto result = indexTree.getClosestVertices(location, nVertices);
167
168 BOOST_TEST(result.size() == nVertices);
169 BOOST_TEST(std::is_permutation(result.begin(), result.end(), expectedResult.begin()));
170 }
171}
172
174BOOST_AUTO_TEST_CASE(QueryWithBoxEmpty)
175{
176 PRECICE_TEST(1_rank);
177 auto mesh = vertexMesh3D();
178 Index indexTree(mesh);
179 mesh::Vertex searchVertex(Eigen::Vector3d(0.8, 1, 0), 0);
180 double radius = 0.1; // No vertices in radius
181
182 auto results = indexTree.getVerticesInsideBox(searchVertex, radius);
183 BOOST_TEST(results.empty());
184}
185
187BOOST_AUTO_TEST_CASE(QueryWithBox2Matches)
188{
189 PRECICE_TEST(1_rank);
190 auto mesh = vertexMesh3D();
191 Index indexTree(mesh);
192
193 mesh::Vertex searchVertex(Eigen::Vector3d(0.8, 1, 0), 0);
194 double radius = 0.81; // Two vertices in radius
195
196 auto results = indexTree.getVerticesInsideBox(searchVertex, radius);
197 BOOST_TEST(results.size() == 2);
198 BOOST_TEST(mesh->vertex(results.at(0)).getCoords() == Eigen::Vector3d(0, 1, 0));
199 BOOST_TEST(mesh->vertex(results.at(1)).getCoords() == Eigen::Vector3d(1, 1, 0));
200}
201
203BOOST_AUTO_TEST_CASE(QueryWithBoxEverything)
204{
205 PRECICE_TEST(1_rank);
206 auto mesh = vertexMesh3D();
207 Index indexTree(mesh);
208
209 mesh::Vertex searchVertex(Eigen::Vector3d(0.8, 1, 0), 0);
210 double radius = std::numeric_limits<double>::max();
211
212 auto results = indexTree.getVerticesInsideBox(searchVertex, radius);
213 BOOST_TEST(results.size() == 8);
214}
215
216BOOST_AUTO_TEST_CASE(QueryRtreeBoundingBox2D)
217{
218 PRECICE_TEST(1_rank);
219 auto mesh = edgeMesh2D();
220 auto result = mesh->index().getRtreeBounds();
221 mesh->computeBoundingBox();
222 auto comparison = mesh->getBoundingBox();
223
224 BOOST_TEST(result == comparison);
225 BOOST_TEST(result.minCorner() == Eigen::Vector2d(0, 0));
226 BOOST_TEST(result.maxCorner() == Eigen::Vector2d(1, 1));
227}
228
229BOOST_AUTO_TEST_CASE(QueryRtreeBoundingBox3D)
230{
231 PRECICE_TEST(1_rank);
232 auto mesh = vertexMesh3D();
233 auto result = mesh->index().getRtreeBounds();
234 mesh->computeBoundingBox();
235 auto comparison = mesh->getBoundingBox();
236
237 BOOST_TEST(result == comparison);
238 BOOST_TEST(result.minCorner() == Eigen::Vector3d(0, 0, 0));
239 BOOST_TEST(result.maxCorner() == Eigen::Vector3d(1, 1, 1));
240}
241
242BOOST_AUTO_TEST_CASE(QueryRtreeBoundingBox3DComplex)
243{
244 PRECICE_TEST(1_rank);
246 mesh->createVertex(Eigen::Vector3d(7, 4, 3.3));
247 mesh->createVertex(Eigen::Vector3d(26.4777, 5, 8));
248 mesh->createVertex(Eigen::Vector3d(-23.4, 100000.2, 7));
249 mesh->createVertex(Eigen::Vector3d(0.211, -21.37, 0.00003));
250 auto result = mesh->index().getRtreeBounds();
251 mesh->computeBoundingBox();
252 auto comparison = mesh->getBoundingBox();
253
254 BOOST_TEST(result == comparison);
255 BOOST_TEST(result.minCorner() == Eigen::Vector3d(-23.4, -21.37, 0.00003));
256 BOOST_TEST(result.maxCorner() == Eigen::Vector3d(26.4777, 100000.2, 8));
257}
258
260
262
264{
265 PRECICE_TEST(1_rank);
266 auto mesh = edgeMesh2D();
267 Index indexTree(mesh);
268 Eigen::Vector2d location(0.2, 0.8);
269
270 auto results = indexTree.getClosestEdges(location, 1);
271 BOOST_TEST(results.size() == 1);
272 auto &edge = mesh->edges().at(results.front().index);
273
274 BOOST_TEST(edge.vertex(0).getCoords() == Eigen::Vector2d(1, 0));
275 BOOST_TEST(edge.vertex(1).getCoords() == Eigen::Vector2d(1, 1));
276}
277
279{
280 PRECICE_TEST(1_rank);
281 auto mesh = edgeMesh3D();
282 Index indexTree(mesh);
283 Eigen::Vector3d location(1.8, 0.0, 0.8);
284
285 auto results = indexTree.getClosestEdges(location, 1);
286
287 BOOST_TEST(results.size() == 1);
288 auto match = results.front().index;
289
290 BOOST_TEST(match < mesh->edges().size());
291 auto & edge = mesh->edges().at(match);
292 Eigen::Vector3d p1(1, 1, 0);
293 Eigen::Vector3d p2(1, 1, 1);
294 BOOST_TEST((edge.vertex(0).getCoords() == p1 || edge.vertex(0).getCoords() == p2));
295 if (edge.vertex(0).getCoords() == p1) {
296 BOOST_TEST(edge.vertex(1).getCoords() == p2);
297 } else {
298 BOOST_TEST(edge.vertex(1).getCoords() == p1);
299 }
300}
301
302BOOST_AUTO_TEST_CASE(Query3DFullEdge)
303{
304 PRECICE_TEST(1_rank);
306 const double z1 = 0.1;
307 const double z2 = -0.1;
308 auto & v00 = mesh->createVertex(Eigen::Vector3d(0, 0, 0));
309 auto & v01 = mesh->createVertex(Eigen::Vector3d(0, 1, 0));
310 auto & v10 = mesh->createVertex(Eigen::Vector3d(1, 0, z1));
311 auto & v11 = mesh->createVertex(Eigen::Vector3d(1, 1, z1));
312 auto & v20 = mesh->createVertex(Eigen::Vector3d(2, 0, z2));
313 auto & v21 = mesh->createVertex(Eigen::Vector3d(2, 1, z2));
314 auto & ell = mesh->createEdge(v00, v01);
315 auto & elt = mesh->createEdge(v01, v11);
316 auto & elr = mesh->createEdge(v11, v10);
317 auto & elb = mesh->createEdge(v10, v00);
318 auto & eld = mesh->createEdge(v00, v11);
319 auto & erl = elr;
320 auto & ert = mesh->createEdge(v11, v21);
321 auto & err = mesh->createEdge(v21, v20);
322 auto & erb = mesh->createEdge(v20, v10);
323 auto & erd = mesh->createEdge(v10, v21);
324 mesh->createTriangle(ell, elt, eld);
325 mesh->createTriangle(eld, elb, elr);
326 mesh->createTriangle(erl, ert, erd);
327 mesh->createTriangle(erd, erb, err);
328
329 Index indexTree(mesh);
330 Eigen::Vector3d location(0.8, 0.5, 0.0);
331 auto results = indexTree.getClosestEdges(location, 2);
332
334 &mesh->edges().at(results.at(0).index),
335 &mesh->edges().at(results.at(1).index),
336 };
337 std::set<mesh::Edge *> expected{&elr, &eld};
338
339 BOOST_TEST(matches.size() == 2);
340 BOOST_TEST(matches == expected, boost::test_tools::per_element());
341}
342
344
346
347BOOST_AUTO_TEST_CASE(Query3DFullTriangle)
348{
349 PRECICE_TEST(1_rank);
350
352 const double z1 = 0.1;
353 const double z2 = -0.1;
354 auto & v00 = mesh->createVertex(Eigen::Vector3d(0, 0, 0));
355 auto & v01 = mesh->createVertex(Eigen::Vector3d(0, 1, 0));
356 auto & v10 = mesh->createVertex(Eigen::Vector3d(1, 0, z1));
357 auto & v11 = mesh->createVertex(Eigen::Vector3d(1, 1, z1));
358 auto & v20 = mesh->createVertex(Eigen::Vector3d(2, 0, z2));
359 auto & v21 = mesh->createVertex(Eigen::Vector3d(2, 1, z2));
360 auto & ell = mesh->createEdge(v00, v01);
361 auto & elt = mesh->createEdge(v01, v11);
362 auto & elr = mesh->createEdge(v11, v10);
363 auto & elb = mesh->createEdge(v10, v00);
364 auto & eld = mesh->createEdge(v00, v11);
365 auto & erl = elr;
366 auto & ert = mesh->createEdge(v11, v21);
367 auto & err = mesh->createEdge(v21, v20);
368 auto & erb = mesh->createEdge(v20, v10);
369 auto & erd = mesh->createEdge(v10, v21);
370 auto & tlt = mesh->createTriangle(ell, elt, eld);
371 auto & tlb = mesh->createTriangle(eld, elb, elr);
372 auto & trt = mesh->createTriangle(erl, ert, erd);
373 auto & trb = mesh->createTriangle(erd, erb, err);
374
375 Index indexTree(mesh);
376
377 Eigen::Vector3d location(0.7, 0.5, 0.0);
378
379 auto results = indexTree.getClosestTriangles(location, 3);
380 BOOST_TEST(results.size() == 3);
381
383 &mesh->triangles().at(results.at(0).index),
384 &mesh->triangles().at(results.at(1).index),
385 &mesh->triangles().at(results.at(2).index)};
386 std::set<mesh::Triangle *> expected{&tlb, &tlt, &trt};
387
388 BOOST_TEST(matches.size() == 3);
389 BOOST_TEST(matches == expected, boost::test_tools::per_element());
390}
391
392BOOST_AUTO_TEST_SUITE_END() // Triangle
393
394BOOST_AUTO_TEST_SUITE(Projection)
395
396BOOST_AUTO_TEST_CASE(ProjectionToVertex)
397{
398 PRECICE_TEST(1_rank);
399 auto meshPtr = fullMesh();
400 Index indexTree(meshPtr);
401
402 Eigen::Vector3d location(4.0, 0.0, 0.0);
403 std::vector<int> expectedIndices = {2};
404 std::vector<double> expectedWeights = {1.0};
405
406 auto match = indexTree.findNearestProjection(location, 1);
407
408 BOOST_TEST(match.polation.getWeightedElements().size() == 1); // Check number of weights
409 BOOST_TEST(match.polation.distance() == 1.0); // Check the distance
410 BOOST_TEST(match.polation.isInterpolation());
411
412 for (int i = 0; i < static_cast<int>(match.polation.getWeightedElements().size()); ++i) {
413 BOOST_TEST(match.polation.getWeightedElements().at(i).vertexID == expectedIndices.at(i)); // Check index
414 BOOST_TEST(match.polation.getWeightedElements().at(i).weight == expectedWeights.at(i)); // Check the weight
415 }
416}
417
418BOOST_AUTO_TEST_CASE(ProjectionToEdge)
419{
420 PRECICE_TEST(1_rank);
421 auto meshPtr = fullMesh();
422 Index indexTree(meshPtr);
423
424 Eigen::Vector3d location(2.0, -1.0, 0.0);
425 std::vector<int> expectedIndices = {2, 3};
426 std::vector<double> expectedWeights = {0.5, 0.5};
427
428 auto match = indexTree.findNearestProjection(location, 1);
429
430 BOOST_TEST(match.polation.getWeightedElements().size() == 2); // Check number of weights
431 BOOST_TEST(match.polation.distance() == 1.0); // Check the distance
432 BOOST_TEST(match.polation.isInterpolation());
433
434 for (int i = 0; i < static_cast<int>(match.polation.getWeightedElements().size()); ++i) {
435 BOOST_TEST(match.polation.getWeightedElements().at(i).vertexID == expectedIndices.at(i)); // Check index
436 BOOST_TEST(match.polation.getWeightedElements().at(i).weight == expectedWeights.at(i)); // Check the weight
437 }
438}
439
440BOOST_AUTO_TEST_CASE(ProjectionToTriangle)
441{
442 PRECICE_TEST(1_rank);
443 auto meshPtr = fullMesh();
444 Index indexTree(meshPtr);
445
446 Eigen::Vector3d location(1.0, 1.0, 0.1);
447 std::vector<int> expectedIndices = {0, 1, 3};
448 std::vector<double> expectedWeights = {1.0 / 3.0, 1.0 / 3.0, 1.0 / 3.0};
449
450 auto match = indexTree.findNearestProjection(location, 1);
451
452 BOOST_TEST(match.polation.getWeightedElements().size() == 3); // Check number of weights
453 BOOST_TEST(match.polation.distance() == 0.1); // Check the distance
454 BOOST_TEST(match.polation.isInterpolation());
455
456 for (int i = 0; i < static_cast<int>(match.polation.getWeightedElements().size()); ++i) {
457 BOOST_TEST(match.polation.getWeightedElements().at(i).vertexID == expectedIndices.at(i)); // Check index
458 BOOST_TEST(match.polation.getWeightedElements().at(i).weight == expectedWeights.at(i)); // Check the weight
459 }
460}
461
462BOOST_AUTO_TEST_SUITE_END() // Projection
463
464BOOST_AUTO_TEST_SUITE(Tetrahedra)
465
466BOOST_AUTO_TEST_CASE(CubeBoundingBoxIndex)
467{
468 PRECICE_TEST(1_rank);
469 PtrMesh ptr(new Mesh("MyMesh", 3, testing::nextMeshID()));
470 auto & mesh = *ptr;
471 Index indexTree(ptr);
472
473 Eigen::Vector3d location(0.5, 0.5, 0.5);
474 std::vector<int> expectedIndices = {0, 1};
475 // Set up 2 tetrahedra with the same bounding box
476 auto &v00 = mesh.createVertex(Eigen::Vector3d(0, 0, 0));
477 auto &v01 = mesh.createVertex(Eigen::Vector3d(1, 0, 0));
478 auto &v02 = mesh.createVertex(Eigen::Vector3d(0, 1, 0));
479 auto &v03 = mesh.createVertex(Eigen::Vector3d(1, 0, 1));
480 auto &v04 = mesh.createVertex(Eigen::Vector3d(1, 1, 1));
481
482 mesh.createTetrahedron(v00, v01, v02, v03);
483 mesh.createTetrahedron(v04, v01, v02, v03);
484
485 auto match = indexTree.getEnclosingTetrahedra(location);
486
487 BOOST_TEST(match.size() == 2);
488}
489
491{
492 /*
493 For a location and 3 tetrahedra such that:
494 - First contains the location
495 - Second doesn't, but its Bounding Box does
496 - Third doesn't and neither does its AABB
497 Check that only 1st and 2nd are found by getEnclosingTetrahedra
498 */
499 PRECICE_TEST(1_rank);
500 PtrMesh ptr(new Mesh("MyMesh", 3, testing::nextMeshID()));
501 auto & mesh = *ptr;
502 Index indexTree(ptr);
503
504 Eigen::Vector3d location(0.2, 0.2, 0.2);
505 std::vector<int> expectedIndices = {0, 1};
506
507 // Set containing tetra
508 auto &v00 = mesh.createVertex(Eigen::Vector3d(0, 0, 0));
509 auto &v01 = mesh.createVertex(Eigen::Vector3d(1, 0, 0));
510 auto &v02 = mesh.createVertex(Eigen::Vector3d(0, 1, 0));
511 auto &v03 = mesh.createVertex(Eigen::Vector3d(0, 0, 1));
512 mesh.createTetrahedron(v00, v01, v02, v03);
513
514 // Set non-containing tetra with containing BB (from 0 to 1 in each direction)
515 auto &v10 = mesh.createVertex(Eigen::Vector3d(1, 1, 1));
516 auto &v11 = mesh.createVertex(Eigen::Vector3d(1, 0, 0));
517 auto &v12 = mesh.createVertex(Eigen::Vector3d(0, 1, 0));
518 auto &v13 = mesh.createVertex(Eigen::Vector3d(0, 0, 1));
519 mesh.createTetrahedron(v10, v11, v12, v13);
520
521 // Set tetra far away
522 auto &v20 = mesh.createVertex(Eigen::Vector3d(1, 1, 1));
523 auto &v21 = mesh.createVertex(Eigen::Vector3d(2, 1, 1));
524 auto &v22 = mesh.createVertex(Eigen::Vector3d(1, 2, 1));
525 auto &v23 = mesh.createVertex(Eigen::Vector3d(1, 1, 2));
526 mesh.createTetrahedron(v20, v21, v22, v23);
527
528 auto match = indexTree.getEnclosingTetrahedra(location);
529
530 BOOST_TEST(match.size() == 2);
531 BOOST_TEST(((match[0] == 0 && match[1] == 1) || (match[0] == 1 && match[1] == 0)));
532}
533
534BOOST_AUTO_TEST_CASE(TetraWorksOnBoundary)
535{
536 /*
537 Check that the AABB safety factor is high enough. Do all the corners of a tetra fit inside its AABB?
538 */
539 PRECICE_TEST(1_rank);
540 PtrMesh ptr(new Mesh("MyMesh", 3, testing::nextMeshID()));
541 auto & mesh = *ptr;
542 Index indexTree(ptr);
543
545 locations.push_back(Eigen::Vector3d(0, 0, 0));
546 locations.push_back(Eigen::Vector3d(1, 0, 0));
547 locations.push_back(Eigen::Vector3d(0, 1, 0));
548 locations.push_back(Eigen::Vector3d(0, 0, 1));
549
550 // Set containing tetra
551 auto &v00 = mesh.createVertex(Eigen::Vector3d(0, 0, 0));
552 auto &v01 = mesh.createVertex(Eigen::Vector3d(1, 0, 0));
553 auto &v02 = mesh.createVertex(Eigen::Vector3d(0, 1, 0));
554 auto &v03 = mesh.createVertex(Eigen::Vector3d(0, 0, 1));
555 mesh.createTetrahedron(v00, v01, v02, v03);
556
557 for (const auto &vertex : locations) {
558 auto match = indexTree.getEnclosingTetrahedra(vertex);
559 BOOST_TEST(match.size() == 1);
560 }
561}
562
563BOOST_AUTO_TEST_SUITE_END() // Tetrahedra
564
double const * ptr
Definition ExportCSV.cpp:23
BOOST_AUTO_TEST_SUITE(PreProcess)
BOOST_AUTO_TEST_SUITE_END()
BOOST_AUTO_TEST_CASE(Query2DVertex)
#define PRECICE_TEST(...)
Definition Testing.hpp:27
T at(T... args)
T begin(T... args)
Linear edge of a mesh, defined by two Vertex objects.
Definition Edge.hpp:16
Container and creator for meshes.
Definition Mesh.hpp:39
Triangle & createTriangle(Edge &edgeOne, Edge &edgeTwo, Edge &edgeThree)
Creates and initializes a Triangle object.
Definition Mesh.cpp:119
Vertex & vertex(VertexID id)
Mutable access to a vertex by VertexID.
Definition Mesh.cpp:41
const query::Index & index() const
Call preprocess() before index() to ensure correct projection handling.
Definition Mesh.hpp:315
void computeBoundingBox()
Computes the boundingBox for the vertices.
Definition Mesh.cpp:242
TriangleContainer & triangles()
Returns modifiable container holding all triangles.
Definition Mesh.cpp:78
const BoundingBox & getBoundingBox() const
Returns the bounding box of the mesh.
Definition Mesh.cpp:365
Edge & createEdge(Vertex &vertexOne, Vertex &vertexTwo)
Creates and initializes an Edge object.
Definition Mesh.cpp:111
EdgeContainer & edges()
Returns modifiable container holding all edges.
Definition Mesh.cpp:68
Vertex & createVertex(const Eigen::VectorXd &coords)
Creates and initializes a Vertex object.
Definition Mesh.cpp:103
Triangle of a mesh, defined by three vertices.
Definition Triangle.hpp:27
Vertex of a mesh.
Definition Vertex.hpp:16
VertexID getID() const
Returns the unique (among vertices of one mesh on one processor) ID of the vertex.
Definition Vertex.hpp:111
Class to query the index trees of the mesh.
Definition Index.hpp:65
mesh::BoundingBox getRtreeBounds()
Definition Index.cpp:367
std::vector< TetrahedronID > getEnclosingTetrahedra(const Eigen::VectorXd &location)
Return all the tetrahedra whose axis-aligned bounding box contains a vertex.
Definition Index.cpp:263
VertexMatch getClosestVertex(const Eigen::VectorXd &sourceCoord)
Get the closest vertex to the given vertex.
Definition Index.cpp:171
ProjectionMatch findNearestProjection(const Eigen::VectorXd &location, int n)
Find the closest interpolation element to the given location. If exists, triangle or edge projection ...
Definition Index.cpp:275
std::vector< TriangleMatch > getClosestTriangles(const Eigen::VectorXd &sourceCoord, int n)
Get n number of closest triangles to the given vertex.
Definition Index.cpp:210
std::vector< VertexID > getVerticesInsideBox(const mesh::Vertex &centerVertex, double radius)
Return all the vertices inside the box formed by vertex and radius (boundary exclusive)
Definition Index.cpp:223
std::vector< VertexID > getClosestVertices(const Eigen::VectorXd &sourceCoord, int n)
Get n number of closest vertices to the given vertex.
Definition Index.cpp:184
std::vector< EdgeMatch > getClosestEdges(const Eigen::VectorXd &sourceCoord, int n)
Get n number of closest edges to the given vertex.
Definition Index.cpp:197
T end(T... args)
T is_permutation(T... args)
T max(T... args)
provides Mesh, Data and primitives.
contains geometrical queries.
Main namespace of the precice library.
T push_back(T... args)
T size(T... args)