File indexing completed on 2025-01-18 09:11:21
0001
0002
0003
0004
0005
0006
0007
0008
0009 #include "Acts/Geometry/CylinderVolumeBuilder.hpp"
0010
0011 #include "Acts/Definitions/Algebra.hpp"
0012 #include "Acts/Definitions/Common.hpp"
0013 #include "Acts/Geometry/BoundarySurfaceFace.hpp"
0014 #include "Acts/Geometry/CylinderLayer.hpp"
0015 #include "Acts/Geometry/CylinderVolumeBounds.hpp"
0016 #include "Acts/Geometry/IConfinedTrackingVolumeBuilder.hpp"
0017 #include "Acts/Geometry/ILayerBuilder.hpp"
0018 #include "Acts/Geometry/ITrackingVolumeHelper.hpp"
0019 #include "Acts/Geometry/Layer.hpp"
0020 #include "Acts/Geometry/TrackingVolume.hpp"
0021 #include "Acts/Geometry/VolumeBounds.hpp"
0022 #include "Acts/Surfaces/CylinderBounds.hpp"
0023 #include "Acts/Surfaces/CylinderSurface.hpp"
0024 #include "Acts/Surfaces/RadialBounds.hpp"
0025 #include "Acts/Surfaces/Surface.hpp"
0026 #include "Acts/Surfaces/SurfaceBounds.hpp"
0027 #include "Acts/Utilities/BinningType.hpp"
0028 #include "Acts/Utilities/Helpers.hpp"
0029
0030 #include <algorithm>
0031 #include <iterator>
0032 #include <vector>
0033
0034 #include <boost/algorithm/string.hpp>
0035 #include <math.h>
0036
0037 Acts::CylinderVolumeBuilder::CylinderVolumeBuilder(
0038 const Acts::CylinderVolumeBuilder::Config& cvbConfig,
0039 std::unique_ptr<const Logger> logger)
0040 : Acts::ITrackingVolumeBuilder(), m_cfg(), m_logger(std::move(logger)) {
0041 setConfiguration(cvbConfig);
0042 }
0043
0044 Acts::CylinderVolumeBuilder::~CylinderVolumeBuilder() = default;
0045
0046 void Acts::CylinderVolumeBuilder::setConfiguration(
0047 const Acts::CylinderVolumeBuilder::Config& cvbConfig) {
0048
0049
0050 m_cfg = cvbConfig;
0051 }
0052
0053 void Acts::CylinderVolumeBuilder::setLogger(
0054 std::unique_ptr<const Logger> newLogger) {
0055 m_logger = std::move(newLogger);
0056 }
0057
0058 std::shared_ptr<Acts::TrackingVolume>
0059 Acts::CylinderVolumeBuilder::trackingVolume(
0060 const GeometryContext& gctx, TrackingVolumePtr existingVolume,
0061 std::shared_ptr<const VolumeBounds> externalBounds) const {
0062 ACTS_DEBUG("Configured to build volume : " << m_cfg.volumeName);
0063 if (existingVolume) {
0064 ACTS_DEBUG("- will wrap/enclose : " << existingVolume->volumeName());
0065 }
0066
0067
0068
0069 MutableTrackingVolumePtr volume = nullptr;
0070
0071
0072
0073 ACTS_DEBUG("-> Building layers");
0074 LayerVector negativeLayers;
0075 LayerVector centralLayers;
0076 LayerVector positiveLayers;
0077
0078
0079 WrappingConfig wConfig;
0080
0081
0082 if (m_cfg.layerBuilder) {
0083
0084 negativeLayers = m_cfg.layerBuilder->negativeLayers(gctx);
0085
0086 centralLayers = m_cfg.layerBuilder->centralLayers(gctx);
0087
0088 positiveLayers = m_cfg.layerBuilder->positiveLayers(gctx);
0089 }
0090 ACTS_DEBUG("-> Building layers complete");
0091
0092
0093 MutableTrackingVolumeVector centralVolumes;
0094 if (m_cfg.ctVolumeBuilder) {
0095 centralVolumes = m_cfg.ctVolumeBuilder->centralVolumes();
0096 }
0097
0098
0099
0100
0101 if (existingVolume) {
0102
0103 auto existingBounds = dynamic_cast<const CylinderVolumeBounds*>(
0104 &existingVolume->volumeBounds());
0105
0106 wConfig.existingVolumeConfig.present = true;
0107 wConfig.existingVolumeConfig.rMin =
0108 existingBounds->get(CylinderVolumeBounds::eMinR);
0109 wConfig.existingVolumeConfig.rMax =
0110 existingBounds->get(CylinderVolumeBounds::eMaxR);
0111 wConfig.existingVolumeConfig.zMin =
0112 existingVolume->center().z() -
0113 existingBounds->get(CylinderVolumeBounds::eHalfLengthZ);
0114 wConfig.existingVolumeConfig.zMax =
0115 existingVolume->center().z() +
0116 existingBounds->get(CylinderVolumeBounds::eHalfLengthZ);
0117 }
0118
0119
0120
0121 VolumeConfig externalBoundConfig;
0122 if (externalBounds) {
0123 const CylinderVolumeBounds* ocvBounds =
0124 dynamic_cast<const CylinderVolumeBounds*>(externalBounds.get());
0125
0126 if (ocvBounds != nullptr) {
0127
0128 wConfig.externalVolumeConfig.present = true;
0129 wConfig.externalVolumeConfig.rMin =
0130 ocvBounds->get(CylinderVolumeBounds::eMinR);
0131 wConfig.externalVolumeConfig.rMax =
0132 ocvBounds->get(CylinderVolumeBounds::eMaxR);
0133 wConfig.externalVolumeConfig.zMin =
0134 -ocvBounds->get(CylinderVolumeBounds::eHalfLengthZ);
0135 wConfig.externalVolumeConfig.zMax =
0136 ocvBounds->get(CylinderVolumeBounds::eHalfLengthZ);
0137 }
0138 }
0139
0140
0141
0142
0143
0144
0145
0146
0147
0148
0149
0150
0151
0152
0153
0154
0155
0156
0157
0158
0159
0160 wConfig.nVolumeConfig = analyzeContent(gctx, negativeLayers, {});
0161 wConfig.cVolumeConfig = analyzeContent(gctx, centralLayers, centralVolumes);
0162 wConfig.pVolumeConfig = analyzeContent(gctx, positiveLayers, {});
0163
0164 bool hasLayers = wConfig.nVolumeConfig.present ||
0165 wConfig.cVolumeConfig.present ||
0166 wConfig.pVolumeConfig.present;
0167
0168 if (!hasLayers) {
0169 ACTS_INFO("No layers present, returning nullptr");
0170 return nullptr;
0171 }
0172
0173 std::string layerConfiguration = "|";
0174 if (wConfig.nVolumeConfig.present) {
0175
0176 ACTS_VERBOSE("Negative layers are present: rmin, rmax | zmin, zmax = "
0177 << wConfig.nVolumeConfig.toString());
0178 std::vector<std::string> centers;
0179 std::transform(negativeLayers.begin(), negativeLayers.end(),
0180 std::back_inserter(centers), [&](const auto& layer) {
0181 return std::to_string(
0182 layer->surfaceRepresentation().center(gctx)[eZ]);
0183 });
0184 ACTS_VERBOSE("-> z locations: " << boost::algorithm::join(centers, ", "));
0185
0186 layerConfiguration += " Negative Endcap |";
0187 }
0188 if (wConfig.cVolumeConfig.present) {
0189
0190 ACTS_VERBOSE("Central layers are present: rmin, rmax | zmin, zmax = "
0191 << wConfig.cVolumeConfig.toString());
0192 std::vector<std::string> centers;
0193 std::transform(centralLayers.begin(), centralLayers.end(),
0194 std::back_inserter(centers), [&](const auto& layer) {
0195 return std::to_string(VectorHelpers::perp(
0196 layer->surfaceRepresentation().center(gctx)));
0197 });
0198 ACTS_VERBOSE("-> radii: " << boost::algorithm::join(centers, ", "));
0199
0200 layerConfiguration += " Barrel |";
0201 }
0202 if (wConfig.pVolumeConfig.present) {
0203
0204 ACTS_VERBOSE("Positive layers are present: rmin, rmax | zmin, zmax = "
0205 << wConfig.pVolumeConfig.toString());
0206 std::vector<std::string> centers;
0207 std::transform(positiveLayers.begin(), positiveLayers.end(),
0208 std::back_inserter(centers), [&](const auto& layer) {
0209 return std::to_string(
0210 layer->surfaceRepresentation().center(gctx)[eZ]);
0211 });
0212 ACTS_VERBOSE("-> z locations: " << boost::algorithm::join(centers, ", "));
0213
0214 layerConfiguration += " Positive Endcap |";
0215 }
0216
0217 ACTS_DEBUG("Layer configuration is : " << layerConfiguration);
0218
0219
0220
0221 ACTS_VERBOSE("Configurations after layer parsing " << '\n'
0222 << wConfig.toString());
0223
0224 wConfig.configureContainerVolume();
0225 ACTS_VERBOSE("Configuration after container synchronisation "
0226 << '\n'
0227 << wConfig.toString());
0228
0229 if (wConfig.existingVolumeConfig.present) {
0230 wConfig.wrapInsertAttach();
0231 ACTS_VERBOSE("Configuration after wrapping, insertion, attachment "
0232 << '\n'
0233 << wConfig.toString());
0234 } else {
0235
0236
0237
0238 wConfig.wCondition = NoWrapping;
0239 }
0240
0241
0242 auto tvHelper = m_cfg.trackingVolumeHelper;
0243
0244 auto barrel =
0245 wConfig.cVolumeConfig.present
0246 ? tvHelper->createTrackingVolume(
0247 gctx, wConfig.cVolumeConfig.layers,
0248 wConfig.cVolumeConfig.volumes, m_cfg.volumeMaterial,
0249 wConfig.cVolumeConfig.rMin, wConfig.cVolumeConfig.rMax,
0250 wConfig.cVolumeConfig.zMin, wConfig.cVolumeConfig.zMax,
0251 m_cfg.volumeName + "::Barrel")
0252 : nullptr;
0253
0254
0255
0256
0257 auto createEndcap =
0258 [&](VolumeConfig& centralConfig, VolumeConfig& endcapConfig,
0259 const std::string& endcapName) -> MutableTrackingVolumePtr {
0260
0261 if (!endcapConfig.present) {
0262 return nullptr;
0263 }
0264
0265 if (m_cfg.checkRingLayout) {
0266 ACTS_DEBUG("Configured to check for ring layout - parsing layers.");
0267
0268 std::vector<double> innerRadii = {};
0269 std::vector<double> outerRadii = {};
0270 for (const auto& elay : endcapConfig.layers) {
0271 auto discBounds = dynamic_cast<const RadialBounds*>(
0272 &(elay->surfaceRepresentation().bounds()));
0273 if (discBounds != nullptr) {
0274 double tolerance = m_cfg.ringTolerance;
0275
0276 double rMin = discBounds->rMin();
0277 auto innerSearch = std::ranges::find_if(innerRadii, [&](double r) {
0278 return std::abs(rMin - r) < tolerance;
0279 });
0280 if (innerSearch == innerRadii.end()) {
0281 innerRadii.push_back(rMin);
0282 }
0283
0284 double rMax = discBounds->rMax();
0285 auto outerSearch = std::ranges::find_if(outerRadii, [&](double r) {
0286 return std::abs(rMax - r) < tolerance;
0287 });
0288 if (outerSearch == outerRadii.end()) {
0289 outerRadii.push_back(rMax);
0290 }
0291 }
0292 }
0293
0294
0295
0296 std::ranges::sort(innerRadii);
0297 std::ranges::sort(outerRadii);
0298
0299 ACTS_DEBUG("Inner radii:" << [&]() {
0300 std::stringstream ss;
0301 for (double f : innerRadii) {
0302 ss << " " << f;
0303 }
0304 return ss.str();
0305 }());
0306
0307 ACTS_DEBUG("Outer radii:" << [&]() {
0308 std::stringstream ss;
0309 for (double f : outerRadii) {
0310 ss << " " << f;
0311 }
0312 return ss.str();
0313 }());
0314
0315 if (innerRadii.size() == outerRadii.size() && !innerRadii.empty()) {
0316 bool consistent = true;
0317
0318 ACTS_VERBOSE("Checking ring radius consistency");
0319 std::vector<double> interRadii = {};
0320 for (std::size_t ir = 1; ir < innerRadii.size(); ++ir) {
0321
0322 ACTS_VERBOSE(
0323 "or #" << ir - 1 << " < ir #" << ir << ": " << outerRadii[ir - 1]
0324 << " < " << innerRadii[ir] << ", ok: "
0325 << (outerRadii[ir - 1] < innerRadii[ir] ? "yes" : "no"));
0326 if (outerRadii[ir - 1] < innerRadii[ir]) {
0327 interRadii.push_back(0.5 * (outerRadii[ir - 1] + innerRadii[ir]));
0328 } else {
0329 consistent = false;
0330 break;
0331 }
0332 }
0333
0334 if (consistent) {
0335 ACTS_DEBUG("Ring layout detection: " << innerRadii.size()
0336 << " volumes.");
0337
0338 std::vector<std::pair<double, double>> volumeRminRmax = {};
0339 for (unsigned int ii = 0; ii < interRadii.size(); ++ii) {
0340 if (ii == 0) {
0341 volumeRminRmax.push_back({endcapConfig.rMin, interRadii[ii]});
0342 }
0343 if (ii + 1 < interRadii.size()) {
0344 volumeRminRmax.push_back({interRadii[ii], interRadii[ii + 1]});
0345 } else {
0346 volumeRminRmax.push_back({interRadii[ii], endcapConfig.rMax});
0347 }
0348 }
0349 auto ringLayers =
0350 std::vector<LayerVector>(innerRadii.size(), LayerVector());
0351
0352 for (const auto& elay : endcapConfig.layers) {
0353
0354 double test = elay->surfaceRepresentation().referencePositionValue(
0355 gctx, AxisDirection::AxisR);
0356
0357 auto ringVolume =
0358 std::ranges::find_if(volumeRminRmax, [&](const auto& vrr) {
0359 return (test > vrr.first && test < vrr.second);
0360 });
0361 if (ringVolume != volumeRminRmax.end()) {
0362 unsigned int ringBin =
0363 std::distance(volumeRminRmax.begin(), ringVolume);
0364 ringLayers[ringBin].push_back(elay);
0365 }
0366 }
0367
0368 ACTS_DEBUG("Ring layout configuration: ");
0369
0370 std::vector<TrackingVolumePtr> endcapContainer;
0371 unsigned int ir = 0;
0372 for (auto& rLayers : ringLayers) {
0373 ACTS_DEBUG(" - ring volume " << ir << " with " << rLayers.size()
0374 << " layers, and rmin/rmax = "
0375 << volumeRminRmax[ir].first << "/"
0376 << volumeRminRmax[ir].second);
0377 endcapContainer.push_back(tvHelper->createTrackingVolume(
0378 gctx, rLayers, centralConfig.volumes, m_cfg.volumeMaterial,
0379 volumeRminRmax[ir].first, volumeRminRmax[ir].second,
0380 endcapConfig.zMin, endcapConfig.zMax,
0381 m_cfg.volumeName + endcapName + std::string("::Ring") +
0382 std::to_string(ir)));
0383 ++ir;
0384 }
0385
0386 return tvHelper->createContainerTrackingVolume(gctx, endcapContainer);
0387 } else {
0388 ACTS_DEBUG("Ring radii found to be inconsistent");
0389 }
0390 } else {
0391 ACTS_DEBUG("Have " << innerRadii.size() << " inner radii and "
0392 << outerRadii.size() << " outer radii");
0393 }
0394 }
0395
0396
0397 return tvHelper->createTrackingVolume(
0398 gctx, endcapConfig.layers, centralConfig.volumes, m_cfg.volumeMaterial,
0399 endcapConfig.rMin, endcapConfig.rMax, endcapConfig.zMin,
0400 endcapConfig.zMax, m_cfg.volumeName + endcapName);
0401 };
0402
0403
0404 auto nEndcap = createEndcap(wConfig.cVolumeConfig, wConfig.nVolumeConfig,
0405 "::NegativeEndcap");
0406
0407
0408 auto pEndcap = createEndcap(wConfig.cVolumeConfig, wConfig.pVolumeConfig,
0409 "::PositiveEndcap");
0410
0411 ACTS_DEBUG("Newly created volume(s) will be " << wConfig.wConditionScreen);
0412
0413
0414 if (wConfig.wCondition == Wrapping || wConfig.wCondition == Inserting ||
0415 wConfig.wCondition == NoWrapping) {
0416 ACTS_VERBOSE("Combined new container is being built.");
0417
0418 std::vector<TrackingVolumePtr> volumesContainer;
0419 if (nEndcap) {
0420 volumesContainer.push_back(nEndcap);
0421 volume = nEndcap;
0422
0423 if (!m_cfg.buildToRadiusZero) {
0424 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[0],
0425 Acts::tubeInnerCover);
0426 }
0427 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[1],
0428 Acts::tubeOuterCover);
0429 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[2],
0430 Acts::negativeFaceXY);
0431 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[3],
0432 Acts::positiveFaceXY);
0433 }
0434 if (barrel) {
0435
0436 volumesContainer.push_back(barrel);
0437 volume = barrel;
0438
0439 if (!m_cfg.buildToRadiusZero) {
0440 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[0],
0441 Acts::tubeInnerCover);
0442 }
0443 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[1],
0444 Acts::tubeOuterCover);
0445 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[3],
0446 Acts::negativeFaceXY);
0447 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[4],
0448 Acts::positiveFaceXY);
0449 }
0450 if (pEndcap) {
0451 volumesContainer.push_back(pEndcap);
0452 volume = pEndcap;
0453
0454 if (!m_cfg.buildToRadiusZero) {
0455 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[0],
0456 Acts::tubeInnerCover);
0457 }
0458 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[1],
0459 Acts::tubeOuterCover);
0460 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[4],
0461 Acts::negativeFaceXY);
0462 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[5],
0463 Acts::positiveFaceXY);
0464 }
0465
0466 volume =
0467 volumesContainer.size() > 1
0468 ? tvHelper->createContainerTrackingVolume(gctx, volumesContainer)
0469 : volume;
0470 } else if (wConfig.wCondition != Attaching) {
0471
0472 volume = nEndcap ? nEndcap : (barrel ? barrel : pEndcap);
0473 }
0474
0475
0476 TrackingVolumePtr existingVolumeCp = existingVolume;
0477
0478 if (existingVolumeCp) {
0479
0480 std::vector<TrackingVolumePtr> existingContainer;
0481 if (wConfig.fGapVolumeConfig.present) {
0482
0483 auto fGap = tvHelper->createGapTrackingVolume(
0484 gctx, wConfig.cVolumeConfig.volumes, m_cfg.volumeMaterial,
0485 wConfig.fGapVolumeConfig.rMin, wConfig.fGapVolumeConfig.rMax,
0486 wConfig.fGapVolumeConfig.zMin, wConfig.fGapVolumeConfig.zMax, 1,
0487 false, m_cfg.volumeName + "::fGap");
0488
0489 existingContainer.push_back(fGap);
0490 }
0491 existingContainer.push_back(existingVolumeCp);
0492 if (wConfig.sGapVolumeConfig.present) {
0493
0494 auto sGap = tvHelper->createGapTrackingVolume(
0495 gctx, wConfig.cVolumeConfig.volumes, m_cfg.volumeMaterial,
0496 wConfig.sGapVolumeConfig.rMin, wConfig.sGapVolumeConfig.rMax,
0497 wConfig.sGapVolumeConfig.zMin, wConfig.sGapVolumeConfig.zMax, 1,
0498 false, m_cfg.volumeName + "::sGap");
0499
0500 existingContainer.push_back(sGap);
0501 }
0502
0503
0504 existingVolumeCp =
0505 existingContainer.size() > 1
0506 ? tvHelper->createContainerTrackingVolume(gctx, existingContainer)
0507 : existingVolumeCp;
0508
0509
0510
0511 existingContainer.clear();
0512 if (wConfig.wCondition == CentralWrapping) {
0513 existingContainer.push_back(existingVolumeCp);
0514 existingContainer.push_back(barrel);
0515 } else if (wConfig.wCondition == CentralInserting) {
0516 existingContainer.push_back(barrel);
0517 existingContainer.push_back(existingVolumeCp);
0518 }
0519
0520 existingVolumeCp =
0521 !existingContainer.empty()
0522 ? tvHelper->createContainerTrackingVolume(gctx, existingContainer)
0523 : existingVolumeCp;
0524
0525 std::vector<TrackingVolumePtr> totalContainer;
0526
0527 if (wConfig.wCondition == Attaching ||
0528 wConfig.wCondition == CentralWrapping ||
0529 wConfig.wCondition == CentralInserting) {
0530 if (nEndcap) {
0531 totalContainer.push_back(nEndcap);
0532 }
0533 totalContainer.push_back(existingVolumeCp);
0534 if (pEndcap) {
0535 totalContainer.push_back(pEndcap);
0536 }
0537 } else if (wConfig.wCondition == Inserting && volume) {
0538 totalContainer.push_back(volume);
0539 totalContainer.push_back(existingVolumeCp);
0540 } else if (wConfig.wCondition == Wrapping && volume) {
0541 totalContainer.push_back(existingVolumeCp);
0542 totalContainer.push_back(volume);
0543 } else {
0544 ACTS_ERROR("Misconfiguration in volume building detected.");
0545 return nullptr;
0546 }
0547
0548 volume = tvHelper->createContainerTrackingVolume(gctx, totalContainer);
0549 }
0550
0551 return volume;
0552 }
0553
0554
0555 Acts::VolumeConfig Acts::CylinderVolumeBuilder::analyzeContent(
0556 const GeometryContext& gctx, const LayerVector& lVector,
0557 const MutableTrackingVolumeVector& mtvVector) const {
0558
0559
0560
0561 VolumeConfig lConfig;
0562
0563 if (!lVector.empty() || !mtvVector.empty()) {
0564
0565 lConfig.present = true;
0566
0567 for (auto& layer : lVector) {
0568
0569 double thickness = layer->thickness();
0570
0571 const Vector3& center = layer->surfaceRepresentation().center(gctx);
0572
0573 const CylinderLayer* cLayer =
0574 dynamic_cast<const CylinderLayer*>(layer.get());
0575 if (cLayer != nullptr) {
0576
0577 double rMinC =
0578 cLayer->surfaceRepresentation().bounds().get(CylinderBounds::eR) -
0579 0.5 * thickness;
0580 double rMaxC =
0581 cLayer->surfaceRepresentation().bounds().get(CylinderBounds::eR) +
0582 0.5 * thickness;
0583
0584 double hZ = cLayer->surfaceRepresentation().bounds().get(
0585 CylinderBounds::eHalfLengthZ);
0586 lConfig.rMin =
0587 std::min(lConfig.rMin, rMinC - m_cfg.layerEnvelopeR.first);
0588 lConfig.rMax =
0589 std::max(lConfig.rMax, rMaxC + m_cfg.layerEnvelopeR.second);
0590 lConfig.zMin =
0591 std::min(lConfig.zMin, center.z() - hZ - m_cfg.layerEnvelopeZ);
0592 lConfig.zMax =
0593 std::max(lConfig.zMax, center.z() + hZ + m_cfg.layerEnvelopeZ);
0594 }
0595
0596 const RadialBounds* dBounds = dynamic_cast<const RadialBounds*>(
0597 &(layer->surfaceRepresentation().bounds()));
0598 if (dBounds != nullptr) {
0599
0600 double rMinD = dBounds->rMin();
0601 double rMaxD = dBounds->rMax();
0602 double zMinD = center.z() - 0.5 * thickness;
0603 double zMaxD = center.z() + 0.5 * thickness;
0604 lConfig.rMin =
0605 std::min(lConfig.rMin, rMinD - m_cfg.layerEnvelopeR.first);
0606 lConfig.rMax =
0607 std::max(lConfig.rMax, rMaxD + m_cfg.layerEnvelopeR.second);
0608 lConfig.rMin = std::max(0.0, lConfig.rMin);
0609 lConfig.zMin = std::min(lConfig.zMin, zMinD - m_cfg.layerEnvelopeZ);
0610 lConfig.zMax = std::max(lConfig.zMax, zMaxD + m_cfg.layerEnvelopeZ);
0611 }
0612 }
0613 for (auto& volume : mtvVector) {
0614 const CylinderVolumeBounds* cvBounds =
0615 dynamic_cast<const CylinderVolumeBounds*>(&volume->volumeBounds());
0616 if (cvBounds != nullptr) {
0617 lConfig.rMin =
0618 std::min(lConfig.rMin, cvBounds->get(CylinderVolumeBounds::eMinR));
0619 lConfig.rMax =
0620 std::max(lConfig.rMax, cvBounds->get(CylinderVolumeBounds::eMaxR));
0621 lConfig.zMin = std::min(
0622 lConfig.zMin, -cvBounds->get(CylinderVolumeBounds::eHalfLengthZ));
0623 lConfig.zMax = std::max(
0624 lConfig.zMax, cvBounds->get(CylinderVolumeBounds::eHalfLengthZ));
0625 }
0626 }
0627 }
0628
0629
0630 lConfig.layers = lVector;
0631
0632 lConfig.volumes = mtvVector;
0633
0634 if (m_cfg.buildToRadiusZero) {
0635 ACTS_VERBOSE("This layer builder is configured to build to the beamline.");
0636 lConfig.rMin = 0.;
0637 }
0638
0639
0640 return lConfig;
0641 }