26 std::unique_ptr<const Logger> logger)
41 std::unique_ptr<const Logger> newLogger) {
42 m_logger = std::move(newLogger);
45 std::shared_ptr<Acts::TrackingVolume>
49 ACTS_DEBUG(
"Configured to build volume : " << m_cfg.volumeName);
51 ACTS_DEBUG(
"- will wrap/enclose : " << existingVolume->volumeName());
68 if (m_cfg.layerBuilder) {
70 negativeLayers = m_cfg.layerBuilder->negativeLayers(gctx);
72 centralLayers = m_cfg.layerBuilder->centralLayers(gctx);
74 positiveLayers = m_cfg.layerBuilder->positiveLayers(gctx);
79 if (m_cfg.ctVolumeBuilder) {
80 centralVolumes = m_cfg.ctVolumeBuilder->centralVolumes();
89 &existingVolume->volumeBounds());
97 existingVolume->center().z() -
100 existingVolume->center().z() +
107 if (externalBounds) {
111 if (ocvBounds !=
nullptr) {
145 wConfig.
nVolumeConfig = analyzeContent(gctx, negativeLayers, {});
146 wConfig.
cVolumeConfig = analyzeContent(gctx, centralLayers, centralVolumes);
147 wConfig.
pVolumeConfig = analyzeContent(gctx, positiveLayers, {});
149 std::string layerConfiguration =
"|";
152 ACTS_VERBOSE(
"Negative layers are present: rmin, rmax | zmin, zmax = "
155 layerConfiguration +=
" Negative Endcap |";
159 ACTS_VERBOSE(
"Central layers are present: rmin, rmax | zmin, zmax = "
162 layerConfiguration +=
" Barrel |";
166 ACTS_VERBOSE(
"Positive layers are present: rmin, rmax | zmin, zmax = "
169 layerConfiguration +=
" Positive Endcap |";
172 ACTS_DEBUG(
"Layer configuration is : " << layerConfiguration);
176 ACTS_VERBOSE(
"Configurations after layer parsing " <<
'\n'
180 ACTS_VERBOSE(
"Configuration after container synchronisation "
186 ACTS_VERBOSE(
"Configuration after wrapping, insertion, attachment "
197 auto tvHelper = m_cfg.trackingVolumeHelper;
201 ? tvHelper->createTrackingVolume(
206 m_cfg.volumeName +
"::Barrel")
216 if (not endcapConfig) {
220 if (m_cfg.checkRingLayout) {
221 ACTS_DEBUG(
"Configured to check for ring layout - parsing layers.");
223 std::vector<double> innerRadii = {};
224 std::vector<double> outerRadii = {};
225 for (
const auto& elay : endcapConfig.layers) {
227 &(elay->surfaceRepresentation().bounds()));
228 if (discBounds !=
nullptr) {
231 double rMin = discBounds->rMin();
232 auto innerSearch = std::find_if(
233 innerRadii.begin(), innerRadii.end(), [&](
double reference) {
236 if (innerSearch == innerRadii.end()) {
237 innerRadii.push_back(rMin);
240 double rMax = discBounds->rMax();
241 auto outerSearch = std::find_if(
242 outerRadii.begin(), outerRadii.end(), [&](
double reference) {
245 if (outerSearch == outerRadii.end()) {
246 outerRadii.push_back(rMax);
251 if (innerRadii.size() == outerRadii.size() and not innerRadii.empty()) {
252 bool consistent =
true;
254 std::vector<double> interRadii = {};
255 for (
int ir = 1;
ir < int(innerRadii.size()); ++
ir) {
257 if (outerRadii[
ir - 1] < innerRadii[
ir]) {
258 interRadii.push_back(0.5 * (outerRadii[ir - 1] + innerRadii[ir]));
266 ACTS_DEBUG(
"Ring layout detection: " << innerRadii.size()
269 std::vector<std::pair<double, double>> volumeRminRmax = {};
270 for (
unsigned int ii = 0; ii < interRadii.size(); ++ii) {
272 volumeRminRmax.push_back({endcapConfig.rMin, interRadii[ii]});
274 if (ii + 1 < interRadii.size()) {
275 volumeRminRmax.push_back({interRadii[ii], interRadii[ii + 1]});
277 volumeRminRmax.push_back({interRadii[ii], endcapConfig.rMax});
281 std::vector<LayerVector>(innerRadii.size(),
LayerVector());
283 for (
const auto& elay : endcapConfig.layers) {
286 elay->surfaceRepresentation().binningPositionValue(gctx,
binR);
288 auto ringVolume = std::find_if(
289 volumeRminRmax.begin(), volumeRminRmax.end(),
290 [&](
const auto& reference) {
291 return (test > reference.first and test < reference.second);
293 if (ringVolume != volumeRminRmax.end()) {
294 unsigned int ringBin =
295 std::distance(volumeRminRmax.begin(), ringVolume);
296 ringLayers[ringBin].push_back(elay);
302 std::vector<TrackingVolumePtr> endcapContainer;
304 for (
auto& rLayers : ringLayers) {
305 ACTS_DEBUG(
" - ring volume " << ir <<
" with " << rLayers.size()
306 <<
" layers, and rmin/rmax = "
307 << volumeRminRmax[
ir].first <<
"/"
308 << volumeRminRmax[
ir].second);
309 endcapContainer.push_back(tvHelper->createTrackingVolume(
310 gctx, rLayers, centralConfig.
volumes, m_cfg.volumeMaterial,
311 volumeRminRmax[ir].first, volumeRminRmax[ir].second,
312 endcapConfig.zMin, endcapConfig.zMax,
313 m_cfg.volumeName + endcapName + std::string(
"::Ring") +
318 return tvHelper->createContainerTrackingVolume(gctx, endcapContainer);
324 return tvHelper->createTrackingVolume(
325 gctx, endcapConfig.layers, centralConfig.
volumes, m_cfg.volumeMaterial,
326 endcapConfig.rMin, endcapConfig.rMax, endcapConfig.zMin,
327 endcapConfig.zMax, m_cfg.volumeName + endcapName);
345 std::vector<TrackingVolumePtr> volumesContainer;
347 volumesContainer.push_back(nEndcap);
350 if (not m_cfg.buildToRadiusZero) {
351 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[0],
354 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[1],
356 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[2],
358 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[3],
363 volumesContainer.push_back(barrel);
366 if (not m_cfg.buildToRadiusZero) {
367 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[0],
370 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[1],
372 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[3],
374 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[4],
378 volumesContainer.push_back(pEndcap);
381 if (not m_cfg.buildToRadiusZero) {
382 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[0],
385 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[1],
387 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[4],
389 volume->assignBoundaryMaterial(m_cfg.boundaryMaterial[5],
394 volumesContainer.size() > 1
395 ? tvHelper->createContainerTrackingVolume(gctx, volumesContainer)
399 volume = nEndcap ? nEndcap : (barrel ? barrel : pEndcap);
405 if (existingVolumeCp) {
407 std::vector<TrackingVolumePtr> existingContainer;
410 auto fGap = tvHelper->createGapTrackingVolume(
414 false, m_cfg.volumeName +
"::fGap");
416 existingContainer.push_back(fGap);
418 existingContainer.push_back(existingVolumeCp);
421 auto sGap = tvHelper->createGapTrackingVolume(
425 false, m_cfg.volumeName +
"::sGap");
427 existingContainer.push_back(sGap);
432 existingContainer.size() > 1
433 ? tvHelper->createContainerTrackingVolume(gctx, existingContainer)
438 existingContainer.clear();
440 existingContainer.push_back(existingVolumeCp);
441 existingContainer.push_back(barrel);
443 existingContainer.push_back(barrel);
444 existingContainer.push_back(existingVolumeCp);
448 !existingContainer.empty()
449 ? tvHelper->createContainerTrackingVolume(gctx, existingContainer)
452 std::vector<TrackingVolumePtr> totalContainer;
458 totalContainer.push_back(nEndcap);
460 totalContainer.push_back(existingVolumeCp);
462 totalContainer.push_back(pEndcap);
465 totalContainer.push_back(volume);
466 totalContainer.push_back(existingVolumeCp);
468 totalContainer.push_back(existingVolumeCp);
469 totalContainer.push_back(volume);
471 ACTS_ERROR(
"Misconfiguration in volume building detected.");
475 volume = tvHelper->createContainerTrackingVolume(gctx, totalContainer);
490 if (!lVector.empty() || !mtvVector.empty()) {
494 for (
auto&
layer : lVector) {
498 const Vector3D& center =
layer->surfaceRepresentation().center(gctx);
502 if (cLayer !=
nullptr) {
514 std::min(lConfig.
rMin, rMinC - m_cfg.layerEnvelopeR.first);
516 std::max(lConfig.
rMax, rMaxC + m_cfg.layerEnvelopeR.second);
518 std::min(lConfig.
zMin, center.z() - hZ - m_cfg.layerEnvelopeZ);
520 std::max(lConfig.
zMax, center.z() + hZ + m_cfg.layerEnvelopeZ);
524 &(
layer->surfaceRepresentation().bounds()));
525 if (dBounds !=
nullptr) {
527 double rMinD = dBounds->
rMin();
528 double rMaxD = dBounds->
rMax();
529 double zMinD = center.z() - 0.5 *
thickness;
530 double zMaxD = center.z() + 0.5 *
thickness;
532 std::min(lConfig.
rMin, rMinD - m_cfg.layerEnvelopeR.first);
534 std::max(lConfig.
rMax, rMaxD + m_cfg.layerEnvelopeR.second);
539 for (
auto&
volume : mtvVector) {
542 if (cvBounds !=
nullptr) {
560 if (m_cfg.buildToRadiusZero) {
561 ACTS_VERBOSE(
"This layer builder is configured to build to the beamline.");