ECCE @ EIC Software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
DetectorConstruction.cc
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file DetectorConstruction.cc
1 //
2 // ********************************************************************
3 // * License and Disclaimer *
4 // * *
5 // * The Geant4 software is copyright of the Copyright Holders of *
6 // * the Geant4 Collaboration. It is provided under the terms and *
7 // * conditions of the Geant4 Software License, included in the file *
8 // * LICENSE and available at http://cern.ch/geant4/license . These *
9 // * include a list of copyright holders. *
10 // * *
11 // * Neither the authors of this software system, nor their employing *
12 // * institutes,nor the agencies providing financial support for this *
13 // * work make any representation or warranty, express or implied, *
14 // * regarding this software system or assume any liability for its *
15 // * use. Please see the license in the file LICENSE and URL above *
16 // * for the full disclaimer and the limitation of liability. *
17 // * *
18 // * This code implementation is the result of the scientific and *
19 // * technical work of the GEANT4 collaboration. *
20 // * By using, copying, modifying or distributing the software (or *
21 // * any work based on the software) you agree to acknowledge its *
22 // * use in resulting scientific publications, and indicate your *
23 // * acceptance of all terms of the Geant4 Software license. *
24 // ********************************************************************
25 //
26 //
29 
30 #include "DetectorConstruction.hh"
31 #include "DetectorMessenger.hh"
32 
33 #include "G4Material.hh"
34 #include "G4NistManager.hh"
35 #include "G4Tubs.hh"
36 #include "G4Trd.hh"
37 #include "G4LogicalVolume.hh"
38 #include "G4PVPlacement.hh"
39 #include "G4Transform3D.hh"
40 #include "G4RotationMatrix.hh"
41 #include "G4ReflectionFactory.hh"
42 
43 #include "G4GeometryManager.hh"
44 #include "G4PhysicalVolumeStore.hh"
45 #include "G4LogicalVolumeStore.hh"
46 #include "G4SolidStore.hh"
47 #include "G4PhysicalConstants.hh"
48 #include "G4SystemOfUnits.hh"
49 
50 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
51 
54  fMessenger(0),
55  fMethod(kWithDirectMatrix),
56  fWorldVolume(0),
57  fTrdVolume(0)
58 
59 {
60  fMessenger = new DetectorMessenger(this);
61 }
62 
63 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
64 
66 {
67  delete fMessenger;
68 }
69 
70 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
71 
73 {
74  // Materials
76  G4Material* material = nist->FindOrBuildMaterial("G4_AIR");
77 
78  // Clean old geometry, if any
79  //
84 
85  // World
86  //
87  G4double rmin = 0.;
88  G4double rmax = 5*cm;
89  G4double hz = 5*cm;
90  G4double phiMin = 0.;
91  G4double deltaPhi = 360*degree;
92 
93  G4Tubs* solidWorld
94  = new G4Tubs("World", //name
95  rmin, rmax, hz, phiMin, deltaPhi); //size
96 
98  = new G4LogicalVolume(solidWorld, //solid
99  material, //material
100  "World"); //name
101 
102  G4VPhysicalVolume* physiWorld
103  = new G4PVPlacement(0, //no rotation
104  G4ThreeVector(), //at (0,0,0)
105  fWorldVolume, //logical volume
106  "World", //name
107  0, //mother volume
108  false, //no boolean operation
109  0); //copy number
110 
111  // Trd volume
112  //
113  G4double dX1 = 1*cm;
114  G4double dX2 = 1*cm;
115  G4double dY1 = 1*cm;
116  G4double dY2 = 2*cm;
117  G4double dZ = 3*cm;
118 
119  G4Trd* solidTrd
120  = new G4Trd("trd", //name
121  dX1/2, dX2/2, dY1/2, dY2/2, dZ/2); //size
122 
123  fTrdVolume
124  = new G4LogicalVolume(solidTrd, //solid
125  material, //material
126  "trd"); //name
127 
128 
129  // Place Volume1 and Volume2 according to selected methods
130  //
131  switch ( fMethod ) {
135  case kWithEulerAngles: PlaceWithEulerAngles(); break;
136  case kWithReflections: PlaceWithReflections(); break;
137  default: ;;
138  }
139 
140  // Return the root volume
141  //
142  return physiWorld;
143 }
144 
145 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
146 
148 {
149  G4double og = 3*cm;
150 
151  // 1st position
152  //
153  G4double phi = 30*deg;
154  // u, v, w are the daughter axes, projected on the mother frame
155  G4ThreeVector u = G4ThreeVector(0, 0, -1);
156  G4ThreeVector v = G4ThreeVector(-std::sin(phi), std::cos(phi),0.);
157  G4ThreeVector w = G4ThreeVector( std::cos(phi), std::sin(phi),0.);
158  G4RotationMatrix rotm1 = G4RotationMatrix(u, v, w);
159  G4cout << "\n --> phi = " << phi/deg << " deg; direct rotation matrix : ";
160  rotm1.print(G4cout);
161  G4ThreeVector position1 = og*w;
162  G4Transform3D transform1 = G4Transform3D(rotm1,position1);
163 
164  new G4PVPlacement(transform1, //position, rotation
165  fTrdVolume, //logical volume
166  "Trd", //name
167  fWorldVolume, //mother volume
168  false, //no boolean operation
169  1); //copy number
170 
171  // 2nd position
172  //
173  phi = phi + 90*deg;
174  v = G4ThreeVector(-std::sin(phi), std::cos(phi),0.);
175  w = G4ThreeVector( std::cos(phi), std::sin(phi),0.);
176  G4RotationMatrix rotm2 = G4RotationMatrix(u, v, w);
177  G4ThreeVector position2 = og*w;
178  G4Transform3D transform2 = G4Transform3D(rotm2,position2);
179  new G4PVPlacement(transform2, //position, rotation
180  fTrdVolume, //logical volume
181  "Trd", //name
182  fWorldVolume, //mother volume
183  false, //no boolean operation
184  2); //copy number
185 }
186 
187 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
188 
190 {
191  G4double og = 3*cm;
192 
193  // 1st position
194  //
195  G4double phi = 30*deg;
196  // u, v, w are the daughter axes, projected on the mother frame
197  G4ThreeVector u = G4ThreeVector(0, 0, -1);
198  G4ThreeVector v = G4ThreeVector(-std::sin(phi), std::cos(phi),0.);
199  G4ThreeVector w = G4ThreeVector( std::cos(phi), std::sin(phi),0.);
200  G4RotationMatrix rotm1 = G4RotationMatrix(u, v, w);
201  G4RotationMatrix* rotm1Inv = new G4RotationMatrix(rotm1.inverse());
202  G4cout << "\n --> phi = " << phi/deg << " deg; inverse rotation matrix : ";
203  rotm1Inv->print(G4cout);
204  G4ThreeVector position1 = og*w;
205 
206  new G4PVPlacement(rotm1Inv,
207  position1,
208  fTrdVolume, //logical volume
209  "Trd", //name
210  fWorldVolume, //mother volume
211  false, //no boolean operation
212  1); //copy number
213 
214  // 2nd position
215  //
216  phi = phi + 90*deg;
217  v = G4ThreeVector(-std::sin(phi), std::cos(phi),0.);
218  w = G4ThreeVector( std::cos(phi), std::sin(phi),0.);
219  G4RotationMatrix rotm2 = G4RotationMatrix(u, v, w);
220  G4RotationMatrix* rotm2Inv = new G4RotationMatrix(rotm2.inverse());
221  G4ThreeVector position2 = og*w;
222 
223  new G4PVPlacement(rotm2Inv, //rotation
224  position2, //position
225  fTrdVolume, //logical volume
226  "Trd", //name
227  fWorldVolume, //mother volume
228  false, //no boolean operation
229  2); //copy number
230 }
231 
232 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
233 
235 {
236  G4double og = 3*cm;
237 
238  // 1st position (with first G4PVPlacement constructor)
239  //
240  G4double phi = 30*deg, theta = 90*deg;
241  G4ThreeVector rotAxis =
242  G4ThreeVector(std::sin(theta-pi/2), 0., std::cos(theta-pi/2));
244  rotm1.rotateY(theta);
245  rotm1.rotate (phi, rotAxis);
246  G4cout << "\n --> direct rotation matrix : "
247  << " theta = " << theta/deg << " deg;"
248  << " phi = " << phi/deg << " deg;";
249  rotm1.print(G4cout);
250  G4ThreeVector w = G4ThreeVector( std::sin(theta)*std::cos(phi),
251  std::sin(phi), std::cos(theta)*std::cos(phi));
252  G4ThreeVector position1 = og*w;
253  G4Transform3D transform1(rotm1,position1);
254 
255  new G4PVPlacement(transform1, //rotation,position
256  fTrdVolume, //logical volume
257  "Trd", //name
258  fWorldVolume, //mother volume
259  false, //no boolean operation
260  1); //copy number
261 
262  // 2nd position (with second G4PVPlacement constructor)
263  //
264  phi = phi + 90*deg;
265  //rotm2Inv could be calculated with rotm2.inverse()
266  //but also by the following :
267  G4RotationMatrix* rotm2Inv = new G4RotationMatrix();
268  rotm2Inv->rotate (-phi, rotAxis);
269  rotm2Inv->rotateY(-theta);
270  w = G4ThreeVector( std::sin(theta)*std::cos(phi),
271  std::sin(phi), std::cos(theta)*std::cos(phi));
272  G4ThreeVector position2 = og*w;
273 
274  new G4PVPlacement(rotm2Inv, //rotation
275  position2, //position
276  fTrdVolume, //logical volume
277  "Trd", //name
278  fWorldVolume, //mother volume
279  false, //no boolean operation
280  2); //copy number
281 }
282 
283 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
284 
286 {
287  //definitions : mother frame = {x,y,z} ; daughter frame = {u,v,w}
288  // n = node line = intercept of xy and uv planes
289  // phi_euler = (x,n) : precession
290  // theta_euler = (z,w) : nutation
291  // psi_euler = (n,u) : proper rotation
292 
293  G4double og = 3*cm;
294 
295  // 1st position (with first G4PVPlacement constructor)
296  //
297  G4double phi = 30*deg;
298  G4double phi_euler = phi + pi/2;
299  G4double theta_euler = 90*deg;
300  G4double psi_euler = -90*deg;
301  //attention : clhep Euler constructor build inverse matrix !
302  G4RotationMatrix rotm1Inv = G4RotationMatrix(phi_euler,theta_euler,psi_euler);
303  G4RotationMatrix rotm1 = rotm1Inv.inverse();
304  //remark : could be built as rotm1 = G4RotationMatrix(-psi, -theta, -phi)
305  G4cout << "\n --> phi = " << phi/deg << " deg; direct rotation matrix : ";
306  rotm1.print(G4cout);
307  G4ThreeVector w = G4ThreeVector(std::cos(phi), std::sin(phi),0.);
308  G4ThreeVector position1 = og*w;
309  G4Transform3D transform1 = G4Transform3D(rotm1,position1);
310 
311  new G4PVPlacement(transform1, //position, rotation
312  fTrdVolume, //logical volume
313  "Trd", //name
314  fWorldVolume, //mother volume
315  false, //no boolean operation
316  1); //copy number
317 
318  // 2nd position (with second G4PVPlacement constructor)
319  //
320  phi = phi + 90*deg;
321 
322  phi_euler = phi + pi/2;
323  G4RotationMatrix* rotm2Inv
324  = new G4RotationMatrix(phi_euler,theta_euler,psi_euler);
325  w = G4ThreeVector(std::cos(phi), std::sin(phi),0.);
326  G4ThreeVector position2 = og*w;
327 
328  new G4PVPlacement(rotm2Inv, //rotation
329  position2, //position
330  fTrdVolume, //logical volume
331  "Trd", //name
332  fWorldVolume, //mother volume
333  false, //no boolean operation
334  2); //copy number
335 }
336 
337 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
338 
340 {
344 
345  G4double og = 3*cm;
346 
347  // Place first two positionz in z = - 3cm
348  //
349 
350  // 1st position
351  G4double phi = 30*deg;
352  G4RotationMatrix rotm1;
353  //rotm1.rotateY(90*deg);
354  rotm1.rotateZ(phi);
355  G4ThreeVector uz = G4ThreeVector(std::cos(phi), std::sin(phi), 0);
356  G4ThreeVector position = og*uz;
357  G4Transform3D transform1(rotm1,position);
358  G4Transform3D translateZ = HepGeom::Translate3D(0, 0, -3.*cm);
359 
360  new G4PVPlacement(translateZ * transform1, //rotation,position
361  fTrdVolume, //logical volume
362  "Trd", //name
363  fWorldVolume, //mother volume
364  false, //no boolean operation
365  1); //copy number
366 
367  // 2nd position
368  phi = phi + pi/2 ;
369  G4RotationMatrix rotm2;
370  //rotm2.rotateY(90*deg);
371  rotm2.rotateZ(phi);
372  uz = G4ThreeVector(std::cos(phi), std::sin(phi), 0.);
373  position = og*uz;
374  G4Transform3D transform2 = G4Transform3D(rotm2, position);
375 
376  new G4PVPlacement(translateZ * transform2, //rotation, position
377  fTrdVolume, //logical volume
378  "Trd", //name
379  fWorldVolume, //mother volume
380  false, //no boolean operation
381  2); //copy number
382 
383 
384  // Place next two positionz in z = + 3cm with reflection
385  //
386 
387  // 3rd position
388  translateZ = HepGeom::Translate3D(0, 0, +3.*cm);
389  G4Transform3D reflect3D = HepGeom::ReflectZ3D();
390 
392  ->Place(translateZ * transform1 * reflect3D, //rotation,position
393  "Trd", //name
394  fTrdVolume, //logical volume
395  fWorldVolume, //mother volume
396  false, //no boolean operation
397  3); //copy number
398 
399  // 4rd position
401  ->Place( translateZ * transform2 * reflect3D,//rotation,position
402  "Trd", //name
403  fTrdVolume, //logical volume
404  fWorldVolume, //mother volume
405  false, //no boolean operation
406  4); //copy number
407 }
408 
409 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
410 
411 #include "G4RunManager.hh"
412 
414  fMethod = method;
416 }
417 
418 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......