Geant4  9.6.p02
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
B2aDetectorConstruction.cc
Go to the documentation of this file.
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 // $Id$
27 //
30 
32 #include "B2aDetectorMessenger.hh"
33 #include "B2MagneticField.hh"
34 #include "B2TrackerSD.hh"
35 
36 #include "G4Material.hh"
37 #include "G4NistManager.hh"
38 
39 #include "G4Box.hh"
40 #include "G4Tubs.hh"
41 #include "G4LogicalVolume.hh"
42 #include "G4PVPlacement.hh"
43 
44 #include "G4SDManager.hh"
45 
46 #include "G4GeometryTolerance.hh"
47 #include "G4GeometryManager.hh"
48 
49 #include "G4UserLimits.hh"
50 
51 #include "G4VisAttributes.hh"
52 #include "G4Colour.hh"
53 
54 #include "G4SystemOfUnits.hh"
55 
56 //#include "G4ios.hh"
57 
58 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
59 
61 :
62  fNbOfChambers(0),
63  fLogicTarget(NULL), fLogicChamber(NULL),
64  fTargetMaterial(NULL), fChamberMaterial(NULL),
65  fStepLimit(NULL),
66  fCheckOverlaps(true)
67 {
68  fMessenger = new B2aDetectorMessenger(this);
69  fMagField = new B2MagneticField();
70 
71  fNbOfChambers = 5;
72  fLogicChamber = new G4LogicalVolume*[fNbOfChambers];
73 }
74 
75 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
76 
78 {
79  delete [] fLogicChamber;
80  delete fMagField;
81  delete fStepLimit;
82  delete fMessenger;
83 }
84 
85 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
86 
88 {
89  // Define materials
90  DefineMaterials();
91 
92  // Define volumes
93  return DefineVolumes();
94 }
95 
96 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
97 
98 void B2aDetectorConstruction::DefineMaterials()
99 {
100  // Material definition
101 
102  G4NistManager* nistManager = G4NistManager::Instance();
103 
104  G4bool fromIsotopes = false;
105 
106  // Air defined using NIST Manager
107  nistManager->FindOrBuildMaterial("G4_AIR", fromIsotopes);
108 
109  // Lead defined using NIST Manager
110  fTargetMaterial = nistManager->FindOrBuildMaterial("G4_Pb", fromIsotopes);
111 
112  // Xenon gas defined using NIST Manager
113  fChamberMaterial = nistManager->FindOrBuildMaterial("G4_Xe", fromIsotopes);
114 
115  // Print materials
117 }
118 
119 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
120 
121 G4VPhysicalVolume* B2aDetectorConstruction::DefineVolumes()
122 {
123  G4Material* air = G4Material::GetMaterial("G4_AIR");
124 
125  // Sizes of the principal geometrical components (solids)
126 
127  G4double chamberSpacing = 80*cm; // from chamber center to center!
128 
129  G4double chamberWidth = 20.0*cm; // width of the chambers
130  G4double targetLength = 5.0*cm; // full length of Target
131 
132  G4double trackerLength = (fNbOfChambers+1)*chamberSpacing;
133 
134  G4double worldLength = 1.2 * (2*targetLength + trackerLength);
135 
136  G4double targetRadius = 0.5*targetLength; // Radius of Target
137  targetLength = 0.5*targetLength; // Half length of the Target
138  G4double trackerSize = 0.5*trackerLength; // Half length of the Tracker
139 
140  // Definitions of Solids, Logical Volumes, Physical Volumes
141 
142  // World
143 
145 
146  G4cout << "Computed tolerance = "
148  << " mm" << G4endl;
149 
150  G4Box* worldS
151  = new G4Box("world", //its name
152  worldLength/2,worldLength/2,worldLength/2); //its size
153  G4LogicalVolume* worldLV
154  = new G4LogicalVolume(
155  worldS, //its solid
156  air, //its material
157  "World"); //its name
158 
159  // Must place the World Physical volume unrotated at (0,0,0).
160  //
161  G4VPhysicalVolume* worldPV
162  = new G4PVPlacement(
163  0, // no rotation
164  G4ThreeVector(), // at (0,0,0)
165  worldLV, // its logical volume
166  "World", // its name
167  0, // its mother volume
168  false, // no boolean operations
169  0, // copy number
170  fCheckOverlaps); // checking overlaps
171 
172  // Target
173 
174  G4ThreeVector positionTarget = G4ThreeVector(0,0,-(targetLength+trackerSize));
175 
176  G4Tubs* targetS
177  = new G4Tubs("target",0.,targetRadius,targetLength,0.*deg,360.*deg);
178  fLogicTarget
179  = new G4LogicalVolume(targetS, fTargetMaterial,"Target",0,0,0);
180  new G4PVPlacement(0, // no rotation
181  positionTarget, // at (x,y,z)
182  fLogicTarget, // its logical volume
183  "Target", // its name
184  worldLV, // its mother volume
185  false, // no boolean operations
186  0, // copy number
187  fCheckOverlaps); // checking overlaps
188 
189  G4cout << "Target is " << 2*targetLength/cm << " cm of "
190  << fTargetMaterial->GetName() << G4endl;
191 
192  // Tracker
193 
194  G4ThreeVector positionTracker = G4ThreeVector(0,0,0);
195 
196  G4Tubs* trackerS
197  = new G4Tubs("tracker",0,trackerSize,trackerSize, 0.*deg, 360.*deg);
198  G4LogicalVolume* trackerLV
199  = new G4LogicalVolume(trackerS, air, "Tracker",0,0,0);
200  new G4PVPlacement(0, // no rotation
201  positionTracker, // at (x,y,z)
202  trackerLV, // its logical volume
203  "Tracker", // its name
204  worldLV, // its mother volume
205  false, // no boolean operations
206  0, // copy number
207  fCheckOverlaps); // checking overlaps
208 
209  // Visualization attributes
210 
211  G4VisAttributes* boxVisAtt= new G4VisAttributes(G4Colour(1.0,1.0,1.0));
212  G4VisAttributes* chamberVisAtt = new G4VisAttributes(G4Colour(1.0,1.0,0.0));
213 
214  worldLV ->SetVisAttributes(boxVisAtt);
215  fLogicTarget ->SetVisAttributes(boxVisAtt);
216  trackerLV ->SetVisAttributes(boxVisAtt);
217 
218  // Sensitive detectors
219 
220  G4String trackerChamberSDname = "B2/TrackerChamberSD";
221  B2TrackerSD* aTrackerSD = new B2TrackerSD(trackerChamberSDname,
222  "TrackerHitsCollection");
224 
225  // Tracker segments
226 
227  G4cout << "There are " << fNbOfChambers << " chambers in the tracker region. "
228  << "\nThe chambers are " << chamberWidth/cm << " cm of "
229  << fChamberMaterial->GetName() << "\nThe distance between chamber is "
230  << chamberSpacing/cm << " cm" << G4endl;
231 
232  G4double firstPosition = -trackerSize + chamberSpacing;
233  G4double firstLength = trackerLength/10;
234  G4double lastLength = trackerLength;
235 
236  G4double halfWidth = 0.5*chamberWidth;
237  G4double rmaxFirst = 0.5 * firstLength;
238 
239  G4double rmaxIncr = 0.0;
240  if( fNbOfChambers > 0 ){
241  rmaxIncr = 0.5 * (lastLength-firstLength)/(fNbOfChambers-1);
242  if (chamberSpacing < chamberWidth) {
243  G4Exception("B2aDetectorConstruction::DefineVolumes()",
244  "InvalidSetup", FatalException,
245  "Width>Spacing");
246  }
247  }
248 
249  for (G4int copyNo=0; copyNo<fNbOfChambers; copyNo++) {
250 
251  G4double Zposition = firstPosition + copyNo * chamberSpacing;
252  G4double rmax = rmaxFirst + copyNo * rmaxIncr;
253 
254  G4Tubs* chamberS
255  = new G4Tubs("chamber", 0, rmax, halfWidth, 0.*deg, 360.*deg);
256 
257  fLogicChamber[copyNo] =
258  new G4LogicalVolume(chamberS,fChamberMaterial,"Chamber",0,0,0);
259 
260  fLogicChamber[copyNo]->SetSensitiveDetector( aTrackerSD );
261  fLogicChamber[copyNo]->SetVisAttributes(chamberVisAtt);
262 
263  new G4PVPlacement(0, // no rotation
264  G4ThreeVector(0,0,Zposition), // at (x,y,z)
265  fLogicChamber[copyNo], // its logical volume
266  "Chamber", // its name
267  trackerLV, // its mother volume
268  false, // no boolean operations
269  copyNo, // copy number
270  fCheckOverlaps); // checking overlaps
271 
272  }
273 
274  // Example of User Limits
275  //
276  // Below is an example of how to set tracking constraints in a given
277  // logical volume
278  //
279  // Sets a max step length in the tracker region, with G4StepLimiter
280 
281  G4double maxStep = 0.5*chamberWidth;
282  fStepLimit = new G4UserLimits(maxStep);
283  trackerLV->SetUserLimits(fStepLimit);
284 
292 
293  // Always return the physical world
294 
295  return worldPV;
296 }
297 
298 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
299 
301 {
302  G4NistManager* nistManager = G4NistManager::Instance();
303  G4bool fromIsotopes = false;
304 
305  G4Material* pttoMaterial =
306  nistManager->FindOrBuildMaterial(materialName, fromIsotopes);
307 
308  if (fTargetMaterial != pttoMaterial) {
309  if ( pttoMaterial ) {
310  fTargetMaterial = pttoMaterial;
311  if (fLogicTarget) fLogicTarget->SetMaterial(fTargetMaterial);
312  G4cout << "\n----> The target is made of " << materialName << G4endl;
313  } else {
314  G4cout << "\n--> WARNING from SetTargetMaterial : "
315  << materialName << " not found" << G4endl;
316  }
317  }
318 }
319 
320 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
321 
323 {
324  G4NistManager* nistManager = G4NistManager::Instance();
325  G4bool fromIsotopes = false;
326 
327  G4Material* pttoMaterial =
328  nistManager->FindOrBuildMaterial(materialName, fromIsotopes);
329 
330  if (fChamberMaterial != pttoMaterial) {
331  if ( pttoMaterial ) {
332  fChamberMaterial = pttoMaterial;
333  for (G4int copyNo=0; copyNo<fNbOfChambers; copyNo++) {
334  if (fLogicChamber[copyNo]) fLogicChamber[copyNo]->
335  SetMaterial(fChamberMaterial);
336  }
337  G4cout << "\n----> The chambers are made of " << materialName << G4endl;
338  } else {
339  G4cout << "\n--> WARNING from SetChamberMaterial : "
340  << materialName << " not found" << G4endl;
341  }
342  }
343 }
344 
345 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
346 
348 {
349  fMagField->SetMagFieldValue(fieldValue);
350 }
351 
352 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
353 
355 {
356  if ((fStepLimit)&&(maxStep>0.)) fStepLimit->SetMaxAllowedStep(maxStep);
357 }
358 
359 //....oooOO0OOooo........oooOO0OOooo........oooOO0OOooo........oooOO0OOooo......
360 
362 {
363  fCheckOverlaps = checkOverlaps;
364 }