ATLAS Offline Software
Loading...
Searching...
No Matches
SCT_DetectorFactory.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3*/
4
5//
6// SCT_DetectorFactory: This is the top level node
7//
8
9
10#include "SCT_DetectorFactory.h"
11
13
15
16//
17// GeoModel include files:
18//
21#include "GeoModelKernel/GeoAlignableTransform.h"
22#include "GeoModelKernel/GeoDefinitions.h"
23#include "GeoModelKernel/GeoIdentifierTag.h"
24#include "GeoModelKernel/GeoLogVol.h"
25#include "GeoModelKernel/GeoMaterial.h"
26#include "GeoModelKernel/GeoNameTag.h"
27#include "GeoModelKernel/GeoPhysVol.h"
28#include "GeoModelKernel/GeoShape.h"
29#include "GeoModelKernel/GeoShapeShift.h"
30#include "GeoModelKernel/GeoShapeUnion.h"
31#include "GeoModelKernel/GeoTransform.h"
32#include "GeoModelKernel/GeoTube.h"
33#include "GeoModelKernel/GeoVPhysVol.h"
35
39
43
44#include "SCT_Barrel.h"
45#include "SCT_DataBase.h"
46#include "SCT_Forward.h"
48#include "SCT_GeometryManager.h"
50#include "SCT_Identifier.h"
51#include "SCT_MaterialManager.h"
52
54
56
57#include "GaudiKernel/ISvcLocator.h"
58#include "GaudiKernel/SystemOfUnits.h"
59
60#include <iomanip>
61#include <iostream>
62#include <string>
63
66
68 const SCT_Options & options)
69 : InDetDD::DetectorFactoryBase(athenaComps),
71{
72
73 // Create the detector manager
75
76 // Create the database
77 m_db = std::make_unique<SCT_DataBase>(athenaComps);
78
79 // Create the material manager
80 m_materials = std::make_unique<SCT_MaterialManager>(m_db.get());
81
82 // Create the Si common items
83 std::unique_ptr<InDetDD::SiCommonItems> commonItems{std::make_unique<InDetDD::SiCommonItems>(athenaComps->getIdHelper())};
84
85 // Create the geometry manager.
86 m_geometryManager = std::make_unique<SCT_GeometryManager>(m_db.get());
87 m_geometryManager->setOptions(options);
88 m_geometryManager->setCommonItems(commonItems.get());
89
90 // Add SiCommonItems to SCT_DetectorManager to hold and delete it.
91 m_detectorManager->setCommonItems(std::move(commonItems));
92
93 m_useDynamicAlignFolders = options.dynamicAlignFolders();
94
95 // Set Version information
96 // Get the geometry tag
97 DecodeVersionKey versionKey(geoDbTagSvc(),"SCT");
98 IRDBRecordset_ptr switchSet
99 = rdbAccessSvc()->getRecordsetPtr("SctSwitches", versionKey.tag(), versionKey.node());
100 const IRDBRecord *switches = (*switchSet)[0];
101
102 std::string layout = "Final";
103 std::string description;
104 if (!switches->isFieldNull("LAYOUT")) {
105 layout = switches->getString("LAYOUT");
106 }
107 if (!switches->isFieldNull("DESCRIPTION")) {
108 description = switches->getString("DESCRIPTION");
109 }
110
111 std::string versionTag = rdbAccessSvc()->getChildTag("SCT", versionKey.tag(), versionKey.node());
112 std::string versionName = switches->getString("VERSIONNAME");
113 int versionMajorNumber = 3;
114 int versionMinorNumber = 6;
115 int versionPatchNumber = 0;
116 InDetDD::Version version(versionTag,
117 versionName,
118 layout,
120 versionMajorNumber,
121 versionMinorNumber,
122 versionPatchNumber);
123 m_detectorManager->setVersion(version);
124
125}
126
127
129{
130 // NB the detector manager (m_detectorManager)is stored in the detector store by the
131 // Tool and so we don't delete it.
132}
133
134void SCT_DetectorFactory::create(GeoPhysVol *world)
135{
136
137 msg(MSG::INFO) << "Building SCT Detector." << endmsg;
138 msg(MSG::INFO) << " " << m_detectorManager->getVersion().fullDescription() << endmsg;
139
140 // Change precision.
141 int oldPrecision = std::cout.precision(6);
142
143 // The tree tops get added to world. We name it "indet" though.
144 GeoPhysVol *indet = world;
145
146 const SCT_GeneralParameters * sctGeneral = m_geometryManager->generalParameters();
147
148 GeoTrf::Transform3D sctTransform = sctGeneral->partTransform("SCT");
149
150 std::string barrelLabel = "Barrel";
151 std::string forwardPlusLabel = "EndcapA";
152 std::string forwardMinusLabel = "EndcapC";
153
154 bool barrelPresent = sctGeneral->partPresent(barrelLabel);
155 bool forwardPlusPresent = sctGeneral->partPresent(forwardPlusLabel);
156 bool forwardMinusPresent = sctGeneral->partPresent(forwardMinusLabel);
157
158
159
160 //
161 // The Barrel
162 //
163 if (barrelPresent) {
164
165 msg(MSG::DEBUG) << "Building the SCT Barrel." << endmsg;
166
167 m_detectorManager->numerology().addBarrel(0);
168
169 // Create the SCT Barrel
170 SCT_Barrel sctBarrel("SCT_Barrel", m_detectorManager, m_geometryManager.get(), m_materials.get(), nullptr, nullptr, nullptr);
171
172 SCT_Identifier id{m_geometryManager->athenaComps()->getIdHelper()};
173 id.setBarrelEC(0);
174 GeoVPhysVol * barrelPV = sctBarrel.build(id);
175 GeoAlignableTransform * barrelTransform = new GeoAlignableTransform(sctTransform * sctGeneral->partTransform(barrelLabel));
176
177 //indet->add(new GeoNameTag("SCT_Barrel"));
178 // The name tag here is what is used by the GeoModel viewer.
179 GeoNameTag *topLevelNameTag = new GeoNameTag("SCT");
180 indet->add(topLevelNameTag);
181 indet->add(new GeoIdentifierTag(0));
182 indet->add(barrelTransform);
183 indet->add(barrelPV);
184 m_detectorManager->addTreeTop(barrelPV);
185
186 // Store alignable transform
187 m_detectorManager->addAlignableTransform(3, id.getWaferId(), barrelTransform, barrelPV);
188
189 }
190
191 //
192 // The Positive Z Endcap (EndcapA)
193 //
194 if (forwardPlusPresent) {
195
196 msg(MSG::DEBUG) << "Building the SCT Endcap A (positive z)." << endmsg;
197
198 m_detectorManager->numerology().addEndcap(2);
199
200 // Create the Forward
201 SCT_Forward sctForwardPlus("SCT_ForwardA", +2, m_detectorManager, m_geometryManager.get(), m_materials.get(), nullptr, nullptr, nullptr);
202
203 SCT_Identifier idFwdPlus{m_geometryManager->athenaComps()->getIdHelper()};
204 idFwdPlus.setBarrelEC(2);
205 GeoVPhysVol * forwardPlusPV = sctForwardPlus.build(idFwdPlus);
206 GeoTrf::Transform3D fwdTransformPlus(sctTransform
207 * sctGeneral->partTransform(forwardPlusLabel)
208 * GeoTrf::TranslateZ3D(sctForwardPlus.zCenter()));
209 GeoAlignableTransform * fwdGeoTransformPlus = new GeoAlignableTransform(fwdTransformPlus);
210
211 //indet->add(new GeoNameTag("SCT_ForwardPlus"));
212 // The name tag here is what is used by the GeoModel viewer.
213 GeoNameTag *topLevelNameTag = new GeoNameTag("SCT");
214 indet->add(topLevelNameTag);
215 indet->add(new GeoIdentifierTag(2));
216 indet->add(fwdGeoTransformPlus);
217 indet->add(forwardPlusPV);
218 m_detectorManager->addTreeTop(forwardPlusPV);
219
220 // Store alignable transform
221 m_detectorManager->addAlignableTransform(3, idFwdPlus.getWaferId(), fwdGeoTransformPlus, forwardPlusPV);
222 }
223
224 //
225 // The Negative Z Endcap (EndcapC)
226 //
227
228 if (forwardMinusPresent) {
229
230 msg(MSG::DEBUG) << "Building the SCT Endcap C (negative z)." << endmsg;
231
232 m_detectorManager->numerology().addEndcap(-2);
233
234 SCT_Forward sctForwardMinus("SCT_ForwardC", -2, m_detectorManager, m_geometryManager.get(), m_materials.get(), nullptr, nullptr, nullptr);
235
236 SCT_Identifier idFwdMinus{m_geometryManager->athenaComps()->getIdHelper()};
237 idFwdMinus.setBarrelEC(-2);
238 GeoVPhysVol * forwardMinusPV = sctForwardMinus.build(idFwdMinus);
239
240 GeoTrf::Transform3D rot;
241 rot = GeoTrf::RotateY3D(180 * Gaudi::Units::degree);
242
243 GeoTrf::Transform3D fwdTransformMinus(sctTransform
244 * sctGeneral->partTransform(forwardMinusLabel)
245 * rot
246 * GeoTrf::TranslateZ3D(sctForwardMinus.zCenter()));
247 GeoAlignableTransform * fwdGeoTransformMinus = new GeoAlignableTransform(fwdTransformMinus);
248
249 //indet->add(new GeoNameTag("SCT_ForwardMinus"));
250 // The name tag here is what is used by the GeoModel viewer.
251 GeoNameTag *topLevelNameTag = new GeoNameTag("SCT");
252 indet->add(topLevelNameTag);
253 indet->add(new GeoIdentifierTag(-2));
254 indet->add(fwdGeoTransformMinus);
255 indet->add(forwardMinusPV);
256 m_detectorManager->addTreeTop(forwardMinusPV);
257
258
259 // Store alignable transform
260 m_detectorManager->addAlignableTransform(3, idFwdMinus.getWaferId(), fwdGeoTransformMinus, forwardMinusPV);
261 }
262
263 // Set the neighbours
264 m_detectorManager->initNeighbours();
265
266 // Set maximum number of strips in numerology.
267 for (int iDesign = 0; iDesign < m_detectorManager->numDesigns(); iDesign++) {
268 m_detectorManager->numerology().setMaxNumPhiCells(m_detectorManager->getSCT_Design(iDesign)->cells());
269 }
270
271 // Register the keys and the level corresponding to the key
272 // and whether it expects a global or local shift.
273 // level 0: sensor, level 1: module, level 2, layer/disc, level 3: whole barrel/enccap
274
275
277
278 m_detectorManager->addAlignFolderType(InDetDD::static_run1);
279 m_detectorManager->addFolder("/Indet/Align");
280 m_detectorManager->addChannel("/Indet/Align/ID",3,InDetDD::global);
281 m_detectorManager->addChannel("/Indet/Align/SCT",2,InDetDD::global);
282
283 if (barrelPresent) {
284 m_detectorManager->addChannel("/Indet/Align/SCTB1",1,InDetDD::local);
285 m_detectorManager->addChannel("/Indet/Align/SCTB2",1,InDetDD::local);
286 m_detectorManager->addChannel("/Indet/Align/SCTB3",1,InDetDD::local);
287 m_detectorManager->addChannel("/Indet/Align/SCTB4",1,InDetDD::local);
288 }
289 if (forwardPlusPresent) {
290 m_detectorManager->addChannel("/Indet/Align/SCTEA1",1,InDetDD::local);
291 m_detectorManager->addChannel("/Indet/Align/SCTEA2",1,InDetDD::local);
292 m_detectorManager->addChannel("/Indet/Align/SCTEA3",1,InDetDD::local);
293 m_detectorManager->addChannel("/Indet/Align/SCTEA4",1,InDetDD::local);
294 m_detectorManager->addChannel("/Indet/Align/SCTEA5",1,InDetDD::local);
295 m_detectorManager->addChannel("/Indet/Align/SCTEA6",1,InDetDD::local);
296 m_detectorManager->addChannel("/Indet/Align/SCTEA7",1,InDetDD::local);
297 m_detectorManager->addChannel("/Indet/Align/SCTEA8",1,InDetDD::local);
298 m_detectorManager->addChannel("/Indet/Align/SCTEA9",1,InDetDD::local);
299 }
300 if (forwardMinusPresent) {
301 m_detectorManager->addChannel("/Indet/Align/SCTEC1",1,InDetDD::local);
302 m_detectorManager->addChannel("/Indet/Align/SCTEC2",1,InDetDD::local);
303 m_detectorManager->addChannel("/Indet/Align/SCTEC3",1,InDetDD::local);
304 m_detectorManager->addChannel("/Indet/Align/SCTEC4",1,InDetDD::local);
305 m_detectorManager->addChannel("/Indet/Align/SCTEC5",1,InDetDD::local);
306 m_detectorManager->addChannel("/Indet/Align/SCTEC6",1,InDetDD::local);
307 m_detectorManager->addChannel("/Indet/Align/SCTEC7",1,InDetDD::local);
308 m_detectorManager->addChannel("/Indet/Align/SCTEC8",1,InDetDD::local);
309 m_detectorManager->addChannel("/Indet/Align/SCTEC9",1,InDetDD::local);
310 }
311 }
312
313 else {
315 m_detectorManager->addGlobalFolder("/Indet/AlignL1/ID");
316 m_detectorManager->addGlobalFolder("/Indet/AlignL2/SCT");
317 m_detectorManager->addChannel("/Indet/AlignL1/ID",3,InDetDD::global);
318 m_detectorManager->addChannel("/Indet/AlignL2/SCT",2,InDetDD::global);
319 m_detectorManager->addFolder("/Indet/AlignL3");
320
321 if (barrelPresent) {
322 m_detectorManager->addChannel("/Indet/AlignL3/SCTB1",1,InDetDD::local);
323 m_detectorManager->addChannel("/Indet/AlignL3/SCTB2",1,InDetDD::local);
324 m_detectorManager->addChannel("/Indet/AlignL3/SCTB3",1,InDetDD::local);
325 m_detectorManager->addChannel("/Indet/AlignL3/SCTB4",1,InDetDD::local);
326 }
327 if (forwardPlusPresent) {
328 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA1",1,InDetDD::local);
329 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA2",1,InDetDD::local);
330 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA3",1,InDetDD::local);
331 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA4",1,InDetDD::local);
332 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA5",1,InDetDD::local);
333 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA6",1,InDetDD::local);
334 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA7",1,InDetDD::local);
335 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA8",1,InDetDD::local);
336 m_detectorManager->addChannel("/Indet/AlignL3/SCTEA9",1,InDetDD::local);
337 }
338 if (forwardMinusPresent) {
339 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC1",1,InDetDD::local);
340 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC2",1,InDetDD::local);
341 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC3",1,InDetDD::local);
342 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC4",1,InDetDD::local);
343 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC5",1,InDetDD::local);
344 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC6",1,InDetDD::local);
345 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC7",1,InDetDD::local);
346 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC8",1,InDetDD::local);
347 m_detectorManager->addChannel("/Indet/AlignL3/SCTEC9",1,InDetDD::local);
348 }
349 }
350
351 // Return precision to its original value
352 std::cout.precision(oldPrecision);
353
354}
355
356
361
362
#define endmsg
This file defines the class for a collection of AttributeLists where each one is associated with a ch...
Definition of the abstract IRDBAccessSvc interface.
std::shared_ptr< IRDBRecordset > IRDBRecordset_ptr
Definition of the abstract IRDBRecord interface.
Definition of the abstract IRDBRecordset interface.
This is a helper class to query the version tags from GeoModelSvc and determine the appropriate tag a...
const std::string & tag() const
Return version tag.
const std::string & node() const
Return the version node.
virtual std::string getChildTag(const std::string &childNode, const std::string &parentTag, const std::string &parentNode, const std::string &connName="ATLASDD")=0
Gets the tag name for the node by giving its parent node tag.
virtual IRDBRecordset_ptr getRecordsetPtr(const std::string &node, const std::string &tag, const std::string &tag2node="", const std::string &connName="ATLASDD")=0
Provides access to the Recordset object containing HVS-tagged data.
IRDBRecord is one record in the IRDBRecordset object.
Definition IRDBRecord.h:27
virtual const std::string & getString(const std::string &fieldName) const =0
Get string field value.
virtual bool isFieldNull(const std::string &fieldName) const =0
Check if the field value is NULL.
DetectorFactoryBase(InDetDD::AthenaComps *athenaComps)
const IGeoDbTagSvc * geoDbTagSvc() const
Dedicated detector manager extending the functionality of the SiDetectorManager with dedicated SCT in...
Helper class to concentrate common items, such as the pointer to the IdHelper, the lorentzAngle tool ...
Class to hold version information consisting of tag, name layout and description as strings,...
Definition Version.h:24
virtual GeoVPhysVol * build(SCT_Identifier id)
InDetDD::SCT_DetectorManager * m_detectorManager
std::unique_ptr< SCT_MaterialManager > m_materials
std::unique_ptr< SCT_DataBase > m_db
virtual void create(GeoPhysVol *world)
virtual const InDetDD::SCT_DetectorManager * getDetectorManager() const
std::unique_ptr< SCT_GeometryManager > m_geometryManager
SCT_DetectorFactory(SCT_GeoModelAthenaComps *athenaComps, const SCT_Options &options)
virtual GeoVPhysVol * build(SCT_Identifier id)
double zCenter() const
Definition SCT_Forward.h:49
const GeoTrf::Transform3D & partTransform(const std::string &partName) const
bool partPresent(const std::string &partName) const
Class to hold various Athena components.
const SCT_ID * getIdHelper() const
void setBarrelEC(int i)
Identifier getWaferId()
std::string description
glabal timer - how long have I taken so far?
Definition hcg.cxx:91
Message Stream Member.
@ timedependent_run2
MsgStream & msg
Definition testRead.cxx:32