10 #include "gtest/gtest.h" 14 #include "libmesh/face_tri3.h" 15 #include "libmesh/edge_edge2.h" 16 #include "libmesh/cell_tet4.h" 34 TEST(SBMBndElementTest, Edge2Normal)
38 std::unique_ptr<Node> n0(
new Node(
Point(0.0, 0.0, 0.0), 0));
39 std::unique_ptr<Node> n1(
new Node(
Point(1.0, 0.0, 0.0), 1));
41 edge->set_node(0) = n0.get();
42 edge->set_node(1) = n1.get();
45 Point n = bnd_edge.normal();
47 EXPECT_NEAR(n(0), 0.0, 1e-12);
48 EXPECT_NEAR(n(2), 0.0, 1e-12);
49 EXPECT_NEAR(std::abs(n(1)), 1.0, 1e-12);
55 EXPECT_TRUE(bnd_edge.intersect(line_segment_ab));
61 EXPECT_FALSE(bnd_edge.intersect(line_segment_cd));
64 Point pt(0.5, 1.0, 0.0);
65 Point dist = bnd_edge.distanceFrom(pt);
66 EXPECT_NEAR(dist(1), -1.0, 1e-12);
69 TEST(SBMBndElementTest, Tri3Normal)
71 std::unique_ptr<Tri3> tri(
new Tri3());
73 std::unique_ptr<Node> n0(
new Node(
Point(0.0, 0.0, 0.0), 0));
74 std::unique_ptr<Node> n1(
new Node(
Point(1.0, 0.0, 0.0), 1));
75 std::unique_ptr<Node> n2(
new Node(
Point(0.0, 1.0, 0.0), 2));
77 tri->set_node(0) = n0.get();
78 tri->set_node(1) = n1.get();
79 tri->set_node(2) = n2.get();
82 Point n = bnd_tri.normal();
84 EXPECT_NEAR(n(0), 0.0, 1e-12);
85 EXPECT_NEAR(n(1), 0.0, 1e-12);
86 EXPECT_NEAR(std::abs(n(2)), 1.0, 1e-12);
92 EXPECT_TRUE(bnd_tri.intersect(line_segment_ab));
98 EXPECT_FALSE(bnd_tri.intersect(line_segment_cd));
101 Point pt(0.3, 0.3, 1.0);
102 Point dist = bnd_tri.distanceFrom(pt);
103 EXPECT_NEAR(dist(2), -1.0, 1e-12);
106 TEST(SBMBndElementTest, Edge2NormalTilted)
108 std::unique_ptr<Edge2>
edge(
new Edge2());
110 std::unique_ptr<Node> n0(
new Node(
Point(0.0, 0.0, 0.0), 0));
111 std::unique_ptr<Node> n1(
new Node(
Point(1.0, 1.0, 0.0), 1));
113 edge->set_node(0) = n0.get();
114 edge->set_node(1) = n1.get();
117 Point n = bnd_edge.normal();
120 const double inv_sqrt2 = 1.0 / std::sqrt(2.0);
121 EXPECT_NEAR(n(0), -inv_sqrt2, 1e-12);
122 EXPECT_NEAR(n(1), inv_sqrt2, 1e-12);
123 EXPECT_NEAR(n(2), 0.0, 1e-12);
129 EXPECT_TRUE(bnd_edge.intersect(line_segment_ab));
135 EXPECT_FALSE(bnd_edge.intersect(line_segment_cd));
138 Point pt(0.5, 0.0, 0.0);
139 Point dist = bnd_edge.distanceFrom(pt);
141 double dot = dist(0) * n(0) + dist(1) * n(1);
145 TEST(SBMBndElementTest, Edge2DistanceNodeFallback)
150 std::unique_ptr<Edge2>
edge(
new Edge2());
151 std::unique_ptr<Node> n0(
new Node(
Point(0.0, 0.0, 0.0), 0));
152 std::unique_ptr<Node> n1(
new Node(
Point(1.0, 0.0, 0.0), 1));
153 edge->set_node(0) = n0.get();
154 edge->set_node(1) = n1.get();
160 Point pt(2.0, 1.0, 0.0);
161 Point dist = bnd_edge.distanceFrom(pt);
162 EXPECT_NEAR(dist(0), -1.0, 1e-12);
163 EXPECT_NEAR(dist(1), -1.0, 1e-12);
164 EXPECT_NEAR(dist(2), 0.0, 1e-12);
167 TEST(SBMBndElementTest, Tri3NormalTilted)
169 std::unique_ptr<Tri3> tri(
new Tri3());
171 std::unique_ptr<Node> n0(
new Node(
Point(0.0, 0.0, 0.0), 0));
172 std::unique_ptr<Node> n1(
new Node(
Point(1.0, 0.0, 1.0), 1));
173 std::unique_ptr<Node> n2(
new Node(
Point(0.0, 1.0, 1.0), 2));
175 tri->set_node(0) = n0.get();
176 tri->set_node(1) = n1.get();
177 tri->set_node(2) = n2.get();
180 Point n = bnd_tri.normal();
183 const double inv_sqrt3 = 1.0 / std::sqrt(3.0);
184 EXPECT_NEAR(n(0), -inv_sqrt3, 1e-12);
185 EXPECT_NEAR(n(1), -inv_sqrt3, 1e-12);
186 EXPECT_NEAR(n(2), inv_sqrt3, 1e-12);
192 EXPECT_TRUE(bnd_tri.intersect(line_segment_ab));
198 EXPECT_FALSE(bnd_tri.intersect(line_segment_cd));
201 Point pt(2.0, 0.0, 2.0);
202 Point dist = bnd_tri.distanceFrom(pt);
203 EXPECT_NEAR(dist(0), -1.0, 1e-12);
204 EXPECT_NEAR(dist(1), 0.0, 1e-12);
205 EXPECT_NEAR(dist(2), -1.0, 1e-12);
207 Point pt2(0.0, 0.0, 0.0);
208 Point dist2 = bnd_tri.distanceFrom(pt2);
209 EXPECT_NEAR(dist2(0), 0.0, 1e-12);
210 EXPECT_NEAR(dist2(1), 0.0, 1e-12);
211 EXPECT_NEAR(dist2(2), 0.0, 1e-12);
214 TEST(SBMBndElementTest, ProjectedBoundingBoxDiagonal)
221 std::unique_ptr<Tri3> tri(
new Tri3());
222 std::unique_ptr<Node> n0(
new Node(
Point(0.0, 0.0, 0.0), 0));
223 std::unique_ptr<Node> n1(
new Node(
Point(1.0, 0.0, 0.0), 1));
224 std::unique_ptr<Node> n2(
new Node(
Point(0.0, 1.0, 0.0), 2));
225 tri->set_node(0) = n0.get();
226 tri->set_node(1) = n1.get();
227 tri->set_node(2) = n2.get();
231 EXPECT_NEAR(bnd_tri.getProjectedBoundingBoxDiagonal(
Point(0.0, 0.0, 1.0) ),
235 const double inv_sqrt2 = 1.0 / std::sqrt(2.0);
237 bnd_tri.getProjectedBoundingBoxDiagonal(
Point(inv_sqrt2, inv_sqrt2, 0.0) ),
242 TEST(SBMBndElementTest, BaseDynamicDispatcherIntersectAndBoundingBall)
248 std::unique_ptr<Edge2>
edge(
new Edge2());
249 std::unique_ptr<Node> e0(
new Node(
Point(0.0, 0.0, 0.0), 0));
250 std::unique_ptr<Node> e1(
new Node(
Point(1.0, 0.0, 0.0), 1));
251 edge->set_node(0) = e0.get();
252 edge->set_node(1) = e1.get();
258 EXPECT_TRUE(edge_base.intersect(crossing));
259 EXPECT_FALSE(edge_base.intersect(parallel));
262 EXPECT_NEAR(edge_ball.center()(0), 0.5, 1e-12);
263 EXPECT_NEAR(edge_ball.radius(), 0.5, 1e-12);
265 std::unique_ptr<Tri3> tri(
new Tri3());
266 std::unique_ptr<Node> t0(
new Node(
Point(0.0, 0.0, 0.0), 0));
267 std::unique_ptr<Node> t1(
new Node(
Point(1.0, 0.0, 0.0), 1));
268 std::unique_ptr<Node> t2(
new Node(
Point(0.0, 1.0, 0.0), 2));
269 tri->set_node(0) = t0.get();
270 tri->set_node(1) = t1.get();
271 tri->set_node(2) = t2.get();
277 EXPECT_TRUE(tri_base.intersect(piercing));
278 EXPECT_FALSE(tri_base.intersect(missing));
281 EXPECT_GT(tri_ball.radius(), 0.0);
284 TEST(SBMBndElementTest, ConstructionRejectsUnsupportedSideType)
289 std::unique_ptr<Tet4> tet(
new Tet4());
290 std::unique_ptr<Node> n0(
new Node(
Point(0.0, 0.0, 0.0), 0));
291 std::unique_ptr<Node> n1(
new Node(
Point(1.0, 0.0, 0.0), 1));
292 std::unique_ptr<Node> n2(
new Node(
Point(0.0, 1.0, 0.0), 2));
293 std::unique_ptr<Node> n3(
new Node(
Point(0.0, 0.0, 1.0), 3));
294 tet->set_node(0) = n0.get();
295 tet->set_node(1) = n1.get();
296 tet->set_node(2) = n2.get();
297 tet->set_node(3) = n3.get();
305 catch (
const std::exception & e)
307 EXPECT_NE(std::string(e.what()).
find(
"unsupported side type"), std::string::npos);
314 TEST(SBMBndElementTest, UnsupportedGeometryDispatchersThrow)
319 std::unique_ptr<Edge2>
edge(
new Edge2());
320 std::unique_ptr<Node> n0(
new Node(
Point(0.0, 0.0, 0.0), 0));
321 std::unique_ptr<Node> n1(
new Node(
Point(1.0, 0.0, 0.0), 1));
322 edge->set_node(0) = n0.get();
323 edge->set_node(1) = n1.get();
334 base.intersect(line);
336 catch (
const std::exception & e)
338 EXPECT_NE(std::string(e.what()).
find(
"unsupported geometry type"), std::string::npos);
348 base.computeBoundingBall();
350 catch (
const std::exception & e)
352 EXPECT_NE(std::string(e.what()).
find(
"unsupported geometry type"), std::string::npos);
KOKKOS_INLINE_FUNCTION const T * find(const T &target, const T *const begin, const T *const end)
The following methods are specializations for using the Parallel::packed_range_* routines for a vecto...
Base class for SBM boundary elements.
SBMBndElementBase(const Elem *elem, const Point &normal)
Constructor takes a pointer to a boundary element and its precomputed unit normal.
Derived class for 3-node triangular elements (Tri3) Triangle is listed first so it is initialized bef...
Ball computeBoundingBall() const override
Derived class for 2-node edge elements LineSegment is listed first so it is initialized before SBMBnd...
TEST(SBMBndElementTest, Edge2Normal)