File indexing completed on 2026-05-27 07:24:21
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010 #include "detray/geometry/shapes/trapezoid2D.hpp"
0011
0012 #include "detray/definitions/units.hpp"
0013 #include "detray/geometry/concepts.hpp"
0014 #include "detray/geometry/mask.hpp"
0015
0016
0017 #include "detray/test/framework/types.hpp"
0018 #include "detray/test/utils/ratio_test.hpp"
0019
0020
0021 #include <gtest/gtest.h>
0022
0023 using namespace detray;
0024
0025 using test_algebra = test::algebra;
0026 using scalar = test::scalar;
0027 using point3 = test::point3;
0028
0029 constexpr scalar tol{1e-7f};
0030
0031
0032 GTEST_TEST(detray_masks, trapezoid2D) {
0033 static_assert(concepts::shape<trapezoid2D, test_algebra>);
0034 static_assert(concepts::planar_shape<trapezoid2D, test_algebra>);
0035
0036 point3 p2_in = {1.f, -0.5f, 0.f};
0037 point3 p2_edge = {2.5f, 1.f, 0.f};
0038 point3 p2_out = {3.f, 1.5f, 0.f};
0039
0040 constexpr scalar hx_miny{1.f * unit<scalar>::mm};
0041 constexpr scalar hx_maxy{3.f * unit<scalar>::mm};
0042 constexpr scalar hy{2.f * unit<scalar>::mm};
0043 constexpr scalar divisor{1.f / (2.f * hy)};
0044
0045 mask<trapezoid2D, test_algebra> t2{0u, hx_miny, hx_maxy, hy, divisor};
0046
0047 ASSERT_NEAR(t2[trapezoid2D::e_half_length_0], hx_miny, tol);
0048 ASSERT_NEAR(t2[trapezoid2D::e_half_length_1], hx_maxy, tol);
0049 ASSERT_NEAR(t2[trapezoid2D::e_half_length_2], hy, tol);
0050 ASSERT_NEAR(t2[trapezoid2D::e_divisor], divisor, tol);
0051
0052 ASSERT_TRUE(t2.is_inside(p2_in));
0053 ASSERT_TRUE(t2.is_inside(p2_edge));
0054 ASSERT_FALSE(t2.is_inside(p2_out));
0055
0056
0057
0058 const scalar a{t2.area()};
0059 EXPECT_NEAR(a, 16.f * unit<scalar>::mm2, tol);
0060 ASSERT_EQ(a, t2.measure());
0061
0062
0063 constexpr scalar envelope{0.01f};
0064 const auto loc_bounds = t2.local_min_bounds(envelope);
0065 ASSERT_NEAR(loc_bounds[cuboid3D::e_min_x], -(hx_maxy + envelope), tol);
0066 ASSERT_NEAR(loc_bounds[cuboid3D::e_min_y], -(hy + envelope), tol);
0067 ASSERT_NEAR(loc_bounds[cuboid3D::e_min_z], -envelope, tol);
0068 ASSERT_NEAR(loc_bounds[cuboid3D::e_max_x], (hx_maxy + envelope), tol);
0069 ASSERT_NEAR(loc_bounds[cuboid3D::e_max_y], (hy + envelope), tol);
0070 ASSERT_NEAR(loc_bounds[cuboid3D::e_max_z], envelope, tol);
0071
0072 const auto centroid = t2.centroid();
0073 ASSERT_NEAR(centroid[0], 0.f, tol);
0074 ASSERT_NEAR(centroid[1], 1.f / 3.f, tol);
0075 ASSERT_NEAR(centroid[2], 0.f, tol);
0076 }
0077
0078
0079 GTEST_TEST(detray_masks, trapezoid2D_ratio_test) {
0080 struct mask_check {
0081 bool operator()(const point3 &p, const mask<trapezoid2D, test_algebra> &tp,
0082 const test::transform3 &trf, const scalar t) {
0083 return tp.is_inside(trf, p, t);
0084 }
0085 };
0086
0087 constexpr mask<trapezoid2D, test_algebra> tp{0u, 2.f, 3.f, 4.f,
0088 1.f / (2.f * 4.f)};
0089
0090 constexpr scalar t{0.f};
0091 const test::transform3 trf{};
0092 constexpr scalar size{10.f * unit<scalar>::mm};
0093 const auto n_points{static_cast<std::size_t>(std::pow(500, 3))};
0094
0095
0096 std::vector<point3> points =
0097 test::generate_regular_points<cuboid3D>(n_points, {size});
0098
0099 scalar ratio = test::ratio_test<mask_check>(points, tp, trf, t);
0100
0101 const scalar area{tp.measure()};
0102 const scalar world{size * size};
0103
0104 ASSERT_NEAR(ratio, area / world, 0.004f);
0105 }