ATLAS Offline Software
GeoPixelIBLFwdSvcCADModel.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2024 CERN for the benefit of the ATLAS collaboration
3 */
4 
5 
6 // Build IBL fwd services (wavy shape)
7 // This is built one time per layer.
8 
10 
11 #include "GeoModelKernel/GeoTube.h"
12 #include "GeoModelKernel/GeoTubs.h"
13 
14 #if defined(GEOTORUS) && GEOTORUS==1
15  #include "GeoModelKernel/GeoTorus.h"
16 #endif
17 
18 #include "GeoModelKernel/GeoSimplePolygonBrep.h"
19 #include "GeoModelKernel/GeoShape.h"
20 #include "GeoModelKernel/GeoShapeUnion.h"
21 #include "GeoModelKernel/GeoShapeShift.h"
22 #include "GeoModelKernel/GeoLogVol.h"
23 #include "GeoModelKernel/GeoPhysVol.h"
24 #include "GeoModelKernel/GeoMaterial.h"
25 #include "GeoModelKernel/GeoNameTag.h"
26 
27 #include "GeoModelKernel/GeoTransform.h"
28 #include "GaudiKernel/PhysicalConstants.h"
29 
30 #include <algorithm>
31 #include <iomanip>
32 #include <iostream>
33 #include <utility>
34 using std::max;
35 
38  GeoModelIO::ReadGeoModel* sqliteReader,
39  std::shared_ptr<std::map<std::string, GeoFullPhysVol*>> mapFPV,
40  std::shared_ptr<std::map<std::string, GeoAlignableTransform*>> mapAX,
41  int /*section*/)
42  : GeoVPixelFactory(ddmgr, mgr, sqliteReader, std::move(mapFPV), std::move(mapAX)),
43  m_supportPhysA(nullptr),
44  m_supportPhysC(nullptr),
45  m_xformSupportA(nullptr),
46  m_xformSupportC(nullptr)
47 {
48 }
49 
51 {
52 
53  m_gmt_mgr->msg(MSG::INFO) <<"Build IBL fwd services - CAD tool design - Build()"<<endmsg;
54 
55 #if !defined(GEOTORUS) || GEOTORUS==0
56 
57  m_gmt_mgr->msg(MSG::INFO) <<"Build IBL fwd services - CAD tool design - Torus object is not defined "<<GEOTORUS<<endmsg;
58  return 0;
59 
60 #else
61 
62  m_gmt_mgr->msg(MSG::INFO) <<"Build IBL fwd services - CAD tool design - Torus object is defined"<<endmsg;
63 
64  // double safety = 0.01*Gaudi::Units::mm;
65 
66  // IBL layer shift ( 2mm shift issue )
67  double layerZshift = m_gmt_mgr->PixelLayerGlobalShift();
68  int nSectors = m_gmt_mgr->NPixelSectors();
69  double phiOfModuleZero = m_gmt_mgr->PhiOfModuleZero();
70  double layerRadius = m_gmt_mgr->PixelLayerRadius();
71 
72  // check if sectors are properly defined
73  if(nSectors==0) return nullptr;
74  double angle=360./(double)nSectors*Gaudi::Units::deg;
75 
76  // Defines the IBL_Fwd02 section in the IBL services area
77  double innerRadius = 33.;
78  double outerRadius = 42.499;
79  double zMin = 834.607;
80  double zMax = 3290.795;
81 
82  double zLength = zMax-zMin;
83  double halfLength = zLength*.5;
84  double zMiddle = (zMin+zMax)*.5;
85 
86  // Define IBL fwd svc section for side A and C
87  std::ostringstream lnameA;
88  lnameA<<"Brl0A_FwdSvc";
89  std::ostringstream lnameC;
90  lnameC<<"Brl0C_FwdSvc";
91 
92  // Build encompassing volume for both A and C sides (assemblies)
93  const GeoTube* supportShapeA = new GeoTube(innerRadius,outerRadius,halfLength);
94  const GeoTube* supportShapeC = new GeoTube(innerRadius,outerRadius,halfLength);
95  const GeoMaterial* ether = m_mat_mgr->getMaterial("special::Ether");
96  GeoLogVol* supportLogVol_A = new GeoLogVol(lnameA.str(),supportShapeA,ether);
97  GeoLogVol* supportLogVol_C = new GeoLogVol(lnameA.str(),supportShapeC,ether);
98 
99  // Data taken fron CATIA desgin file
100  double delta = 18.;
101  double deltaJunction = 0.;
102  double lgFwdSvc[4]={511., 561., 560., 706. };
103  //double devLgFwdSvc[4]={512., 562., 562., 707. };
104  double devTotalLength = 2460.188;
105  double pi = Gaudi::Units::pi;
106 
107  // Cable bundle sizes
108  double rminCable = 0.;
109  double rmaxCable = 8.*.5;
110  double surfCable = rmaxCable*rmaxCable*pi;
111 
112  // Cooling tube sizes
113  double rminCooling = 0.;
114  double rmaxCooling = 1.75*.5;
115  double surfCooling = rmaxCooling*rmaxCooling*pi;
116 
117  // IPT clip starting position
118  double zpos0 = 903.;
119  double zpos = 0.;
120  double hermJunction = .4;
121  double breakAngle = 11.*Gaudi::Units::deg;
122 
123  // Loop over the wavy shape sections to build a cable and a cooling pipe
124  const GeoShape * gblShapeCableA = nullptr;
125  const GeoShape * gblShapeCoolingA = nullptr;
126  const GeoShape * gblShapeCableC = nullptr;
127  const GeoShape * gblShapeCoolingC = nullptr;
128  for(int i=0; i<4; i++)
129  {
130  double initHalfLength = lgFwdSvc[i]*.5;
131  zpos += initHalfLength;
132  double corHalfLength = initHalfLength-deltaJunction;
133  double radius = .5*(corHalfLength*corHalfLength+delta*delta)/delta;
134  double theta = asin(corHalfLength/radius);
135 
136  if(i==0){
137  double tubeLength=deltaJunction+zpos0-zMin+hermJunction;
138  double zposTrans=zMin+tubeLength*.5-zpos0;
139  const GeoTube* tubeShape = new GeoTube(0., rmaxCable, tubeLength*.5);
140  GeoTrf::Transform3D trfA = GeoTrf::TranslateZ3D(zpos0+zposTrans-zMiddle);
141  gblShapeCableA = addShape(gblShapeCableA, tubeShape, trfA );
142  GeoTrf::Transform3D trfC = GeoTrf::RotateY3D(pi)*GeoTrf::TranslateZ3D(zpos0+zposTrans-zMiddle);
143  gblShapeCableC = addShape(gblShapeCableC, tubeShape, trfC );
144 
145  // std::cout<<"IBL_fwd : junction "<<std::setprecision(15)<<i<<" : "<<zpos0+zposTrans-tubeLength*.5<<" "<<zpos0+zposTrans+tubeLength*.5<<" // "<<zMin<<std::endl;
146 
147  const GeoTube* tubeShape_cooling = new GeoTube(0., rmaxCooling, tubeLength*.5);
148  gblShapeCoolingA = addShape(gblShapeCoolingA, tubeShape_cooling, trfA );
149  gblShapeCoolingC = addShape(gblShapeCoolingC, tubeShape_cooling, trfC );
150  }
151 
152  // std::cout<<"Torus radius : "<<radius<<" "<<perimeter*(2.*theta)/(2.*pi)+2*deltaJunction<<" / "<<devLgFwdSvc[i]<<std::endl;
153 
154  double rtor = radius;
155  const GeoTorus* torusShape = new GeoTorus(rminCable,rmaxCable,rtor,pi*.5-theta,2.*theta);
156  double angle=(i%2==0)?breakAngle:pi-breakAngle;
157  GeoTrf::Transform3D trfA = GeoTrf::RotateZ3D(angle)*GeoTrf::RotateY3D(-pi*.5)*GeoTrf::TranslateY3D(-radius+delta)* GeoTrf::TranslateX3D(zpos0+zpos-zMiddle);
158  gblShapeCableA = addShape(gblShapeCableA, torusShape, trfA );
159  GeoTrf::Transform3D trfC = GeoTrf::RotateZ3D(angle)*GeoTrf::RotateY3D(pi*.5)*GeoTrf::TranslateY3D(-radius+delta)* GeoTrf::TranslateX3D(zpos0+zpos-zMiddle);
160  gblShapeCableC = addShape(gblShapeCableC, torusShape, trfC );
161 
162  const GeoTorus* torusShape_cooling = new GeoTorus(rminCooling,rmaxCooling,rtor,pi*.5-theta,2.*theta);
163  gblShapeCoolingA = addShape(gblShapeCoolingA, torusShape_cooling, trfA );
164  gblShapeCoolingC = addShape(gblShapeCoolingC, torusShape_cooling, trfC );
165 
166  zpos += initHalfLength;
167 
168  if(i==3){
169  zpos=zpos0+zpos-deltaJunction;
170  double tubeLength=zMax-zpos+hermJunction;
171  double zposTrans=zMax-tubeLength*.5;
172  const GeoTube* tubeShape = new GeoTube(0., rmaxCable, tubeLength*.5);
173  GeoTrf::Transform3D trfA = GeoTrf::TranslateZ3D(zposTrans-zMiddle);
174  gblShapeCableA = addShape(gblShapeCableA, tubeShape, trfA );
175  GeoTrf::Transform3D trfC = GeoTrf::RotateY3D(pi)*GeoTrf::TranslateZ3D(zposTrans-zMiddle);
176  gblShapeCableC = addShape(gblShapeCableC, tubeShape, trfC );
177 
178  const GeoTube* tubeShape_cooling = new GeoTube(0., rmaxCooling, tubeLength*.5);
179  gblShapeCoolingA = addShape(gblShapeCoolingA, tubeShape_cooling, trfA );
180  gblShapeCoolingC = addShape(gblShapeCoolingC, tubeShape_cooling, trfC );
181  }
182 
183  }
184 
185 
186  // Material (material budget computed based on the detailed description of a cable bundle and cooling pipe
187  const GeoMaterial* cableMat = m_mat_mgr->getMaterialForVolume("pix::IBL_Fwd02_Cable_Wvy",surfCable*devTotalLength);
188  GeoLogVol * cable_logA = new GeoLogVol("IBL_Fwd02_Cable_A",gblShapeCableA,cableMat);
189  GeoLogVol * cable_logC = new GeoLogVol("IBL_Fwd02_Cable_C",gblShapeCableC,cableMat);
190 
191  const GeoMaterial* coolingMat = m_mat_mgr->getMaterialForVolume("pix::IBL_Fwd02_Cooling_Wvy",surfCooling*devTotalLength);
192  GeoLogVol * cooling_logA = new GeoLogVol("IBL_Fwd02_Cooling_A",gblShapeCoolingA,coolingMat);
193  GeoLogVol * cooling_logC = new GeoLogVol("IBL_Fwd02_Cooling_C",gblShapeCoolingC,coolingMat);
194 
195  // ----------- Create the PhysVol object
196  m_supportPhysA = new GeoPhysVol(supportLogVol_A);
197  m_supportPhysC = new GeoPhysVol(supportLogVol_C);
198 
199  // -------------- Alignement of the services with the previous services (Fwd01 area)
200  double cooling_radius = 35.1;
201  double cooling_angle = -2.154*Gaudi::Units::deg;
202 
203  if(m_gmt_mgr->PixelStaveAxe()==1)
204  {
205  cooling_radius = 34.7 + layerRadius-33.25;
206  cooling_angle = -.1*Gaudi::Units::deg;
207  }
208 
209  double cable_radius = 36.501;
210  GeoPhysVol* cablePhysVolA = new GeoPhysVol(cable_logA);
211  GeoPhysVol* cablePhysVolC = new GeoPhysVol(cable_logC);
212  GeoPhysVol* coolingPhysVolA = new GeoPhysVol(cooling_logA);
213  GeoPhysVol* coolingPhysVolC = new GeoPhysVol(cooling_logC);
214 
215  // nSectors=1;
216 
217  // Loop over the sectors to place the 14 bundles and cooling pipes
218  for(int ii=0; ii<nSectors; ii++)
219  {
220  m_gmt_mgr->SetPhi(ii);
221 
222  // cooling transform
223  double phiOfCooling = phiOfModuleZero+ cooling_angle + ii*angle;
224 
225  std::ostringstream tmp1;
226  tmp1 << "IBL_Fwd02_Cooling_A" << ii;
227  GeoNameTag * tag1 = new GeoNameTag(tmp1.str());
228  GeoTransform* xformA1 = new GeoTransform(GeoTrf::RotateZ3D(phiOfCooling)*GeoTrf::TranslateX3D(cooling_radius));
229  m_supportPhysA->add(tag1);
230  m_supportPhysA->add(xformA1);
231  m_supportPhysA->add(coolingPhysVolA);
232 
233  std::ostringstream tmp1C;
234  tmp1C << "IBL_Fwd02_Cooling_C" << ii;
235  GeoNameTag * tag1C = new GeoNameTag(tmp1C.str());
236  GeoTransform* xformC1 = new GeoTransform(GeoTrf::RotateZ3D(phiOfCooling)*GeoTrf::TranslateX3D(cooling_radius));
237  m_supportPhysC->add(tag1C);
238  m_supportPhysC->add(xformC1);
239  m_supportPhysC->add(coolingPhysVolC);
240 
241  double phiOfCable = phiOfCooling + angle*.5;
242 
243  std::ostringstream tmp2;
244  tmp2 << "IBL_Fwd02_Cable_A" << ii;
245  GeoNameTag * tag2 = new GeoNameTag(tmp2.str());
246  GeoTransform* xformA2 = new GeoTransform(GeoTrf::RotateZ3D(phiOfCable)*GeoTrf::TranslateX3D(cable_radius));
247  m_supportPhysA->add(tag2);
248  m_supportPhysA->add(xformA2);
249  m_supportPhysA->add(cablePhysVolA);
250 
251  std::ostringstream tmp2C;
252  tmp2C << "IBL_Fwd02_Cable_C" << ii;
253  GeoNameTag * tag2C = new GeoNameTag(tmp2C.str());
254  GeoTransform* xformC2 = new GeoTransform(GeoTrf::RotateZ3D(phiOfCable)*GeoTrf::TranslateX3D(cable_radius));
255  m_supportPhysC->add(tag2C);
256  m_supportPhysC->add(xformC2);
257  m_supportPhysC->add(cablePhysVolC);
258 
259  }
260 
261  // Global transforms that include the IBL shift in Z
262  double middleA = zMiddle+layerZshift;
263  double middleC = -zMiddle+layerZshift;
264 
265  GeoTrf::Transform3D supportTrfA = GeoTrf::TranslateZ3D(middleA);
266  m_xformSupportA = new GeoTransform(supportTrfA);
267 
268  GeoTrf::Transform3D supportTrfC = GeoTrf::TranslateZ3D(middleC);
269  m_xformSupportC = new GeoTransform(supportTrfC);
270 
271  return nullptr;
272 
273 #endif
274 
275 }
276 
277 
278 const GeoShape * GeoPixelIBLFwdSvcCADModel::addShape(const GeoShape * lastShape, const GeoShape * nextShape, const GeoTrf::Transform3D & trans)
279 {
280  const GeoShape * shiftedShape = &(*nextShape << trans);
281  if (lastShape) {
282  lastShape = &(lastShape->add(*shiftedShape));
283  } else {
284  lastShape = shiftedShape;
285  }
286  return lastShape;
287 }
PixelGeometryManager::PixelLayerGlobalShift
virtual double PixelLayerGlobalShift()=0
GeoPixelIBLFwdSvcCADModel::m_supportPhysC
GeoPhysVol * m_supportPhysC
Definition: GeoPixelIBLFwdSvcCADModel.h:39
DeMoUpdate.tmp2
string tmp2
Definition: DeMoUpdate.py:1168
max
#define max(a, b)
Definition: cfImp.cxx:41
PixelGeometryManager
Definition: PixelGeometryManager.h:28
PixelGeometryManager::msg
MsgStream & msg(MSG::Level lvl) const
Definition: PixelGeometryManager.h:611
GeoPixelIBLFwdSvcCADModel::Build
virtual GeoVPhysVol * Build() override
Definition: GeoPixelIBLFwdSvcCADModel.cxx:50
GeoPixelIBLFwdSvcCADModel::GeoPixelIBLFwdSvcCADModel
GeoPixelIBLFwdSvcCADModel(InDetDD::PixelDetectorManager *ddmgr, PixelGeometryManager *mgr, GeoModelIO::ReadGeoModel *sqliteReader, std::shared_ptr< std::map< std::string, GeoFullPhysVol * >> mapFPV, std::shared_ptr< std::map< std::string, GeoAlignableTransform * >> mapAX, int)
Definition: GeoPixelIBLFwdSvcCADModel.cxx:36
theta
Scalar theta() const
theta method
Definition: AmgMatrixBasePlugin.h:75
GeoPixelIBLFwdSvcCADModel.h
deg
#define deg
Definition: SbPolyhedron.cxx:17
GeoPixelIBLFwdSvcCADModel::addShape
const GeoShape * addShape(const GeoShape *lastShape, const GeoShape *nextShape, const GeoTrf::Transform3D &trans)
Definition: GeoPixelIBLFwdSvcCADModel.cxx:278
pi
#define pi
Definition: TileMuonFitter.cxx:65
GeoVPixelFactory::m_gmt_mgr
PixelGeometryManager * m_gmt_mgr
Definition: GeoVPixelFactory.h:43
PixelGeometryManager::NPixelSectors
virtual int NPixelSectors()=0
BchCleanup.mgr
mgr
Definition: BchCleanup.py:294
lumiFormat.i
int i
Definition: lumiFormat.py:85
endmsg
#define endmsg
Definition: AnalysisConfig_Ntuple.cxx:63
plotBeamSpotCompare.tag1
string tag1
Definition: plotBeamSpotCompare.py:75
angle
double angle(const GeoTrf::Vector2D &a, const GeoTrf::Vector2D &b)
Definition: TRTDetectorFactory_Full.cxx:73
Amg::Transform3D
Eigen::Affine3d Transform3D
Definition: GeoPrimitives.h:46
InDetMaterialManager::getMaterialForVolume
const GeoMaterial * getMaterialForVolume(const std::string &materialName, double volume, const std::string &newName="")
Create and get material with a density calculated to give weight in predefined weight table.
Definition: InDetMaterialManager.cxx:460
PixelGeometryManager::SetPhi
virtual void SetPhi(int phi)=0
plotBeamSpotCompare.tag2
string tag2
Definition: plotBeamSpotCompare.py:76
xAOD::double
double
Definition: CompositeParticle_v1.cxx:159
GeoPixelIBLFwdSvcCADModel::m_xformSupportC
GeoTransform * m_xformSupportC
Definition: GeoPixelIBLFwdSvcCADModel.h:41
InDetDD::PixelDetectorManager
Definition: PixelDetectorManager.h:47
GeoVPixelFactory::m_mat_mgr
InDetMaterialManager * m_mat_mgr
Definition: GeoVPixelFactory.h:44
PixelGeometryManager::PixelStaveAxe
virtual int PixelStaveAxe()=0
ParticleGun_SamplingFraction.radius
radius
Definition: ParticleGun_SamplingFraction.py:96
PixelGeometryManager::PhiOfModuleZero
virtual double PhiOfModuleZero()=0
GeoPixelIBLFwdSvcCADModel::m_supportPhysA
GeoPhysVol * m_supportPhysA
Definition: GeoPixelIBLFwdSvcCADModel.h:38
PixelGeometryManager::PixelLayerRadius
virtual double PixelLayerRadius()=0
GeoVPixelFactory
This is the base class for all the pieces of the Pixel detector.
Definition: GeoVPixelFactory.h:31
tubeLength
double tubeLength
Definition: MDT_ResponseTest.cxx:32
InDetMaterialManager::getMaterial
const GeoMaterial * getMaterial(const std::string &materialName)
Get material. First looks for locally defined material and if not found looks in GeoModel material ma...
Definition: InDetMaterialManager.cxx:96
GeoPixelIBLFwdSvcCADModel::m_xformSupportA
GeoTransform * m_xformSupportA
Definition: GeoPixelIBLFwdSvcCADModel.h:40