Analysis Software
Documentation for sPHENIX simulation software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
DetectorVolumeBuilder.cpp
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file DetectorVolumeBuilder.cpp
1 // This file is part of the Acts project.
2 //
3 // Copyright (C) 2023 CERN for the benefit of the Acts project
4 //
5 // This Source Code Form is subject to the terms of the Mozilla Public
6 // License, v. 2.0. If a copy of the MPL was not distributed with this
7 // file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 
10 
19 
20 #include <iterator>
21 #include <map>
22 #include <stdexcept>
23 #include <utility>
24 #include <vector>
25 
28  std::unique_ptr<const Acts::Logger> mlogger)
29  : IDetectorComponentBuilder(), m_cfg(cfg), m_logger(std::move(mlogger)) {
30  if (m_cfg.externalsBuilder == nullptr) {
31  throw std::invalid_argument(
32  "DetectorVolumeBuilder: no external structure builder defined.");
33  }
34 }
35 
38  const GeometryContext& gctx) const {
39  // The outgoing root volumes
40  std::vector<std::shared_ptr<DetectorVolume>> rootVolumes;
41  // Screen printout of the auxiliary information
42  if (not m_cfg.auxiliary.empty()) {
43  ACTS_DEBUG(m_cfg.auxiliary);
44  }
45  ACTS_DEBUG("Building a volume with name '" << m_cfg.name << "'.");
46 
47  // Get transform and bounds from the volume
49  m_cfg.externalsBuilder->construct(gctx);
50 
51  // Although only a single volume, describe it as a
52  // container shell for further processing
53  DetectorComponent::PortalContainer portalContainer;
54  // The detector volume to be constructed
55  std::shared_ptr<DetectorVolume> dVolume = nullptr;
56  // If there are no internals, the volume is fully defined
57  if (m_cfg.internalsBuilder == nullptr) {
58  ACTS_VERBOSE("No internal structure present.")
59  // Construct the DetectorVolume
61  portalGenerator, gctx, m_cfg.name, transform, std::move(bounds),
62  tryAllPortals());
63  } else {
64  // Internal structure is present
65  ACTS_VERBOSE("Internal structure is being built.")
66  auto [surfaces, volumes, surfacesUpdator, volumeUpdator] =
67  m_cfg.internalsBuilder->construct(gctx);
68 
69  // Add the internally created volumes as root volumes
70  if (m_cfg.addInternalsToRoot) {
71  for (const auto& v : volumes) {
72  rootVolumes.push_back(v);
73  }
74  }
75  // Construct the DetectorVolume
77  portalGenerator, gctx, m_cfg.name, transform, std::move(bounds),
78  surfaces, volumes, std::move(volumeUpdator),
79  std::move(surfacesUpdator));
80  }
81  // All portals are defined and build the current shell
82  for (auto [ip, p] : enumerate(dVolume->portalPtrs())) {
83  portalContainer[ip] = p;
84  }
85 
86  // Assign the geometry ids if configured to do so
87  if (m_cfg.geoIdGenerator != nullptr) {
88  ACTS_DEBUG("Assigning geometry ids to the detector volume");
89  auto cache = m_cfg.geoIdGenerator->generateCache();
90  m_cfg.geoIdGenerator->assignGeometryId(cache, *dVolume);
91  }
92 
93  // Add to the root volume collection if configured
94  rootVolumes.push_back(dVolume);
95  // The newly built volume is the single produced volume
97  {dVolume},
98  portalContainer,
99  RootDetectorVolumes{rootVolumes, tryRootVolumes()}};
100 }