File indexing completed on 2025-10-27 07:57:31
0001
0002
0003
0004
0005
0006
0007
0008
0009 #include <boost/test/unit_test.hpp>
0010
0011 #include "Acts/Definitions/Algebra.hpp"
0012 #include "Acts/Detector/ProtoDetector.hpp"
0013 #include "Acts/Geometry/Extent.hpp"
0014 #include "Acts/Surfaces/Surface.hpp"
0015 #include "Acts/Utilities/BinningData.hpp"
0016 #include "Acts/Utilities/BinningType.hpp"
0017 #include "Acts/Utilities/Enumerate.hpp"
0018 #include "ActsPlugins/Json/ProtoDetectorJsonConverter.hpp"
0019 #include "ActsPlugins/Json/SurfaceJsonConverter.hpp"
0020
0021 #include <array>
0022 #include <cmath>
0023 #include <fstream>
0024 #include <iterator>
0025 #include <numbers>
0026 #include <optional>
0027 #include <string>
0028 #include <vector>
0029
0030 #include <nlohmann/json.hpp>
0031
0032 #include "EqualityHelpers.hpp"
0033
0034 using namespace Acts;
0035
0036 namespace ActsTests {
0037
0038
0039
0040
0041
0042
0043 bool isEqual(const ProtoVolume& one, const ProtoVolume& two,
0044 const double tolerance = 0.) {
0045 bool nameEq = (one.name == two.name);
0046
0047 BOOST_CHECK(nameEq);
0048
0049 bool extentEq = isEqual(one.extent, two.extent, tolerance);
0050 BOOST_CHECK(extentEq);
0051
0052
0053 bool internalValueEq = (one.internal.has_value() == two.internal.has_value());
0054 BOOST_CHECK(internalValueEq);
0055 bool internalEq = internalValueEq;
0056 if (one.internal.has_value() && two.internal.has_value()) {
0057
0058 const auto& itsOne = one.internal.value();
0059 const auto& itsTwo = two.internal.value();
0060 bool layerTypeEq = (itsOne.layerType == itsTwo.layerType);
0061 BOOST_CHECK(layerTypeEq);
0062 internalEq = layerTypeEq;
0063 bool sBinningSizeEq =
0064 (itsOne.surfaceBinning.size() == itsTwo.surfaceBinning.size());
0065 BOOST_CHECK(sBinningSizeEq);
0066 internalEq = internalEq && sBinningSizeEq;
0067 for (auto [isb, sb] : enumerate(itsOne.surfaceBinning)) {
0068 bool sBinningEq = isEqual(sb, itsTwo.surfaceBinning[isb], tolerance);
0069 BOOST_CHECK(sBinningEq);
0070 internalEq = internalEq && sBinningEq;
0071 }
0072 }
0073 BOOST_CHECK(internalEq);
0074
0075
0076 bool containerValueEq =
0077 (one.container.has_value() == two.container.has_value());
0078 BOOST_CHECK(containerValueEq);
0079 bool containerEq = containerValueEq;
0080 if (one.container.has_value() && two.container.has_value()) {
0081
0082 const auto& ctsOne = one.container.value();
0083 const auto& ctsTwo = two.container.value();
0084 bool layerContainerEq = (ctsOne.layerContainer == ctsTwo.layerContainer);
0085 BOOST_CHECK(layerContainerEq);
0086 containerEq = layerContainerEq;
0087 bool cBinningSizeEq =
0088 ctsOne.constituentBinning.size() == ctsTwo.constituentBinning.size();
0089 containerEq = containerEq && cBinningSizeEq;
0090 BOOST_CHECK(cBinningSizeEq);
0091 for (auto [icb, cb] : enumerate(ctsOne.constituentBinning)) {
0092 bool cBinningEq = isEqual(cb, ctsTwo.constituentBinning[icb], tolerance);
0093 BOOST_CHECK(cBinningEq);
0094 containerEq = containerEq && cBinningEq;
0095 }
0096
0097 bool cSizeEq =
0098 (ctsOne.constituentVolumes.size() == ctsTwo.constituentVolumes.size());
0099 BOOST_CHECK(cSizeEq);
0100 containerEq = cSizeEq;
0101 for (auto [ic, cOne] : enumerate(ctsOne.constituentVolumes)) {
0102 const auto& cTwo = ctsTwo.constituentVolumes[ic];
0103 bool cEq = isEqual(cOne, cTwo, tolerance);
0104 BOOST_CHECK(cEq);
0105 containerEq = containerEq && cEq;
0106 }
0107 }
0108 BOOST_CHECK(containerEq);
0109
0110
0111 return nameEq && extentEq && internalEq && containerEq;
0112 }
0113
0114 BOOST_AUTO_TEST_SUITE(JsonSuite)
0115
0116 BOOST_AUTO_TEST_CASE(ProtoDetectorRoundTrip) {
0117 ExtentEnvelope cylinderLayerEnvelope = ExtentEnvelope::Zero();
0118 cylinderLayerEnvelope[AxisDirection::AxisR] = {1., 1.};
0119 cylinderLayerEnvelope[AxisDirection::AxisZ] = {2., 2.};
0120
0121 ExtentEnvelope discLayerEnvelope = ExtentEnvelope::Zero();
0122 discLayerEnvelope[AxisDirection::AxisR] = {1., 1.};
0123 discLayerEnvelope[AxisDirection::AxisZ] = {1., 1.};
0124
0125
0126 ProtoVolume beamPipeContainer;
0127 beamPipeContainer.name = "odd-beam-pipe";
0128 beamPipeContainer.extent.set(AxisDirection::AxisR, 0., 25);
0129 ProtoVolume beamPipe;
0130 beamPipe.name = "odd-beam-pipe-l";
0131 beamPipe.extent.set(AxisDirection::AxisR, 2., 24.);
0132 beamPipe.internal =
0133 ProtoVolume::InternalStructure{Surface::SurfaceType::Cylinder};
0134 beamPipeContainer.container = ProtoVolume::ContainerStructure{
0135 {beamPipe}, {BinningData(open, AxisDirection::AxisR, {0., 1.})}, true};
0136
0137
0138 ProtoVolume pixelContainer;
0139 pixelContainer.name = "odd-pixel";
0140 pixelContainer.extent.set(AxisDirection::AxisR, 25., 200);
0141
0142 ProtoVolume pixelNec;
0143 pixelNec.name = "odd-pixel-nec";
0144 pixelNec.extent.set(AxisDirection::AxisZ, -3100., -580);
0145
0146 ProtoVolume pixNecD6;
0147 pixNecD6.name = "odd-pixel-nec-d6";
0148 pixNecD6.extent.set(AxisDirection::AxisZ, -1540., -1500);
0149 ProtoVolume pixNecD5;
0150 pixNecD5.name = "odd-pixel-nec-d5";
0151 pixNecD5.extent.set(AxisDirection::AxisZ, -1340., -1300);
0152 ProtoVolume pixNecD4;
0153 pixNecD4.name = "odd-pixel-nec-d4";
0154 pixNecD4.extent.set(AxisDirection::AxisZ, -1140., -1100);
0155 ProtoVolume pixNecD3;
0156 pixNecD3.name = "odd-pixel-nec-d3";
0157 pixNecD3.extent.set(AxisDirection::AxisZ, -1000., -960.);
0158 ProtoVolume pixNecD2;
0159 pixNecD2.name = "odd-pixel-nec-d2";
0160 pixNecD2.extent.set(AxisDirection::AxisZ, -860., -820);
0161 ProtoVolume pixNecD1;
0162 pixNecD1.name = "odd-pixel-nec-d1";
0163 pixNecD1.extent.set(AxisDirection::AxisZ, -740., -700);
0164 ProtoVolume pixNecD0;
0165 pixNecD0.name = "odd-pixel-nec-d0";
0166 pixNecD0.extent.set(AxisDirection::AxisZ, -640., -600);
0167 pixelNec.container = ProtoVolume::ContainerStructure{
0168 {pixNecD6, pixNecD5, pixNecD4, pixNecD3, pixNecD2, pixNecD1, pixNecD0},
0169 {BinningData(open, AxisDirection::AxisZ, {0., 1.})},
0170 true};
0171
0172 BinningData pixEcBinningR =
0173 BinningData(open, AxisDirection::AxisR, 2., 0., 1.);
0174 BinningData pixEcBinningPhi = BinningData(
0175 closed, AxisDirection::AxisPhi, 30., -std::numbers::pi, std::numbers::pi);
0176
0177 for (auto& cv : pixelNec.container.value().constituentVolumes) {
0178 cv.extent.setEnvelope(discLayerEnvelope);
0179 cv.internal = ProtoVolume::InternalStructure{
0180 Surface::SurfaceType::Disc, {pixEcBinningR, pixEcBinningPhi}};
0181 }
0182
0183 ProtoVolume pixelBarrel;
0184 pixelBarrel.name = "odd-pixel-barrel";
0185 pixelBarrel.extent.set(AxisDirection::AxisZ, -580., 580);
0186
0187 ProtoVolume pixBarrelL0;
0188 pixBarrelL0.name = "odd-pixel-barrel-l0";
0189 pixBarrelL0.extent.set(AxisDirection::AxisR, 28., 48.);
0190 pixBarrelL0.extent.set(AxisDirection::AxisZ, -580., 580);
0191 ProtoVolume pixBarrelL1;
0192 pixBarrelL1.name = "odd-pixel-barrel-l1";
0193 pixBarrelL1.extent.set(AxisDirection::AxisR, 62., 76);
0194 pixBarrelL1.extent.set(AxisDirection::AxisZ, -580., 580);
0195 ProtoVolume pixBarrelL2;
0196 pixBarrelL2.name = "odd-pixel-barrel-l2";
0197 pixBarrelL2.extent.set(AxisDirection::AxisR, 100., 120.);
0198 pixBarrelL2.extent.set(AxisDirection::AxisZ, -580., 580);
0199 ProtoVolume pixBarrelL3;
0200 pixBarrelL3.name = "odd-pixel-barrel-l3";
0201 pixBarrelL3.extent.set(AxisDirection::AxisR, 160., 180.);
0202 pixBarrelL3.extent.set(AxisDirection::AxisZ, -580., 580);
0203
0204 pixelBarrel.container = ProtoVolume::ContainerStructure{
0205 {pixBarrelL0, pixBarrelL1, pixBarrelL2, pixBarrelL3},
0206 {BinningData(open, AxisDirection::AxisR, {0., 1})},
0207 true};
0208
0209 for (auto& cv : pixelBarrel.container.value().constituentVolumes) {
0210 cv.extent.setEnvelope(cylinderLayerEnvelope);
0211 cv.internal =
0212 ProtoVolume::InternalStructure{Surface::SurfaceType::Cylinder};
0213 }
0214
0215 ProtoVolume pixelPec;
0216 pixelPec.name = "odd-pixel-pec";
0217 pixelPec.extent.set(AxisDirection::AxisZ, 580., 3100.);
0218
0219 ProtoVolume pixPecD0;
0220 pixPecD0.name = "odd-pixel-pec-d0";
0221 pixPecD0.extent.set(AxisDirection::AxisZ, 600., 640);
0222 ProtoVolume pixPecD1;
0223 pixPecD1.name = "odd-pixel-pec-d1";
0224 pixPecD1.extent.set(AxisDirection::AxisZ, 700., 740);
0225 ProtoVolume pixPecD2;
0226 pixPecD2.name = "odd-pixel-pec-d2";
0227 pixPecD2.extent.set(AxisDirection::AxisZ, 820., 860.);
0228 ProtoVolume pixPecD3;
0229 pixPecD3.name = "odd-pixel-pec-d3";
0230 pixPecD3.extent.set(AxisDirection::AxisZ, 960., 1000.);
0231 ProtoVolume pixPecD4;
0232 pixPecD4.name = "odd-pixel-pec-d4";
0233 pixPecD4.extent.set(AxisDirection::AxisZ, 1100., 1140);
0234 ProtoVolume pixPecD5;
0235 pixPecD5.name = "odd-pixel-pec-d5";
0236 pixPecD5.extent.set(AxisDirection::AxisZ, 1300., 1340.);
0237 ProtoVolume pixPecD6;
0238 pixPecD6.name = "odd-pixel-pec-d6";
0239 pixPecD6.extent.set(AxisDirection::AxisZ, 1500., 1540.);
0240
0241 pixelPec.container = ProtoVolume::ContainerStructure{
0242 {pixPecD0, pixPecD1, pixPecD2, pixPecD3, pixPecD4, pixPecD5, pixPecD6},
0243 {BinningData(open, AxisDirection::AxisZ, {0., 1})},
0244 true};
0245
0246 for (auto& cv : pixelPec.container.value().constituentVolumes) {
0247 cv.extent.setEnvelope(discLayerEnvelope);
0248 cv.internal = ProtoVolume::InternalStructure{
0249 Surface::SurfaceType::Disc, {pixEcBinningR, pixEcBinningPhi}};
0250 }
0251
0252 pixelContainer.container = ProtoVolume::ContainerStructure{
0253 {pixelNec, pixelBarrel, pixelPec},
0254 {BinningData(open, AxisDirection::AxisZ, {-3100., -580., 580., 3100.})}};
0255
0256
0257 ProtoVolume pstContainer;
0258 pstContainer.name = "odd-pst";
0259 pstContainer.extent.set(AxisDirection::AxisR, 200., 210.);
0260 ProtoVolume pst;
0261 pst.name = "odd-pst-l";
0262 pst.extent.set(AxisDirection::AxisR, 201., 209.);
0263 pst.internal = ProtoVolume::InternalStructure{Surface::SurfaceType::Cylinder};
0264 pstContainer.container = ProtoVolume::ContainerStructure{
0265 {pst}, {BinningData(open, AxisDirection::AxisR, {0., 1.})}, true};
0266
0267
0268 ProtoVolume sstripContainer;
0269 sstripContainer.name = "odd-sstrip";
0270 sstripContainer.extent.set(AxisDirection::AxisR, 210., 720);
0271
0272 BinningData sstripEcBinningR =
0273 BinningData(open, AxisDirection::AxisR, 3., 0., 1.);
0274 BinningData sstripEcBinningPhi = BinningData(
0275 closed, AxisDirection::AxisPhi, 42., -std::numbers::pi, std::numbers::pi);
0276
0277 ProtoVolume sstripNec;
0278 sstripNec.name = "odd-sstrip-nec";
0279 sstripNec.extent.set(AxisDirection::AxisZ, -3100., -1200);
0280 ProtoVolume sstripNecD5;
0281 sstripNecD5.name = "odd-sstrip-nec-d5";
0282 sstripNecD5.extent.set(AxisDirection::AxisZ, -3000, -2900.);
0283 ProtoVolume sstripNecD4;
0284 sstripNecD4.name = "odd-sstrip-nec-d4";
0285 sstripNecD4.extent.set(AxisDirection::AxisZ, -2600., -2500.);
0286 ProtoVolume sstripNecD3;
0287 sstripNecD3.name = "odd-sstrip-nec-d3";
0288 sstripNecD3.extent.set(AxisDirection::AxisZ, -2250, -2150.);
0289 ProtoVolume sstripNecD2;
0290 sstripNecD2.name = "odd-sstrip-nec-d2";
0291 sstripNecD2.extent.set(AxisDirection::AxisZ, -1900, -1800.);
0292 ProtoVolume sstripNecD1;
0293 sstripNecD1.name = "odd-sstrip-nec-d1";
0294 sstripNecD1.extent.set(AxisDirection::AxisZ, -1600., -1500.);
0295 ProtoVolume sstripNecD0;
0296 sstripNecD0.name = "odd-sstrip-nec-d0";
0297 sstripNecD0.extent.set(AxisDirection::AxisZ, -1350., -1250.);
0298
0299 sstripNec.container = ProtoVolume::ContainerStructure{
0300 {sstripNecD5, sstripNecD4, sstripNecD3, sstripNecD2, sstripNecD1,
0301 sstripNecD0},
0302 {BinningData(open, AxisDirection::AxisZ, {0., 1})},
0303 true};
0304
0305 for (auto& cv : sstripNec.container.value().constituentVolumes) {
0306 cv.extent.setEnvelope(discLayerEnvelope);
0307 cv.internal = ProtoVolume::InternalStructure{
0308 Surface::SurfaceType::Disc, {sstripEcBinningR, sstripEcBinningPhi}};
0309 }
0310
0311 ProtoVolume sstripBarrel;
0312 sstripBarrel.name = "odd-sstrip-barrel";
0313 sstripBarrel.extent.set(AxisDirection::AxisZ, -1200., 1200);
0314
0315 ProtoVolume sstripBarrelL0;
0316 sstripBarrelL0.name = "odd-sstrip-barrel-l0";
0317 sstripBarrelL0.extent.set(AxisDirection::AxisR, 240., 280.);
0318 ProtoVolume sstripBarrelL1;
0319 sstripBarrelL1.name = "odd-sstrip-barrel-l1";
0320 sstripBarrelL1.extent.set(AxisDirection::AxisR, 340., 380.);
0321 ProtoVolume sstripBarrelL2;
0322 sstripBarrelL2.name = "odd-sstrip-barrel-l2";
0323 sstripBarrelL2.extent.set(AxisDirection::AxisR, 480., 520.);
0324 ProtoVolume sstripBarrelL3;
0325 sstripBarrelL3.name = "odd-sstrip-barrel-l3";
0326 sstripBarrelL3.extent.set(AxisDirection::AxisR, 640., 680.);
0327
0328 sstripBarrel.container = ProtoVolume::ContainerStructure{
0329 {sstripBarrelL0, sstripBarrelL1, sstripBarrelL2, sstripBarrelL3},
0330 {BinningData(open, AxisDirection::AxisR, {0., 1})},
0331 true};
0332
0333 for (auto& cv : sstripBarrel.container.value().constituentVolumes) {
0334 cv.extent.setEnvelope(cylinderLayerEnvelope);
0335 cv.internal =
0336 ProtoVolume::InternalStructure{Surface::SurfaceType::Cylinder};
0337 }
0338
0339 ProtoVolume sstripPec;
0340 sstripPec.name = "odd-sstrip-pec";
0341 sstripPec.extent.set(AxisDirection::AxisZ, 1200., 3100);
0342
0343 ProtoVolume sstripPecD0;
0344 sstripPecD0.name = "odd-sstrip-pec-d0";
0345 sstripPecD0.extent.set(AxisDirection::AxisZ, 1250., 1350);
0346 ProtoVolume sstripPecD1;
0347 sstripPecD1.name = "odd-sstrip-pec-d1";
0348 sstripPecD1.extent.set(AxisDirection::AxisZ, 1500., 1600.);
0349 ProtoVolume sstripPecD2;
0350 sstripPecD2.name = "odd-sstrip-pec-d2";
0351 sstripPecD2.extent.set(AxisDirection::AxisZ, 1800., 1900.);
0352 ProtoVolume sstripPecD3;
0353 sstripPecD3.name = "odd-sstrip-pec-d3";
0354 sstripPecD3.extent.set(AxisDirection::AxisZ, 2150., 2250.);
0355 ProtoVolume sstripPecD4;
0356 sstripPecD4.name = "odd-sstrip-pec-d4";
0357 sstripPecD4.extent.set(AxisDirection::AxisZ, 2500., 2600.);
0358 ProtoVolume sstripPecD5;
0359 sstripPecD5.name = "odd-sstrip-pec-d5";
0360 sstripPecD5.extent.set(AxisDirection::AxisZ, 2900., 3000.);
0361
0362 sstripPec.container = ProtoVolume::ContainerStructure{
0363 {sstripPecD0, sstripPecD1, sstripPecD2, sstripPecD3, sstripPecD4,
0364 sstripPecD5},
0365 {BinningData(open, AxisDirection::AxisZ, {0., 1})},
0366 true};
0367 for (auto& cv : sstripPec.container.value().constituentVolumes) {
0368 cv.extent.setEnvelope(discLayerEnvelope);
0369 cv.internal = ProtoVolume::InternalStructure{
0370 Surface::SurfaceType::Disc, {sstripEcBinningR, sstripEcBinningPhi}};
0371 }
0372
0373 sstripContainer.container = ProtoVolume::ContainerStructure{
0374 {sstripNec, sstripBarrel, sstripPec},
0375 {BinningData(open, AxisDirection::AxisZ,
0376 {-3100., -1200., 1200., 3100.})}};
0377
0378
0379 ProtoVolume lstripContainer;
0380 lstripContainer.name = "odd-lstrip";
0381 lstripContainer.extent.set(AxisDirection::AxisR, 720, 1100.);
0382
0383 ProtoVolume lstripNec;
0384 lstripNec.name = "odd-lstrip-nec";
0385 lstripNec.extent.set(AxisDirection::AxisZ, -3100., -1200);
0386 ProtoVolume lstripNecD5;
0387 lstripNecD5.name = "odd-lstrip-nec-d5";
0388 lstripNecD5.extent.set(AxisDirection::AxisZ, -3050, -2900.);
0389 ProtoVolume lstripNecD4;
0390 lstripNecD4.name = "odd-lstrip-nec-d4";
0391 lstripNecD4.extent.set(AxisDirection::AxisZ, -2650., -2500.);
0392 ProtoVolume lstripNecD3;
0393 lstripNecD3.name = "odd-lstrip-nec-d3";
0394 lstripNecD3.extent.set(AxisDirection::AxisZ, -2300, -2150.);
0395 ProtoVolume lstripNecD2;
0396 lstripNecD2.name = "odd-lstrip-nec-d2";
0397 lstripNecD2.extent.set(AxisDirection::AxisZ, -1950, -1800.);
0398 ProtoVolume lstripNecD1;
0399 lstripNecD1.name = "odd-lstrip-nec-d1";
0400 lstripNecD1.extent.set(AxisDirection::AxisZ, -1650., -1500.);
0401 ProtoVolume lstripNecD0;
0402 lstripNecD0.name = "odd-lstrip-nec-d0";
0403 lstripNecD0.extent.set(AxisDirection::AxisZ, -1400., -1250.);
0404
0405 lstripNec.container = ProtoVolume::ContainerStructure{
0406 {lstripNecD5, lstripNecD4, lstripNecD3, lstripNecD2, lstripNecD1,
0407 lstripNecD0},
0408 {BinningData(open, AxisDirection::AxisZ, {0., 1})},
0409 true};
0410
0411 for (auto& cv : lstripNec.container.value().constituentVolumes) {
0412 cv.extent.setEnvelope(discLayerEnvelope);
0413 cv.internal = ProtoVolume::InternalStructure{Surface::SurfaceType::Disc};
0414 }
0415
0416 ProtoVolume lstripBarrel;
0417 lstripBarrel.name = "odd-lstrip-barrel";
0418 lstripBarrel.extent.set(AxisDirection::AxisZ, -1200., 1200);
0419
0420 ProtoVolume lstripBarrelL0;
0421 lstripBarrelL0.name = "odd-lstrip-barrel-l0";
0422 lstripBarrelL0.extent.set(AxisDirection::AxisR, 800., 840.);
0423 ProtoVolume lstripBarrelL1;
0424 lstripBarrelL1.name = "odd-lstrip-barrel-l1";
0425 lstripBarrelL1.extent.set(AxisDirection::AxisR, 1000., 1050.);
0426
0427 lstripBarrel.container = ProtoVolume::ContainerStructure{
0428 {lstripBarrelL0, lstripBarrelL1},
0429 {BinningData(open, AxisDirection::AxisR, {0., 1})},
0430 true};
0431
0432 for (auto& cv : lstripBarrel.container.value().constituentVolumes) {
0433 cv.extent.setEnvelope(cylinderLayerEnvelope);
0434 cv.internal =
0435 ProtoVolume::InternalStructure{Surface::SurfaceType::Cylinder};
0436 }
0437
0438 ProtoVolume lstripPec;
0439 lstripPec.name = "odd-lstrip-pec";
0440 lstripPec.extent.set(AxisDirection::AxisZ, 1200., 3100);
0441
0442 ProtoVolume lstripPecD0;
0443 lstripPecD0.name = "odd-lstrip-pec-d0";
0444 lstripPecD0.extent.set(AxisDirection::AxisZ, 1250., 1400);
0445 ProtoVolume lstripPecD1;
0446 lstripPecD1.name = "odd-lstrip-pec-d1";
0447 lstripPecD1.extent.set(AxisDirection::AxisZ, 1500., 1650.);
0448 ProtoVolume lstripPecD2;
0449 lstripPecD2.name = "odd-lstrip-pec-d2";
0450 lstripPecD2.extent.set(AxisDirection::AxisZ, 1800., 1950.);
0451 ProtoVolume lstripPecD3;
0452 lstripPecD3.name = "odd-lstrip-pec-d3";
0453 lstripPecD3.extent.set(AxisDirection::AxisZ, 2150., 2300.);
0454 ProtoVolume lstripPecD4;
0455 lstripPecD4.name = "odd-lstrip-pec-d4";
0456 lstripPecD4.extent.set(AxisDirection::AxisZ, 2500., 2650.);
0457 ProtoVolume lstripPecD5;
0458 lstripPecD5.name = "odd-lstrip-pec-d5";
0459 lstripPecD5.extent.set(AxisDirection::AxisZ, 2900., 3050.);
0460
0461 lstripPec.container = ProtoVolume::ContainerStructure{
0462 {lstripPecD0, lstripPecD1, lstripPecD2, lstripPecD3, lstripPecD4,
0463 lstripPecD5},
0464 {BinningData(open, AxisDirection::AxisZ, {0., 1})},
0465 true};
0466 for (auto& cv : lstripPec.container.value().constituentVolumes) {
0467 cv.internal = ProtoVolume::InternalStructure{Surface::SurfaceType::Disc};
0468 cv.extent.setEnvelope(discLayerEnvelope);
0469 }
0470 lstripContainer.container = ProtoVolume::ContainerStructure{
0471 {lstripNec, lstripBarrel, lstripPec},
0472 {BinningData(open, AxisDirection::AxisZ,
0473 {-3100., -1200., 1200., 3100.})}};
0474
0475
0476 ProtoVolume detectorContainer;
0477 detectorContainer.name = "odd-light-world";
0478 detectorContainer.extent.set(AxisDirection::AxisR, 0., 1100.);
0479 detectorContainer.extent.set(AxisDirection::AxisZ, -3100., 3100.);
0480 detectorContainer.container = ProtoVolume::ContainerStructure{
0481 {beamPipeContainer, pixelContainer, pstContainer, sstripContainer,
0482 lstripContainer},
0483 {BinningData(open, AxisDirection::AxisR,
0484 {0., 25., 200., 210., 720., 1100.})}};
0485
0486
0487 ProtoDetector detector;
0488 detector.name = "odd-light";
0489 detector.worldVolume = detectorContainer;
0490
0491
0492 nlohmann::json jdet;
0493 jdet["detector"] = detector;
0494
0495 std::ofstream out;
0496 out.open("odd-proto-detector.json");
0497 out << jdet.dump(4);
0498 out.close();
0499
0500 ProtoDetector detectorIn = jdet["detector"];
0501
0502
0503 BOOST_CHECK_EQUAL(detector.name, detectorIn.name);
0504
0505 const auto& world = detector.worldVolume;
0506 const auto& worldIn = detectorIn.worldVolume;
0507
0508 BOOST_CHECK(isEqual(world, worldIn, 0.1));
0509 }
0510
0511 BOOST_AUTO_TEST_SUITE_END()
0512
0513 }