ATLAS Offline Software
Loading...
Searching...
No Matches
MuonInertMaterialBuilderImpl.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2023 CERN for the benefit of the ATLAS collaboration
3*/
4// Muon
6
7// MuonSpectrometer include
10
11// STD
12#include <fstream>
13#include <iostream>
14#include <map>
15
16#include "GeoModelKernel/GeoShape.h"
17#include "GeoModelKernel/GeoVolumeCursor.h"
18
19// constructor
21 const std::string& t, const std::string& n, const IInterface* p)
23
24// Athena standard methods
25// initialize
27
29 ATH_MSG_INFO(" option Simplify(Muon)GeometryToLayers no longer maintained ");
30 }
31 ATH_MSG_INFO( " initialize() successful");
32 return StatusCode::SUCCESS;
33}
34
36 Muon::MuonInertMaterialBuilderImpl::buildDetachedTrackingVolumesImpl(const PVConstLink& treeTop, bool blend) const {
37
38 if (!treeTop) {
39 throw std::runtime_error("No tree top has been parsed");
40 }
41 // collect inert material objects
42 DetachedVolVec mInert{};
43 // retrieve muon station prototypes from GeoModel
44 auto msTypes = buildDetachedTrackingVolumeTypes(treeTop, blend);
45 ATH_MSG_DEBUG(" obtained " << msTypes.size() << " prototypes");
46
47
48 for (auto& [msTV, transforms]: msTypes) {
49 std::string msTypeName = msTV->name();
50 for (Amg::Transform3D& combTr : transforms) {
51 std::unique_ptr<Trk::DetachedTrackingVolume> newStat{msTV->clone(msTypeName, combTr)};
52 mInert.push_back(std::move(newStat));
53 }
54 }
55 ATH_MSG_DEBUG(" returns " << mInert.size() << " objects (detached volumes)");
56
57 return mInert;
58}
59
60
63
66 GeoVolumeCursor vol(top);
67 while (!vol.atEnd()) {
68 const GeoVPhysVol* cv = vol.getVolume();
69 const GeoLogVol* clv = cv->getLogVol();
70 const std::string_view vname = clv->getName();
71 if (vname.size() > 7 && vname.substr(vname.size() - 7, 7) ==
72 "Station") { // do nothing, active station
73 } else {
74 bool accepted = true;
75 if (vname.substr(0, 3) == "BAR" || vname.substr(0, 2) == "BT" ||
76 vname.substr(0, 6) == "EdgeBT" || vname.substr(0, 6) == "HeadBT"){
77 accepted = m_buildBT;
78 } else if (vname.substr(0, 3) == "ECT") {
79 accepted = m_buildECT;
80 } else if (vname.substr(0, 4) == "Feet" ||
81 (vname.size() > 7 && (vname.substr(3, 4) == "Feet" || vname.substr(4, 4) == "Feet"))) {
82 accepted = m_buildFeets;
83 } else if (vname.substr(0, 4) == "Rail") {
84 accepted = m_buildRails > 0;
85 } else if (vname.substr(0, 1) == "J") {
86 accepted = m_buildShields > 0;
87 // NSW build inertmaterial for spacer frame, aluminium HUB, NJD disk
88 // and A plate
89 } else if (vname.substr(0, 3) == "NSW" && vname.substr(1, 6) == "Spacer") {
90 accepted = m_buildNSWInert;
91 } else if (vname.substr(0, 3) == "NSW" && vname.substr(1, 2) == "Al") {
92 accepted = m_buildNSWInert;
93 } else if (vname.substr(0, 3) == "NJD"){
94 accepted = m_buildNSWInert;
95 } else if (vname.substr(0, 1) == "A" && vname.substr(1, 5) == "Plate"){
96 accepted = m_buildNSWInert;
97 // strange NSW will be anyway build
98 } else if (vname.substr(0, 1) != "J") {
99 accepted = m_buildSupports > 0;
100 }
101 if (!accepted) {
102 ATH_MSG_VERBOSE(" INERT muon object found and rejected :" << vname);
103 vol.next();
104 continue;
105 }
106 ATH_MSG_VERBOSE(" INERT muon object found and accepted :" << vname);
107
108 if (msg().level() == MSG::VERBOSE)
109 printInfo(cv);
110
111 std::vector<std::pair<const GeoVPhysVol*, std::vector<Amg::Transform3D>>> vols;
112
113 bool simpleTree = false;
114 if (!cv->getNChildVols()) {
115 if (!m_gmBrowser.findNamePattern(cv, "Sensitive")) {
116 std::vector<Amg::Transform3D> volTr;
117 volTr.push_back(vol.getTransform());
118 vols.emplace_back(cv, volTr);
119 simpleTree = true;
120 }
121 } else {
122 getObjsForTranslation(cv, Amg::Transform3D::Identity(), vols);
123 }
124
125 for (auto& [physVol, physVolTrfs]: vols) {
126 std::string protoName(vname);
127 if (!simpleTree)
128 protoName += physVol->getLogVol()->getName();
129 ATH_MSG_VERBOSE(" check in:"<< protoName << ", made of "
130 << physVol->getLogVol()->getMaterial()->getName()
131 << " x0 " << physVol->getLogVol()->getMaterial()->getRadLength()
132 << "," << physVol->getLogVol()->getShape()->type());
133
134 bool found = false;
135 for (auto& obj : objs) {
136 if (protoName == obj.first->name()) { // found in another branch already ?
137 found = true;
138 if (simpleTree) {
139 obj.second.push_back(vol.getTransform());
140 } else {
141 obj.second.insert(obj.second.end(),
142 std::make_move_iterator(physVolTrfs.begin()),
143 std::make_move_iterator(physVolTrfs.end()));
144 }
145 }
146 }
147 if (found) {
148 continue;
149 }
150 // envelope creation & simplification done with
151 // TrkDetDescrGeoModelCnv helpers
152 auto newType = m_volumeConverter.translate(physVol, m_simplify, blend, m_blendLimit);
153 if (newType) {
154 const std::string volName = newType->volumeName();
155 auto typeDet = std::make_unique<Trk::DetachedTrackingVolume>(volName, std::move(newType));
156 objs.emplace_back(std::move(typeDet), std::move(physVolTrfs));
157 } else {
158 ATH_MSG_WARNING("volume not translated: " << vname);
159 }
160 } // end new object
161 }
162 vol.next();
163 }
164
165 int count = 0;
166 for (auto& obj : objs)
167 count += obj.second.size();
168
169 ATH_MSG_DEBUG(" returns " << objs.size()<< " prototypes, to be cloned into " << count << " objects");
170
171 return objs;
172}
173
175 const GeoVPhysVol* pv) const {
176 const GeoLogVol* lv = pv->getLogVol();
177 ATH_MSG_VERBOSE("New Muon Inert Object:"
178 << lv->getName() << ", made of "
179 << lv->getMaterial()->getName() << " x0 "
180 << lv->getMaterial()->getRadLength() << ","
181 << lv->getShape()->type());
182 m_geoShapeConverter.decodeShape(lv->getShape());
183 printChildren(pv);
184}
185
187 const GeoVPhysVol* pv) const {
188 // subcomponents
189 unsigned int nc = pv->getNChildVols();
190 for (unsigned int ic = 0; ic < nc; ic++) {
191 Amg::Transform3D transf = pv->getXToChildVol(ic);
192
193 const GeoVPhysVol* cv = &(*(pv->getChildVol(ic)));
194 const GeoLogVol* clv = cv->getLogVol();
195 ATH_MSG_VERBOSE(" ");
197 "subcomponent:"
198 << ic << ":" << clv->getName() << ", made of "
199 << clv->getMaterial()->getName() << " x0 "
200 << clv->getMaterial()->getRadLength() << " , "
201 << clv->getShape()->type() << "," << transf.translation().x() << " "
202 << transf.translation().y() << " " << transf.translation().z());
203
204 m_geoShapeConverter.decodeShape(clv->getShape());
205
206 printChildren(cv);
207 }
208}
209
211 const GeoVPhysVol* pv, const Amg::Transform3D& transform,
212 std::vector<std::pair<const GeoVPhysVol*, std::vector<Amg::Transform3D>>>&
213 vols) const {
214 // subcomponents
215 unsigned int nc = pv->getNChildVols();
216 ATH_MSG_VERBOSE(" INERT getObjsForTranslation from:"
217 << pv->getLogVol()->getName() << ","
218 << pv->getLogVol()->getMaterial()->getName()
219 << ", looping over " << nc << " children");
220 for (unsigned int ic = 0; ic < nc; ic++) {
221 Amg::Transform3D transf = pv->getXToChildVol(ic);
222 const GeoVPhysVol* cv = &(*(pv->getChildVol(ic)));
223 const GeoLogVol* clv = cv->getLogVol();
224 if (clv->getMaterial()->getDensity() > 0. &&
225 m_gmBrowser.findNamePattern(cv, "Sensitive"))
226 continue; // skip sensitive material branches
227 if (!cv->getNChildVols()) {
228 bool found = false;
229 for (auto& vol : vols) {
230 if (clv->getName() == vol.first->getLogVol()->getName()) {
231 if (m_gmBrowser.compareGeoVolumes(cv, vol.first, 1.e-3) !=
232 0)
234 "INERT name branch matching differences detected "
235 "in:"
236 << clv->getName());
237 found = true;
238 vol.second.push_back(transform * transf);
239 break;
240 }
241 }
242 if (!found) {
243 std::vector<Amg::Transform3D> volTr;
244 volTr.push_back(transform * transf);
245 vols.emplace_back(cv, volTr);
246 ATH_MSG_VERBOSE("INERT new volume added:"
247 << clv->getName() << ","
248 << clv->getMaterial()->getName());
249 if (msg().level() <= MSG::VERBOSE)
250 printInfo(cv);
251 }
252 } else {
253 getObjsForTranslation(cv, transform * transf, vols);
254 }
255 }
256}
#define ATH_MSG_INFO(x)
#define ATH_MSG_VERBOSE(x)
#define ATH_MSG_WARNING(x)
#define ATH_MSG_DEBUG(x)
@ top
AthAlgTool(const std::string &type, const std::string &name, const IInterface *parent)
Constructor with parameters:
std::vector< std::unique_ptr< Trk::DetachedTrackingVolume > > DetachedVolVec
Trk::GeoShapeConverter m_geoShapeConverter
shape converter
Trk::VolumeConverter m_volumeConverter
gm->trk volume helper
DetachedVolVec buildDetachedTrackingVolumesImpl(const PVConstLink &treeTop, bool blend) const
void getObjsForTranslation(const GeoVPhysVol *pv, const Amg::Transform3D &, std::vector< std::pair< const GeoVPhysVol *, std::vector< Amg::Transform3D > > > &vols) const
Method extracting material objects from GeoModel tree.
Trk::GMTreeBrowser m_gmBrowser
gm tree helper
MuonInertMaterialBuilderImpl(const std::string &, const std::string &, const IInterface *)
Constructor.
DetachedVolumeVecWithTrfs buildDetachedTrackingVolumeTypes(const PVConstLink &top, bool blend) const
virtual StatusCode initialize() override
AlgTool initialize method.
void printInfo(const GeoVPhysVol *pv) const
Dump from GeoModel tree.
void printChildren(const GeoVPhysVol *pv) const
std::vector< std::pair< std::unique_ptr< Trk::DetachedTrackingVolume >, std::vector< Amg::Transform3D > > > DetachedVolumeVecWithTrfs
Method creating material object prototypes.
int count(std::string s, const std::string &regx)
count how many occurances of a regx are in a string
Definition hcg.cxx:146
Eigen::Affine3d Transform3D
Ensure that the ATLAS eigen extensions are properly loaded.
MsgStream & msg
Definition testRead.cxx:32