File indexing completed on 2026-05-27 07:23:59
0001
0002
0003
0004
0005
0006
0007
0008
0009 #pragma once
0010
0011
0012 #include "detray/definitions/algebra.hpp"
0013 #include "detray/definitions/containers.hpp"
0014 #include "detray/definitions/detail/qualifiers.hpp"
0015 #include "detray/definitions/indexing.hpp"
0016 #include "detray/definitions/math.hpp"
0017 #include "detray/geometry/coordinates/cartesian2D.hpp"
0018 #include "detray/geometry/coordinates/cartesian3D.hpp"
0019 #include "detray/geometry/detail/shape_utils.hpp"
0020
0021
0022 #include <limits>
0023 #include <ostream>
0024 #include <string_view>
0025
0026 namespace detray {
0027
0028
0029
0030
0031
0032 template <unsigned int kCheckIndex = 0u>
0033 class single3D {
0034 public:
0035
0036 static constexpr std::string_view name = "single3D";
0037
0038 enum boundaries : unsigned int {
0039 e_lower = 0u,
0040 e_upper = 1u,
0041 e_size = 2u,
0042 };
0043
0044
0045 template <concepts::scalar scalar_t>
0046 using bounds_type = darray<scalar_t, boundaries::e_size>;
0047
0048
0049 template <concepts::algebra algebra_t>
0050 using local_frame_type = cartesian2D<algebra_t>;
0051
0052
0053 template <typename bool_t>
0054 using result_type = detail::boundary_check_result<bool_t>;
0055
0056
0057 static constexpr std::size_t dim{1u};
0058
0059
0060
0061
0062
0063
0064
0065
0066
0067
0068 template <concepts::scalar scalar_t, concepts::point point_t>
0069 DETRAY_HOST_DEVICE inline scalar_t min_dist_to_boundary(
0070 const bounds_type<scalar_t> &bounds, const point_t &loc_p) const {
0071 return math::min(math::fabs(loc_p[kCheckIndex] - bounds[e_lower]),
0072 math::fabs(bounds[e_upper] - loc_p[kCheckIndex]));
0073 }
0074
0075
0076
0077
0078
0079
0080
0081
0082
0083
0084 template <concepts::algebra algebra_t>
0085 DETRAY_HOST_DEVICE constexpr result_type<dbool<algebra_t>> check_boundaries(
0086 const bounds_type<dscalar<algebra_t>> &bounds,
0087 const dtransform3D<algebra_t> &trf, const dpoint3D<algebra_t> &glob_p,
0088 const dscalar<algebra_t> tol =
0089 std::numeric_limits<dscalar<algebra_t>>::epsilon(),
0090 const dscalar<algebra_t> edge_tol = 0.f) const {
0091
0092 const dpoint3D<algebra_t> loc_p =
0093 cartesian3D<algebra_t>::global_to_local(trf, glob_p, {});
0094
0095 return check_boundaries(bounds, loc_p, tol, edge_tol);
0096 }
0097
0098
0099
0100
0101
0102
0103
0104
0105
0106
0107 template <concepts::scalar scalar_t, concepts::point point_t>
0108 DETRAY_HOST_DEVICE constexpr auto check_boundaries(
0109 const bounds_type<scalar_t> &bounds, const point_t &loc_p,
0110 const scalar_t tol = std::numeric_limits<scalar_t>::epsilon(),
0111 const scalar_t edge_tol = 0.f) const {
0112 auto inside_mask{(bounds[e_lower] - tol <= loc_p[kCheckIndex] &&
0113 loc_p[kCheckIndex] <= bounds[e_upper] + tol)};
0114
0115 decltype(inside_mask) inside_edge{false};
0116 if (detail::any_of(edge_tol > 0.f)) {
0117 const scalar_t full_tol{tol + edge_tol};
0118
0119 inside_edge = (bounds[e_lower] - full_tol <= loc_p[kCheckIndex] &&
0120 loc_p[kCheckIndex] <= bounds[e_upper] + full_tol);
0121 }
0122
0123 return result_type<decltype(inside_mask)>{inside_mask, inside_edge};
0124 }
0125
0126
0127
0128
0129
0130
0131
0132 template <concepts::scalar scalar_t>
0133 DETRAY_HOST_DEVICE constexpr scalar_t measure(
0134 const bounds_type<scalar_t> &bounds) const {
0135 return area(bounds);
0136 }
0137
0138
0139
0140
0141
0142
0143 template <concepts::scalar scalar_t>
0144 DETRAY_HOST_DEVICE constexpr scalar_t area(
0145 const bounds_type<scalar_t> &bounds) const {
0146 return math::fabs(bounds[e_upper] - bounds[e_lower]);
0147 }
0148
0149
0150
0151
0152
0153
0154
0155 template <concepts::scalar scalar_t>
0156 DETRAY_HOST_DEVICE constexpr bounds_type<scalar_t> merge(
0157 const bounds_type<scalar_t> &bounds,
0158 const bounds_type<scalar_t> &o_bounds) const {
0159 bounds_type<scalar_t> new_bounds{};
0160
0161 new_bounds[e_lower] = math::min(bounds[e_lower], o_bounds[e_lower]);
0162 new_bounds[e_upper] = math::max(bounds[e_upper], o_bounds[e_upper]);
0163
0164 return new_bounds;
0165 }
0166
0167
0168
0169
0170
0171
0172
0173
0174
0175
0176 template <concepts::algebra algebra_t>
0177 DETRAY_HOST_DEVICE inline darray<dscalar<algebra_t>, 6> local_min_bounds(
0178 const bounds_type<dscalar<algebra_t>> &bounds,
0179 const dscalar<algebra_t> env =
0180 std::numeric_limits<dscalar<algebra_t>>::epsilon()) const {
0181 assert(env > 0.f);
0182 darray<dscalar<algebra_t>, 6> o_bounds{-env, -env, -env, env, env, env};
0183 o_bounds[kCheckIndex] += bounds[e_lower];
0184 o_bounds[3u + kCheckIndex] += bounds[e_upper];
0185 return o_bounds;
0186 }
0187
0188
0189 template <concepts::algebra algebra_t>
0190 DETRAY_HOST_DEVICE auto centroid(
0191 const bounds_type<dscalar<algebra_t>> &bounds) const {
0192 using point3_t = dpoint3D<algebra_t>;
0193
0194 point3_t centr{0.f, 0.f, 0.f};
0195 centr[kCheckIndex] = 0.5f * (bounds[e_lower] + bounds[e_upper]);
0196
0197 return centr;
0198 }
0199
0200
0201
0202
0203
0204
0205
0206 template <concepts::algebra algebra_t>
0207 DETRAY_HOST dvector<dpoint3D<algebra_t>> vertices(
0208 const bounds_type<dscalar<algebra_t>> & ,
0209 dindex ) const {
0210 throw std::runtime_error(
0211 "Vertex generation for single value shapes is not implemented");
0212 return {};
0213 }
0214
0215
0216
0217
0218
0219
0220
0221 template <concepts::scalar scalar_t>
0222 DETRAY_HOST constexpr bool check_consistency(
0223 const bounds_type<scalar_t> &bounds, std::ostream &os) const {
0224 if (bounds[e_upper] < bounds[e_lower]) {
0225 os << "DETRAY ERROR (HOST): Upper bounds must be smaller than "
0226 "lower bounds ";
0227 return false;
0228 }
0229
0230 return true;
0231 }
0232 };
0233
0234 }