ATLAS Offline Software
Loading...
Searching...
No Matches
SCT_Forward.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#include "SCT_Forward.h"
6
8
12
13#include "SCT_FwdWheel.h"
14#include "SCT_FwdModule.h"
15#include "SCT_FwdRing.h"
16#include "SCT_FwdSupportFrame.h"
17#include "SCT_FwdCoolingPipe.h"
18#include "SCT_FwdPowerTape.h"
21
23
25
26#include "GeoModelRead/ReadGeoModel.h"
27#include "GeoModelKernel/GeoTube.h"
28#include "GeoModelKernel/GeoLogVol.h"
29#include "GeoModelKernel/GeoFullPhysVol.h"
30#include "GeoModelKernel/GeoNameTag.h"
31#include "GeoModelKernel/GeoIdentifierTag.h"
32#include "GeoModelKernel/GeoTransform.h"
33#include "GeoModelKernel/GeoAlignableTransform.h"
34#include "GeoModelKernel/GeoMaterial.h"
35#include "GaudiKernel/SystemOfUnits.h"
36
37#include <cmath>
38#include <sstream>
39#include <utility>
40
41SCT_Forward::SCT_Forward(const std::string & name, int ec,
42 InDetDD::SCT_DetectorManager* detectorManager,
43 SCT_GeometryManager* geometryManager,
44 SCT_MaterialManager* materials,
45 GeoModelIO::ReadGeoModel* sqliteReader,
46 std::shared_ptr<std::map<std::string, GeoFullPhysVol*>> mapFPV,
47 std::shared_ptr<std::map<std::string, GeoAlignableTransform*>> mapAX)
48 : SCT_UniqueComponentFactory(name, detectorManager, geometryManager, materials, sqliteReader, std::move(mapFPV), std::move(mapAX)),
49 m_endcap(ec)
50{
53
54}
55
59
60void
62{
63 const SCT_ForwardParameters * parameters = m_geometryManager->forwardParameters();
64 const SCT_ForwardModuleParameters * moduleParameters = m_geometryManager->forwardModuleParameters();
65
66 //m_numRingTypes = parameters->fwdNumRingTypes();
67 m_numModuleTypes = moduleParameters->fwdModuleNumTypes();
68 m_numWheels = parameters->fwdNumWheels();
69 m_innerRadius = parameters->fwdInnerRadius();
70 m_outerRadius = parameters->fwdOuterRadius();
71 m_zMin = parameters->fwdZMin();
72 m_zMax = parameters->fwdZMax();
73 m_trtGapPos = parameters->fwdTrtGapPos();
74 m_coolingPipeRadius = parameters->fwdCoolingPipeRadius();
75 m_numThermalShieldElements = parameters->fwdNumThermalShieldElements();
76 m_cylinderServicesPresent = parameters->fwdCylinderServicePresent();
77
78 // Outer radius of cylinder services is given by inner radius of OTE
80 for (int iElement = 0; iElement < m_numThermalShieldElements; iElement++){
81 if(parameters->fwdThermalShieldMaterial(iElement) == "sct::FwdOTE") {
82 m_outerRadiusCylinderServices = parameters->fwdThermalShieldInnerRadius(iElement);
83 }
84 }
85 }
86
87 // Length of forward envelope
89
90
91 // Set numerology
92 m_detectorManager->numerology().setNumDisks(m_numWheels);
93
94
95}
96
97
98
99const GeoLogVol *
101{
102 // Create the elements we need for the forward
103 // We make all the module types here. There is a outer, middle, truncated middle and inner type module.
104 std::vector<SCT_FwdModule*> modules;
105 for (int iModuleType = 0; iModuleType < m_numModuleTypes; iModuleType++){
106
107 std::unique_ptr<SCT_FwdModule> module = std::make_unique<SCT_FwdModule>("FwdModule"+intToString(iModuleType), iModuleType,
109 modules.push_back(module.get());
110 m_modules.push_back(std::move(module));
111 }
112
113 for (int iWheel = 0; iWheel < m_numWheels; iWheel++){
114 // Build Wheels
115 std::ostringstream name; name << "Wheel" << iWheel << ((m_endcap > 0) ? "A" : "C");
116 m_wheels.push_back(std::make_unique<SCT_FwdWheel>(name.str(), iWheel, modules, m_endcap,
118 }
119
120 if(m_sqliteReader) return nullptr;
121
122 // Make one end of the Forward tracker
123 // Tube envelope containing the forward
124 const GeoTube * forwardEnvelopeShape = new GeoTube(m_innerRadius, m_outerRadius, 0.5 * m_length);
125 const GeoLogVol * forwardLog =
126 new GeoLogVol(getName(), forwardEnvelopeShape, m_materials->gasMaterial());
127
128 return forwardLog;
129}
130
131GeoVPhysVol *
133{
134 GeoFullPhysVol * forward=nullptr;
135 if(!m_sqliteReader)
136 {
137 forward = new GeoFullPhysVol(m_logVolume);
138
139 for (int iWheel = 0; iWheel < m_numWheels; iWheel++){
140
141 SCT_FwdWheel * wheel = m_wheels[iWheel].get();
142 std::ostringstream wheelName; wheelName << "Wheel#" << iWheel;
143 double zpos = wheel->zPosition() - zCenter();
144 forward->add(new GeoNameTag(wheelName.str()));
145 forward->add(new GeoIdentifierTag(iWheel));
146 GeoAlignableTransform * transform = new GeoAlignableTransform(GeoTrf::TranslateZ3D(zpos));
147 forward->add(transform);
148 id.setLayerDisk(iWheel);
149 GeoVPhysVol * wheelPV = wheel->build(id);
150 forward->add(wheelPV);
151
152 // Store the alignable transform
153 m_detectorManager->addAlignableTransform(2, id.getWaferId(), transform, wheelPV);
154 }
155
156 //
157 // Place SupportFrame
158 //
160 double supportFrameZPos = supportFrame.zPosition() - zCenter();
161 forward->add(new GeoTransform(GeoTrf::TranslateZ3D(supportFrameZPos)));
162 forward->add(supportFrame.getVolume());
163
164 // Make and Place Cylinder Services
165
167
168 // New phi-dependent services
169 SCT_FwdCylinderServices cylinderServices("CylinderServices",
170 supportFrame.outerRadius(),
172 supportFrame.length(),
174 forward->add(new GeoTransform(GeoTrf::TranslateZ3D(supportFrameZPos)));
175 forward->add(cylinderServices.getVolume());
176
177 } else {
178
179 // Old cylindrical services
180 //
181 // Make cooling pipes. These extend from the wheel to the TRT Gap.
182 //
183 {
184 // End position of the pipes.
185 double endPos = m_trtGapPos;
186
187 // Calculate radius to start placing cooling pipes. This is equal to the
188 // outer radius of the support frame + the pipe radius (The pipe radius is to just
189 // give a small gap - it is not really necessary)
190 double innerRadiusCooling = supportFrame.outerRadius() + m_coolingPipeRadius;
191
192 // Inner radius of cylinder representing pipes. Gets incremented for each wheel.
193 double rStart = innerRadiusCooling;
194
195 for (int iWheel = 0; iWheel < m_numWheels; iWheel++){
196 // Start position of the pipes.
197 double startPos = m_wheels[iWheel]->zPosition();
198
199 // Assume one cooling circuit per quadrant of each ring. ie 8 pipes per ring.
200 int numPipes = 8 * m_wheels[iWheel]->numRings();
201
202 // Label Cooling pipe with W# at end of string
203 SCT_FwdCoolingPipe coolingPipe("OffDiskCoolingPipeW"+intToString(iWheel),
204 numPipes, rStart, startPos, endPos,
206
207 // Place the cooling pipes
208 double coolingPipeZPos = coolingPipe.zPosition() - zCenter();
209 forward->add(new GeoTransform(GeoTrf::TranslateZ3D(coolingPipeZPos)));
210 forward->add(coolingPipe.getVolume());
211
212 // Set rStart for next cooling pipe equal to outer radius of this cooling pipe.
213 rStart = coolingPipe.outerRadius();
214
215 }
216 }
217
218 //
219 // Make Power Tapes. These extend from the wheel to the TRT Gap.
220 //
221 {
222
223 // End position of the power tapes.
224 double endPos = m_trtGapPos;
225
226 // Calculate radius to start placing power tapes. This is half way bewteen outer radius
227 // of support fram and outer radius of forward envelope.
228 // The -1 mm is to avoid a clash with the thermal shield.
229 double innerRadiusPowerTapes = 0.5*(supportFrame.outerRadius() + m_outerRadius) - 1*Gaudi::Units::mm;
230
231 // Inner radius of cylinder representing power tapes. Gets incremented for each wheel.
232 double rStart = innerRadiusPowerTapes;
233
234 for (int iWheel = 0; iWheel < m_numWheels; iWheel++){
235
236 // Start position of the power tapes.
237 double startPos = m_wheels[iWheel]->zPosition();
238
239 // Get total number of modules in wheel
240 int numModules = m_wheels[iWheel]->totalModules();
241
242 // Label power tape with W# at end of string
243 SCT_FwdPowerTape powerTape("OffDiskPowerTapeW"+intToString(iWheel),
244 numModules, rStart, startPos, endPos,
246
247 // Place Power Tapes
248 double powerTapeZPos = powerTape.zPosition() - zCenter();
249 forward->add(new GeoTransform(GeoTrf::TranslateZ3D(powerTapeZPos)));
250 forward->add(powerTape.getVolume());
251
252 // Set rStart for next power tape equal to outer radius of this power tape.
253 rStart = powerTape.outerRadius();
254 } // end loop over wheels
255 }
256 }
257
258 //
259 // Place Thermal Shield Elements
260 //
261 for (int iElement = 0; iElement < m_numThermalShieldElements; iElement++){
262 SCT_FwdThermalShieldElement thermalShieldElement("FwdThermalShieldElement"+intToString(iElement),
264 double elementZPos = thermalShieldElement.zPosition() - zCenter();
265 forward->add(new GeoTransform(GeoTrf::TranslateZ3D(elementZPos)));
266 forward->add(thermalShieldElement.getVolume());
267 }
268
269 // Extra Material
270 InDetDD::ExtraMaterial xMat(m_geometryManager->distortedMatManager());
271 xMat.add(forward, "SCTEndcap", zCenter());
272 if (m_endcap > 0) {
273 xMat.add(forward, "SCTEndcapA", zCenter());
274 } else {
275 xMat.add(forward, "SCTEndcapC", zCenter());
276 }
277
278 }else
279 {
280 for (int iWheel = 0; iWheel < m_numWheels; iWheel++){
281
282 SCT_FwdWheel * wheel = m_wheels[iWheel].get();
283 std::ostringstream wheelName; wheelName << "Wheel#" << iWheel;
284 id.setLayerDisk(iWheel);
285 wheel->build(id);
286
287 std::string key=wheelName.str()+"_"+std::to_string(id.getBarrelEC());
288
289 // Store the alignable transform
290 m_detectorManager->addAlignableTransform(2, id.getWaferId(), (*m_mapAX)[key], (*m_mapFPV)[key]);
291 }
292 if (m_endcap > 0) {
293 forward= (*m_mapFPV)["SCTEndcapA"];
294 } else {
295 forward= (*m_mapFPV)["SCTEndcapC"];
296 }
297
298 }
299 return forward;
300}
void add(GeoPhysVol *parent, const std::string &parentName, double zPos=0)
Dedicated detector manager extending the functionality of the SiDetectorManager with dedicated SCT in...
const std::string & getName() const
std::string intToString(int i) const
InDetDD::SCT_DetectorManager * m_detectorManager
SCT_GeometryManager * m_geometryManager
SCT_MaterialManager * m_materials
double m_zMax
Definition SCT_Forward.h:66
std::vector< std::unique_ptr< SCT_FwdWheel > > m_wheels
Definition SCT_Forward.h:77
double m_trtGapPos
Definition SCT_Forward.h:67
void getParameters()
double m_outerRadius
Definition SCT_Forward.h:64
bool m_cylinderServicesPresent
Definition SCT_Forward.h:70
virtual GeoVPhysVol * build(SCT_Identifier id)
virtual const GeoLogVol * preBuild()
double zCenter() const
Definition SCT_Forward.h:49
double m_length
Definition SCT_Forward.h:73
int m_numThermalShieldElements
Definition SCT_Forward.h:69
SCT_Forward(const std::string &name, int ec, InDetDD::SCT_DetectorManager *detectorManager, SCT_GeometryManager *geometryManager, SCT_MaterialManager *materials, GeoModelIO::ReadGeoModel *sqliteReader, std::shared_ptr< std::map< std::string, GeoFullPhysVol * > > mapFPV, std::shared_ptr< std::map< std::string, GeoAlignableTransform * > > mapAX)
std::vector< std::unique_ptr< SCT_FwdModule > > m_modules
Definition SCT_Forward.h:79
double m_outerRadiusCylinderServices
Definition SCT_Forward.h:74
int m_numModuleTypes
Definition SCT_Forward.h:61
double m_zMin
Definition SCT_Forward.h:65
double m_coolingPipeRadius
Definition SCT_Forward.h:68
double m_innerRadius
Definition SCT_Forward.h:63
double outerRadius() const
double zPosition() const
double outerRadius() const
double zPosition() const
virtual GeoVPhysVol * build(SCT_Identifier id)
double zPosition() const
SCT_UniqueComponentFactory(const std::string &name, InDetDD::SCT_DetectorManager *detectorManager, SCT_GeometryManager *geometryManager, SCT_MaterialManager *materials=nullptr, GeoModelIO::ReadGeoModel *sqliteReader=nullptr, std::shared_ptr< std::map< std::string, GeoFullPhysVol * > > mapFPV=nullptr, std::shared_ptr< std::map< std::string, GeoAlignableTransform * > > mapAX=nullptr)
std::shared_ptr< std::map< std::string, GeoFullPhysVol * > > m_mapFPV
std::shared_ptr< std::map< std::string, GeoAlignableTransform * > > m_mapAX
GeoModelIO::ReadGeoModel * m_sqliteReader
STL namespace.