00001
00002
00003 #include "MollerDetectorConstruction.hh"
00004 #include "MollerDetectorMessenger.hh"
00005
00006 #include "MollerDetectorSD.hh"
00007
00008 #include "G4FieldManager.hh"
00009 #include "G4TransportationManager.hh"
00010
00011 #include "G4Material.hh"
00012 #include "G4Element.hh"
00013 #include "G4NistManager.hh"
00014
00015 #include "G4VSolid.hh"
00016 #include "G4Box.hh"
00017 #include "G4Tubs.hh"
00018 #include "G4Cons.hh"
00019 #include "G4Trap.hh"
00020 #include "G4Trd.hh"
00021
00022 #include "G4LogicalVolume.hh"
00023 #include "G4ThreeVector.hh"
00024 #include "G4PVPlacement.hh"
00025 #include "G4UserLimits.hh"
00026 #include "globals.hh"
00027
00028 #include "G4SDManager.hh"
00029 #include "G4VSensitiveDetector.hh"
00030
00031 #include "G4UniformMagField.hh"
00032 #include "G4EqMagElectricField.hh"
00033 #include "G4MagIntegratorStepper.hh"
00034 #include "G4Mag_UsualEqRhs.hh"
00035 #include "G4ChordFinder.hh"
00036 #include "G4PropagatorInField.hh"
00037
00038 #include "G4UImanager.hh"
00039 #include "G4UIcommand.hh"
00040
00041 #include "G4ios.hh"
00042 #include <iostream>
00043
00044
00045 #include "G4GDMLParser.hh"
00046
00047
00048 #include "G4VisAttributes.hh"
00049 #include "G4Colour.hh"
00050
00051
00052
00053 MollerDetectorConstruction::MollerDetectorConstruction()
00054 :
00055 Vacuum(0), Carbon(0), Al(0), Copper(0), Pb(0), Tungsten(0),
00056 Iron(0), H(0), LH2(0),
00057 pGlobalMagnetField(0)
00058 {
00059
00060
00061 CreateGlobalMagneticField();
00062
00063 detectorMessenger = new MollerDetectorMessenger(this);
00064 DefineMaterials();
00065 fTargetLength = 150.0*cm;
00066 collimfileName = "default_coll";
00067 NUM_COLS=10;
00068
00069 }
00070
00071 MollerDetectorConstruction::~MollerDetectorConstruction()
00072 {
00073 for (size_t i = 0; i < washer_logic.size(); i++)
00074 delete washer_logic[i];
00075 for (size_t i = 0; i < washer_phys.size(); i++)
00076 delete washer_phys[i];
00077
00078 for (size_t i = 0; i < trapeziod_logic.size(); i++)
00079 delete trapeziod_logic[i];
00080 for (size_t i = 0; i < trapeziod_phys.size(); i++)
00081 delete trapeziod_phys[i];
00082
00083 if (pGlobalMagnetField) delete pGlobalMagnetField;
00084 delete detectorMessenger;
00085 }
00086
00087 void MollerDetectorConstruction::SetCollimGeomFile(const G4String& nam)
00088 {
00089 collimfileName = nam;
00090 }
00091 void MollerDetectorConstruction::SetDetectorGeomFile(const G4String& nam)
00092 {
00093 G4String fPath = ".";
00094 if (getenv("MOLLERGEANTDIR"))
00095 fPath = getenv("MOLLERGEANTDIR");
00096 else
00097 G4cout << "You do not have MOLLERGEANTDIR defined in your environment!" << G4endl;
00098
00099 detfileName = (fPath+"/"+nam);
00100 }
00101
00102 G4VPhysicalVolume* MollerDetectorConstruction::Construct()
00103 {
00104
00105 G4cout << G4endl << "###### Calling MollerDetectorConstruction::Read() " << G4endl << G4endl;
00106
00107 if (fReadGeoFile){
00108
00109 fGDMLParser.SetOverlapCheck(false);
00110 fGDMLParser.Read(detfileName);
00111
00112 worldVolume = fGDMLParser.GetWorldVolume();
00113
00114
00115
00116
00117
00118 const G4GDMLAuxMapType* auxmap = fGDMLParser.GetAuxMap();
00119
00120 G4cout << "Found " << auxmap->size()
00121 << " volume(s) with auxiliary information."
00122 << G4endl << G4endl;
00123 for(G4GDMLAuxMapType::const_iterator
00124 iter = auxmap->begin();
00125 iter != auxmap->end(); iter++)
00126 {
00127 G4cout << "Volume " << ((*iter).first)->GetName()
00128 << " has the following list of auxiliary information: "<< G4endl;
00129 for (G4GDMLAuxListType::const_iterator
00130 vit = (*iter).second.begin();
00131 vit != (*iter).second.end(); vit++)
00132 {
00133 G4cout << "--> Type: " << (*vit).type
00134 << " Value: " << (*vit).value << std::endl;
00135 }
00136 }
00137 G4cout << G4endl<< G4endl;
00138
00139
00140
00141
00142
00143 G4SDManager* SDman = G4SDManager::GetSDMpointer();
00144 char detectorname[200];
00145
00146 G4VSensitiveDetector* collimatordetector[100];
00147
00148 G4int k=0;
00149 for(G4GDMLAuxMapType::const_iterator
00150 iter = auxmap->begin();
00151 iter != auxmap->end(); iter++)
00152 {
00153 G4LogicalVolume* myvol = (*iter).first;
00154 G4cout << "Volume " << myvol->GetName();
00155
00156 for (G4GDMLAuxListType::const_iterator
00157 vit = (*iter).second.begin();
00158 vit != (*iter).second.end(); vit++)
00159 {
00160 if ((*vit).type == "SensDet")
00161 {
00162 G4String det_type = (*vit).value;
00163
00164
00165 snprintf(detectorname,200,"/detector%i",k+1);
00166 collimatordetector[k] = new MollerDetectorSD(detectorname);
00167
00168 if (collimatordetector[k] != 0)
00169 {
00170
00171 G4cout << " Creating sensitive detector " << det_type
00172 << " for volume " << myvol->GetName()
00173 << G4endl << G4endl;
00174
00175 SDman->AddNewDetector(collimatordetector[k]);
00176 myvol->SetSensitiveDetector(collimatordetector[k]);
00177 }
00178 else
00179 {
00180 G4cout << det_type << " sensitive detector type not found" << G4endl;
00181 }
00182 }
00183 }
00184 k++;
00185 }
00186
00187
00188
00189
00190
00191 G4VisAttributes* motherVisAtt= new G4VisAttributes(G4Colour(1.0,1.0,1.0));
00192 G4VisAttributes* daughterVisAtt= new G4VisAttributes(G4Colour(1.0,1.0,1.0));
00193 G4VisAttributes* targetVisAtt= new G4VisAttributes(G4Colour(1.0,1.0,0.0));
00194 G4VisAttributes* planeDetVisAtt= new G4VisAttributes(G4Colour(0.3,0.8,0.5));
00195
00196 motherVisAtt->SetVisibility(false);
00197
00198 targetVisAtt->SetVisibility(true);
00199
00200 daughterVisAtt->SetVisibility(true);
00201 daughterVisAtt->SetForceWireframe (true);
00202
00203 planeDetVisAtt->SetVisibility(true);
00204 planeDetVisAtt->SetForceWireframe (true);
00205
00206 G4VisAttributes* WVisAtt= new G4VisAttributes(G4Colour(0.7,0.7,0.7));
00207 G4VisAttributes* PbVisAtt= new G4VisAttributes(G4Colour(0.6,0.7,0.8));
00208 G4VisAttributes* CuVisAtt= new G4VisAttributes(G4Colour(1.0,0.5,0.1));
00209 G4VisAttributes* SiVisAtt= new G4VisAttributes(G4Colour(0.4,0.4,0.0));
00210
00211 WVisAtt->SetVisibility(true);
00212 PbVisAtt->SetVisibility(true);
00213 CuVisAtt->SetVisibility(true);
00214 SiVisAtt->SetVisibility(true);
00215
00216 worldVolume->GetLogicalVolume()->SetVisAttributes(motherVisAtt);
00217
00218
00219 for(int i=0;i<worldVolume->GetLogicalVolume()->GetNoDaughters();i++)
00220 {
00221
00222 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->SetVisAttributes(daughterVisAtt);
00223
00224 for (int j=0;j<worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetNoDaughters();j++) {
00225 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->SetVisAttributes(daughterVisAtt);
00226
00227 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->GetMaterial()->GetName().compare("VacuumDet")==0)
00228 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->SetVisAttributes(planeDetVisAtt);
00229
00230 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->GetMaterial()->GetName().compare("Tungsten")==0)
00231 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->SetVisAttributes(WVisAtt);
00232
00233 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->GetMaterial()->GetName().compare("Lead")==0)
00234 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->SetVisAttributes(PbVisAtt);
00235
00236 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->GetMaterial()->GetName().compare("Copper")==0)
00237 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->SetVisAttributes(CuVisAtt);
00238
00239 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->GetMaterial()->GetName().compare("SILICON")==0)
00240 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->SetVisAttributes(SiVisAtt);
00241
00242 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->GetMaterial()->GetName().compare("LiquidHydrogen")==0)
00243 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetDaughter(j)->GetLogicalVolume()->SetVisAttributes(targetVisAtt);
00244 }
00245
00246 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetMaterial()->GetName().compare("VacuumDet")==0)
00247 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->SetVisAttributes(planeDetVisAtt);
00248
00249 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetMaterial()->GetName().compare("Tungsten")==0)
00250 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->SetVisAttributes(WVisAtt);
00251
00252 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetMaterial()->GetName().compare("Lead")==0)
00253 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->SetVisAttributes(PbVisAtt);
00254
00255 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetMaterial()->GetName().compare("Copper")==0)
00256 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->SetVisAttributes(CuVisAtt);
00257
00258 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetMaterial()->GetName().compare("SILICON")==0)
00259 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->SetVisAttributes(SiVisAtt);
00260
00261 if (worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->GetMaterial()->GetName().compare("LiquidHydrogen")==0)
00262 worldVolume->GetLogicalVolume()->GetDaughter(i)->GetLogicalVolume()->SetVisAttributes(targetVisAtt);
00263
00264 }
00265
00266
00267
00268
00269
00270
00271
00272
00273
00274
00275 G4cout << G4endl << "Element table: " << G4endl << G4endl;
00276 G4cout << *(G4Element::GetElementTable()) << G4endl;
00277
00278 G4cout << G4endl << "Material table: " << G4endl << G4endl;
00279 G4cout << *(G4Material::GetMaterialTable()) << G4endl;
00280
00281 G4cout << G4endl << "Geometry tree: " << G4endl << G4endl;
00282 DumpGeometricalTree(worldVolume);
00283
00284 ReadGlobalMagneticField();
00285
00286 } else {
00287
00288 worldVolume = ConstructDetector();
00289 }
00290
00291 G4cout << G4endl << "###### Leaving MollerDetectorConstruction::Read() " << G4endl << G4endl;
00292
00293 return worldVolume;
00294 }
00295
00296 void MollerDetectorConstruction::WriteGeometryFile(const G4String& filename)
00297 {
00298 G4bool appendPointerAddress = true;
00299
00300 fGDMLParser.Write(filename,mother_phys,appendPointerAddress);
00301 }
00302
00303 void MollerDetectorConstruction::DumpGeometricalTree(G4VPhysicalVolume* aVolume,G4int depth)
00304 {
00305 for(int isp=0;isp<depth;isp++)
00306 { G4cout << " "; }
00307 G4cout << aVolume->GetName() << "[" << aVolume->GetCopyNo() << "] "
00308 << aVolume->GetLogicalVolume()->GetName() << " "
00309 << aVolume->GetLogicalVolume()->GetNoDaughters() << " "
00310 << aVolume->GetLogicalVolume()->GetMaterial()->GetName();
00311 if(aVolume->GetLogicalVolume()->GetSensitiveDetector())
00312 {
00313 G4cout << " " << aVolume->GetLogicalVolume()->GetSensitiveDetector()
00314 ->GetFullPathName();
00315 }
00316 G4cout << G4endl;
00317 for(int i=0;i<aVolume->GetLogicalVolume()->GetNoDaughters();i++)
00318 { DumpGeometricalTree(aVolume->GetLogicalVolume()->GetDaughter(i),depth+1); }
00319 }
00320
00321 void MollerDetectorConstruction::DefineMaterials()
00322 {
00323
00324
00325
00326
00327
00328
00329 G4double a;
00330 G4double z;
00331 G4double density;
00332 G4double temp = 20.27*kelvin;
00333 G4int natoms;
00334 G4int nComponents;
00335 G4String symbol;
00336
00337
00338
00339 Vacuum = new G4Material("Vacuum", z=1., a=1.01*g/mole,
00340 density= universe_mean_density,
00341 kStateGas, 2.73*kelvin, 3.e-18*pascal);
00342
00343
00344 Carbon = new G4Material("Carbon", z= 6., a= 12.01*g/mole,
00345 density= 2.265*g/cm3);
00346
00347
00348 Al = new G4Material("Aluminum", z= 13., a= 26.98*g/mole,
00349 density= 2.7*g/cm3);
00350
00351
00352 Copper = new G4Material("Copper", z= 11., a= 63.54*g/mole,
00353 density= 8.96*g/cm3);
00354
00355
00356 Pb = new G4Material("Lead", z= 82., a= 207.19*g/mole,
00357 density= 11.35*g/cm3);
00358
00359
00360 Tungsten = new G4Material("Tungsten", z= 74., a= 183.85*g/mole,
00361 density= 19.3*g/cm3);
00362
00363
00364 Iron = new G4Material("Iron", z= 26., a= 55.85*g/mole,
00365 density= 7.87*g/cm3);
00366
00367
00368 H = new G4Element("Hydrogen", symbol="H",
00369 z= 1., a= 1.00794*g/mole);
00370 LH2 = new G4Material("Liquid Hydrogen", density= 0.0708*g/cm3,
00371 nComponents=1, kStateLiquid, temp);
00372
00373 LH2->AddElement(H, natoms=1);
00374
00375
00376
00377 G4cout << G4endl << "The materials defined are : " << G4endl << G4endl;
00378 G4cout << *(G4Material::GetMaterialTable()) << G4endl;
00379
00380 }
00381
00382 G4VPhysicalVolume* MollerDetectorConstruction::ConstructDetector()
00383 {
00384
00385 G4SDManager* SDman = G4SDManager::GetSDMpointer();
00386 G4String SDname;
00387
00388 G4VisAttributes* VacVisAtt= new G4VisAttributes(G4Colour(0.3,0.8,0.5));
00389 G4VisAttributes* WVisAtt= new G4VisAttributes(G4Colour(0.7,0.7,0.7));
00390 G4VisAttributes* PbVisAtt= new G4VisAttributes(G4Colour(0.6,0.7,0.8));
00391 G4VisAttributes* CuVisAtt= new G4VisAttributes(G4Colour(1.0,0.5,0.1));
00392
00393 VacVisAtt->SetVisibility(true);
00394 VacVisAtt->SetForceWireframe (true);
00395
00396 WVisAtt->SetVisibility(true);
00397 PbVisAtt->SetVisibility(true);
00398 CuVisAtt->SetVisibility(true);
00399
00400
00401
00402
00403
00404 G4double inner_rad = 0.0*cm;
00405 G4double start_angle = 0.0*deg;
00406 G4double end_angle = 360.0*deg;
00407 G4double half_side_mom = 200.0*cm;
00408 G4double half_len_mom = 4000.0*cm;
00409
00410 G4double outer_rad_targ = 4.0*cm;
00411 G4double half_len_targ = fTargetLength/2;
00412
00413 G4cout<< "target half-length = "<<half_len_targ/cm<<G4endl;
00414
00415 G4UserLimits* userLimits = new G4UserLimits(1.0*cm);
00416
00417
00418
00419 G4Box* mother_solid = new G4Box("boxMother", half_side_mom, half_side_mom,
00420 half_len_mom);
00421
00422 mother_logic = new G4LogicalVolume(mother_solid, Vacuum, "logicMother", 0);
00423 mother_logic->SetUserLimits(userLimits);
00424
00425 mother_phys = new G4PVPlacement(0,G4ThreeVector(),
00426 mother_logic, "111",
00427 0, false, 0);
00428
00429
00430
00431
00432 target_solid = new G4Tubs("tubeTarget", inner_rad, outer_rad_targ,
00433 half_len_targ, start_angle, end_angle);
00434
00435 target_logic = new G4LogicalVolume(target_solid, LH2, "logicTarget");
00436
00437
00438 target_phys = new G4PVPlacement(0,G4ThreeVector(0, 0, 0),
00439 target_logic, "targ_0",
00440 mother_logic , false, 0);
00441
00442
00443 G4VisAttributes* motherVisAtt= new G4VisAttributes(G4Colour(1.0,1.0,1.0));
00444 motherVisAtt->SetVisibility(false);
00445 mother_logic->SetVisAttributes(motherVisAtt);
00446
00447 G4VisAttributes* targetVisAtt= new G4VisAttributes(G4Colour(1.0,1.0,0.0));
00448 targetVisAtt->SetVisibility(true);
00449 target_logic->SetVisAttributes(targetVisAtt);
00450
00451
00452
00453 const G4int numsectors=7;
00454
00455 G4double startingphi=pi/2;
00456 G4double startingz=5.8*m;
00457 G4double radius=0.6*m;
00458 G4double internalholeradius=0*m;
00459 G4double thickness = 9.9*cm;
00460
00461 G4VSensitiveDetector* collimatordetector[7];
00462
00463 G4double openingangle=pi/numsectors;
00464 G4Trd* trapeziod_solid = new G4Trd("trapeziod_solid",
00465 radius*tan(openingangle/2.),0.,thickness,thickness,(radius-internalholeradius)/2.);
00466 G4RotationMatrix rotmatrix[numsectors];
00467 char trapphysname[100], traplogname[100];
00468 char washphysname[100];
00469 char detectorname[200];
00470
00471 for (G4int sector = 1; sector <= numsectors; sector++) {
00472 G4double phi = startingphi + 2.*(sector-1)*(pi/numsectors);
00473 rotmatrix[sector-1].rotateX(pi/2.);
00474 rotmatrix[sector-1].rotateZ(-phi);
00475 G4double xpos = radius/2.*sin(phi);
00476 G4double ypos = radius/2.*cos(phi);
00477
00478 snprintf(traplogname,100,"trapeziod_log_%i",sector);
00479 trapeziod_logic.push_back(new G4LogicalVolume(trapeziod_solid, Tungsten, traplogname));
00480
00481
00482 snprintf(trapphysname,100,"trap_phys_%i",sector+NUM_COLS);
00483
00484
00485 trapeziod_phys.push_back(
00486 new G4PVPlacement(G4Transform3D(rotmatrix[sector-1],
00487 G4ThreeVector(xpos,ypos,startingz)),
00488
00489 trapeziod_logic.back(),
00490 trapphysname,
00491 mother_logic,
00492 false,
00493 0,
00494 false));
00495 snprintf(detectorname,200,"/detector%i",sector+NUM_COLS);
00496 collimatordetector[sector-1] = new MollerDetectorSD(SDname=detectorname);
00497 SDman->AddNewDetector(collimatordetector[sector-1]);
00498 trapeziod_logic.back()->SetSensitiveDetector(collimatordetector[sector-1]);
00499 trapeziod_logic.back()->SetVisAttributes(WVisAtt);
00500
00501
00502 }
00503
00504
00505
00506
00507
00508 std::vector<G4VSensitiveDetector*> detector;
00509
00510
00511
00512
00513
00514 std::vector<G4double> dethalfleng;
00515 std::vector<G4double> loc;
00516 dethalfleng.resize(NUM_COLS);
00517 loc.resize(NUM_COLS);
00518
00519
00520 std::vector<G4VSolid*> washer_solid;
00521 washer_solid.resize(NUM_COLS);
00522
00523 char washer_logicname[100];
00524
00525
00526 G4String gPath = ".";
00527 if (getenv("MOLLERGEANTDIR"))
00528 gPath = getenv("MOLLERGEANTDIR");
00529 else
00530 G4cout << "You do not have MOLLERGEANTDIR defined in your environment!" << G4endl;
00531 G4String collgeofile=(gPath+"/geometry/"+collimfileName+".dat");
00532 ReadCollimatorGeometry(collgeofile);
00533
00534 for (int i=0; i<NUM_COLS; i++) {
00535 loc[i] = (collUpstreamZ[i]+collDownstreamZ[i])/2;
00536 dethalfleng[i] = (collDownstreamZ[i]-collUpstreamZ[i])/2;
00537
00538 washer_solid[i] = new G4Cons("solWasher"+
00539 G4UIcommand::ConvertToString((i+1)),
00540 collInnerRadius[i], collOuterRadius[i],
00541 collInnerRadius[i], collOuterRadius[i], dethalfleng[i],
00542 start_angle, end_angle);
00543
00544 snprintf(washer_logicname,100,"logicWasher_%i",i);
00545 snprintf(washphysname,100,"wash_phys_%i",i);
00546
00547 SDname = "/detector";
00548 SDname+=G4UIcommand::ConvertToString((i+1));
00549
00550 detector.push_back (new MollerDetectorSD(SDname));
00551
00552 SDman->AddNewDetector(detector[i]);
00553
00554
00555 if (collMaterial[i] == "Vacuum") {
00556 washer_logic.push_back(new G4LogicalVolume(washer_solid[i], Vacuum, washer_logicname, 0));
00557 washer_logic.back()->SetSensitiveDetector(detector[i]);
00558 washer_logic.back()->SetVisAttributes(VacVisAtt);
00559 } else if (collMaterial[i] == "Tungsten") {
00560 washer_logic.push_back(new G4LogicalVolume(washer_solid[i], Tungsten, washer_logicname, 0));
00561 washer_logic.back()->SetSensitiveDetector(detector[i]);
00562 washer_logic.back()->SetVisAttributes(WVisAtt);
00563 } else if (collMaterial[i] == "Lead") {
00564 washer_logic.push_back(new G4LogicalVolume(washer_solid[i], Pb, washer_logicname, 0));
00565 washer_logic.back()->SetSensitiveDetector(detector[i]);
00566 washer_logic.back()->SetVisAttributes(PbVisAtt);
00567 } else if (collMaterial[i] == "Copper") {
00568 washer_logic.push_back(new G4LogicalVolume(washer_solid[i], Copper, washer_logicname, 0));
00569 washer_logic.back()->SetSensitiveDetector(detector[i]);
00570 washer_logic.back()->SetVisAttributes(CuVisAtt);
00571 } else {
00572 G4cerr << G4endl<< " Check collimator "<< i <<" - material not specified!" << G4endl;
00573 break;
00574 }
00575
00576
00577 washer_phys.push_back(new G4PVPlacement(0,G4ThreeVector(0, 0, loc[i]),
00578 washer_logic.back(),
00579 washphysname,
00580 mother_logic, false, 0));
00581
00582 }
00583
00584
00585 ReadGlobalMagneticField();
00586
00587 return mother_phys;
00588
00589 }
00590
00591
00592 void MollerDetectorConstruction::ReadGlobalMagneticField()
00593 {
00594 pGlobalMagnetField->ReadMagneticField();
00595 }
00596
00597
00598 void MollerDetectorConstruction::CreateGlobalMagneticField()
00599 {
00600
00601
00602
00603
00604
00605
00606 pGlobalMagnetField = new MollerGlobalMagnetField();
00607
00608
00609 fGlobalFieldManager = G4TransportationManager::GetTransportationManager()->GetFieldManager();
00610 G4TransportationManager::GetTransportationManager()->GetPropagatorInField()->SetLargestAcceptableStep(25*cm);
00611 fGlobalFieldManager->SetDetectorField(pGlobalMagnetField);
00612 fGlobalEquation = new G4Mag_UsualEqRhs(pGlobalMagnetField);
00613
00614
00615
00616
00617
00618
00619
00620
00621
00622
00623
00624 fGlobalStepper = new G4SimpleRunge(fGlobalEquation);
00625
00626
00627
00628
00629 G4MagInt_Driver* fGlobalIntgrDriver = new G4MagInt_Driver(1.0e-3*mm,
00630 fGlobalStepper,
00631 fGlobalStepper->GetNumberOfVariables());
00632
00633 fGlobalChordFinder = new G4ChordFinder(fGlobalIntgrDriver);
00634
00635
00636
00637
00638
00639
00640
00641
00642
00643
00644
00645
00646
00647
00648 fGlobalFieldManager->SetChordFinder(fGlobalChordFinder);
00649 }
00650 void MollerDetectorConstruction::ReadCollimatorGeometry(const char* filename)
00651 {
00652
00653 G4cout << G4endl << "###### Calling MollerDetectorConstruction::ReadCollimatorGeometry " << G4endl << G4endl;
00654
00655
00656
00657
00658
00659
00660 G4int coll_index=0;
00661 G4double ri,ro,zu,zd;
00662 G4String collmat;
00663
00664
00665 std::ifstream inputfile;
00666 inputfile.open(filename);
00667 G4cout << G4endl << filename << " opened for reading, ncolls =" <<NUM_COLS<< G4endl<< G4endl;
00668
00669 for (G4int nlines=0;nlines<NUM_COLS;nlines++) {
00670
00671 if (!inputfile.good()) break;
00672
00673 inputfile >> ri >> ro >> zu >> zd >> collmat;
00674
00675
00676
00677 collInnerRadius.push_back (ri*cm);
00678 collOuterRadius.push_back (ro*cm);
00679 collUpstreamZ.push_back (zu*cm);
00680 collDownstreamZ.push_back (zd*cm);
00681 collMaterial.push_back (collmat);
00682
00683 printf("coll ri ro zu zd: %2i %7.2f %7.2f %7.2f %7.2f \t %s\n",coll_index, collInnerRadius[nlines]/cm, collOuterRadius[nlines]/cm,
00684 collUpstreamZ[nlines]/cm, collDownstreamZ[nlines]/cm, collMaterial[nlines].c_str());
00685
00686
00687 coll_index++;
00688 }
00689
00690
00691
00692 inputfile.close();
00693
00694 if (coll_index!=NUM_COLS) {
00695 G4cerr <<"coll_index, "<< coll_index<<" not equal to NUM_COLS,"<<NUM_COLS<<G4endl;
00696 }
00697 else if ((int)collDownstreamZ.size()!=NUM_COLS) {
00698 G4cerr <<"collDownstreamZ.size(), "<< collDownstreamZ.size()<<" not equal to NUM_COLS, "<<NUM_COLS<<G4endl;
00699 }
00700 G4cout << "... done reading " << coll_index << " lines." << G4endl;
00701
00702 G4cout << G4endl << "###### Leaving MollerDetectorConstruction::ReadCollimatorGeometry " << G4endl << G4endl;
00703 }