Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-10-25 07:56:55

0001 // This file is part of the ACTS project.
0002 //
0003 // Copyright (C) 2016 CERN for the benefit of the ACTS project
0004 //
0005 // This Source Code Form is subject to the terms of the Mozilla Public
0006 // License, v. 2.0. If a copy of the MPL was not distributed with this
0007 // file, You can obtain one at https://mozilla.org/MPL/2.0/.
0008 
0009 #include <boost/test/unit_test.hpp>
0010 #include <boost/test/unit_test_suite.hpp>
0011 
0012 #include "Acts/Definitions/Algebra.hpp"
0013 #include "Acts/Definitions/Units.hpp"
0014 #include "Acts/Geometry/CylinderVolumeBounds.hpp"
0015 #include "Acts/Geometry/GridPortalLink.hpp"
0016 #include "Acts/Geometry/Portal.hpp"
0017 #include "Acts/Geometry/TrackingVolume.hpp"
0018 #include "Acts/Geometry/TrapezoidPortalShell.hpp"
0019 #include "Acts/Geometry/TrapezoidVolumeBounds.hpp"
0020 #include "Acts/Geometry/TrivialPortalLink.hpp"
0021 #include "Acts/Utilities/AxisDefinitions.hpp"
0022 
0023 using namespace Acts;
0024 using namespace Acts::UnitLiterals;
0025 
0026 namespace ActsTests {
0027 
0028 GeometryContext gctx;
0029 
0030 std::size_t getVolumeIndex() {
0031   static std::size_t i = 1;
0032   return i++;
0033 }
0034 
0035 auto makeVolume(auto&&... pars) {
0036   TrackingVolume vol(Transform3::Identity(),
0037                      std::make_shared<TrapezoidVolumeBounds>(
0038                          std::forward<decltype(pars)>(pars)...));
0039   vol.setVolumeName("trapezoid" + std::to_string(getVolumeIndex()));
0040   return vol;
0041 };
0042 
0043 auto logger = getDefaultLogger("UnitTests", Logging::VERBOSE);
0044 
0045 BOOST_AUTO_TEST_SUITE(GeometrySuite)
0046 
0047 BOOST_AUTO_TEST_CASE(ConstructionFromVolume) {
0048   // construct a trapezoid tracking volume from which we are gonna build the
0049   // shell
0050   auto trapVol = makeVolume(20_cm, 10_cm, 15_cm, 15_cm);
0051 
0052   // check if indeed invalid for no trapezoid volume
0053 
0054   TrackingVolume cylVolume(
0055       Transform3::Identity(),
0056       std::make_shared<CylinderVolumeBounds>(10_mm, 20_mm, 10_mm));
0057 
0058   BOOST_CHECK_THROW(SingleTrapezoidPortalShell{cylVolume},
0059                     std::invalid_argument);
0060 
0061   SingleTrapezoidPortalShell trapShell{trapVol};
0062 
0063   // check if the shell is valid and has the expected number of portals
0064   BOOST_CHECK(trapShell.isValid());
0065   BOOST_CHECK_EQUAL(trapShell.size(), 6);
0066 
0067   // check if the portals are consistent with their orientation in the shell and
0068   // find the linked volume
0069   using enum TrapezoidVolumeBounds::Face;
0070 
0071   // check XY face in negative Z
0072   const auto* nXY = trapShell.portal(NegativeZFaceXY);
0073 
0074   BOOST_REQUIRE_NE(nXY, nullptr);
0075   BOOST_CHECK_EQUAL(
0076       nXY->resolveVolume(gctx, Vector3{5_cm, 10_cm, -15_cm}, Vector3::UnitZ())
0077           .value(),
0078       &trapVol);
0079   BOOST_CHECK_EQUAL(
0080       nXY->resolveVolume(gctx, Vector3{5_cm, 10_cm, -15_cm}, -Vector3::UnitZ())
0081           .value(),
0082       nullptr);
0083 
0084   // check XY face in positive Z
0085   const auto* pXY = trapShell.portal(PositiveZFaceXY);
0086 
0087   BOOST_REQUIRE_NE(pXY, nullptr);
0088 
0089   BOOST_CHECK_EQUAL(
0090       pXY->resolveVolume(gctx, Vector3{5_cm, 10_cm, 15_cm}, -Vector3::UnitZ())
0091           .value(),
0092       &trapVol);
0093   BOOST_CHECK_EQUAL(
0094       pXY->resolveVolume(gctx, Vector3{5_cm, 10_cm, 15_cm}, Vector3::UnitZ())
0095           .value(),
0096       nullptr);
0097 
0098   // check the trapezoidAlpha face placed in negative X
0099   const auto* nYZ = trapShell.portal(TrapezoidFaceAlpha);
0100   BOOST_REQUIRE_NE(nYZ, nullptr);
0101   BOOST_CHECK_EQUAL(
0102       nYZ->resolveVolume(gctx, Vector3{-15_cm, 0_cm, 0_cm}, Vector3::UnitX())
0103           .value(),
0104       &trapVol);
0105   BOOST_CHECK_EQUAL(
0106       nYZ->resolveVolume(gctx, Vector3{-15_cm, 0_cm, 0_cm}, -Vector3::UnitX())
0107           .value(),
0108       nullptr);
0109 
0110   // check the trapezoidBeta face placed in positive x
0111   const auto* pYZ = trapShell.portal(TrapezoidFaceBeta);
0112   BOOST_REQUIRE_NE(pYZ, nullptr);
0113   BOOST_CHECK_EQUAL(
0114       pYZ->resolveVolume(gctx, Vector3{15_cm, 0_cm, 0_cm}, -Vector3::UnitX())
0115           .value(),
0116       &trapVol);
0117   BOOST_CHECK_EQUAL(
0118       pYZ->resolveVolume(gctx, Vector3{15_cm, 0_cm, 0_cm}, Vector3::UnitX())
0119           .value(),
0120       nullptr);
0121 
0122   // check the ZX face in negative y
0123   const auto* nZX = trapShell.portal(NegativeYFaceZX);
0124   BOOST_CHECK_NE(nZX, nullptr);
0125   BOOST_CHECK_EQUAL(
0126       nZX->resolveVolume(gctx, Vector3{0_cm, -15_cm, 0_cm}, Vector3::UnitY())
0127           .value(),
0128       &trapVol);
0129   BOOST_CHECK_EQUAL(
0130       nZX->resolveVolume(gctx, Vector3{0_cm, -15_cm, 0_cm}, -Vector3::UnitY())
0131           .value(),
0132       nullptr);
0133 
0134   // check the ZX face in positive y
0135   const auto* pZX = trapShell.portal(PositiveYFaceZX);
0136   BOOST_CHECK_NE(pZX, nullptr);
0137   BOOST_CHECK_EQUAL(
0138       pZX->resolveVolume(gctx, Vector3{0_cm, 15_cm, 0_cm}, -Vector3::UnitY())
0139           .value(),
0140       &trapVol);
0141   BOOST_CHECK_EQUAL(
0142       pZX->resolveVolume(gctx, Vector3{0_cm, 15_cm, 0_cm}, Vector3::UnitY())
0143           .value(),
0144       nullptr);
0145 }
0146 
0147 BOOST_AUTO_TEST_CASE(PortalAssignment) {
0148   using enum TrapezoidVolumeBounds::Face;
0149 
0150   // make a trapezoid volume
0151   auto trapVol = makeVolume(5_cm, 8_cm, 10_cm, 15_cm);
0152 
0153   SingleTrapezoidPortalShell trapShell{trapVol};
0154 
0155   // get the portal faces
0156   const auto* nXY = trapShell.portal(NegativeZFaceXY);
0157   const auto* pXY = trapShell.portal(PositiveZFaceXY);
0158 
0159   const auto* nYZ = trapShell.portal(TrapezoidFaceAlpha);
0160   const auto* pYZ = trapShell.portal(TrapezoidFaceBeta);
0161 
0162   auto* nZX = trapShell.portal(NegativeYFaceZX);
0163   auto* pZX = trapShell.portal(PositiveYFaceZX);
0164 
0165   // setting new portals for NegativeYFaceZX and PositiveYFaceZX faces
0166   BOOST_REQUIRE_NE(nZX, nullptr);
0167   BOOST_REQUIRE_NE(pZX, nullptr);
0168 
0169   auto* pZXLink = dynamic_cast<const TrivialPortalLink*>(
0170       pZX->getLink(Direction::OppositeNormal()));
0171   BOOST_REQUIRE_NE(pZXLink, nullptr);
0172 
0173   auto grid = pZXLink->makeGrid(AxisDirection::AxisY);
0174 
0175   auto newPortalPZX =
0176       std::make_shared<Portal>(Direction::OppositeNormal(), std::move(grid));
0177   trapShell.setPortal(newPortalPZX, PositiveYFaceZX);
0178   BOOST_CHECK_EQUAL(trapShell.portal(PositiveYFaceZX), newPortalPZX.get());
0179 
0180   auto* nZXLink = dynamic_cast<const TrivialPortalLink*>(
0181       nZX->getLink(Direction::AlongNormal()));
0182   BOOST_REQUIRE_NE(nZXLink, nullptr);
0183 
0184   grid = nZXLink->makeGrid(AxisDirection::AxisY);
0185 
0186   auto newPortalNZX =
0187       std::make_shared<Portal>(Direction::AlongNormal(), std::move(grid));
0188   trapShell.setPortal(newPortalNZX, NegativeYFaceZX);
0189   BOOST_CHECK_EQUAL(trapShell.portal(NegativeYFaceZX), newPortalNZX.get());
0190 
0191   // check the other portals
0192   BOOST_CHECK_EQUAL(trapShell.portal(NegativeZFaceXY), nXY);
0193   BOOST_CHECK_EQUAL(trapShell.portal(PositiveZFaceXY), pXY);
0194   BOOST_CHECK_EQUAL(trapShell.portal(TrapezoidFaceAlpha), nYZ);
0195   BOOST_CHECK_EQUAL(trapShell.portal(TrapezoidFaceBeta), pYZ);
0196 }
0197 
0198 BOOST_AUTO_TEST_CASE(Fill) {
0199   using enum TrapezoidVolumeBounds::Face;
0200 
0201   auto trapVol = makeVolume(5_cm, 10_cm, 10_cm, 10_cm);
0202 
0203   SingleTrapezoidPortalShell trapShell{trapVol};
0204 
0205   // without filling the shell with the volume the portal link to this direction
0206   // should not exist
0207   BOOST_CHECK_EQUAL(
0208       trapShell.portal(NegativeZFaceXY)->getLink(Direction::OppositeNormal()),
0209       nullptr);
0210 
0211   // create a volume nexto to the previous one and fill the shell with the new
0212   // volume to fill the available slots of the shell
0213   TrackingVolume trapVol2(
0214       Transform3::Identity() * Translation3(Vector3::UnitZ() * 15_cm),
0215       std::make_shared<TrapezoidVolumeBounds>(5_cm, 10_cm, 10_cm, 5_cm),
0216       "trapVol2");
0217 
0218   trapShell.fill(trapVol2);
0219 
0220   BOOST_CHECK_NE(
0221       trapShell.portal(NegativeZFaceXY)->getLink(Direction::OppositeNormal()),
0222       nullptr);
0223 }
0224 
0225 BOOST_AUTO_TEST_CASE(ApplyToVolume) {
0226   using enum TrapezoidVolumeBounds::Face;
0227 
0228   auto trapVol = makeVolume(5_cm, 10_cm, 10_cm, 10_cm);
0229 
0230   SingleTrapezoidPortalShell trapShell{trapVol};
0231 
0232   // volume has not portals assigned yet
0233   BOOST_CHECK_EQUAL(trapVol.portals().size(), 0);
0234 
0235   trapShell.applyToVolume();
0236 
0237   // now volume should have its portals
0238   BOOST_CHECK_EQUAL(trapVol.portals().size(), 6);
0239 }
0240 
0241 BOOST_AUTO_TEST_SUITE_END()
0242 
0243 }  // namespace ActsTests