5 #include "G4GeometryManager.hh" 6 #include "G4LogicalVolumeStore.hh" 7 #include "G4LogicalVolume.hh" 8 #include "G4PhysicalVolumeStore.hh" 9 #include "G4ProductionCuts.hh" 10 #include "G4PVPlacement.hh" 11 #include "G4RunManager.hh" 12 #include "G4SolidStore.hh" 13 #include "G4VisAttributes.hh" 14 #include "G4SDManager.hh" 15 #include "G4OpBoundaryProcess.hh" 43 string hd_msg = gemcOpt.args[
"LOG_MSG"].args +
" Construction: >> ";
44 double VERB = gemcOpt.args[
"G4P_VERBOSITY"].arg ;
45 string catch_v = gemcOpt.args[
"CATCH"].args;
49 G4GeometryManager::GetInstance()->OpenGeometry();
50 G4PhysicalVolumeStore::GetInstance()->Clean();
51 G4LogicalVolumeStore::GetInstance()->Clean();
52 G4SolidStore::GetInstance()->Clean();
56 (*Hall_Map)[
"root"].create_solid(gemcOpt, Hall_Map);
57 (*Hall_Map)[
"root"].create_logical_volume(mats, gemcOpt);
58 (*Hall_Map)[
"root"].create_physical_volumes(gemcOpt, NULL);
59 HasMagfield((*Hall_Map)[
"root"], gemcOpt);
62 if(VERB > 3 || catch_v ==
"root") cout << hd_msg <<
" " << (*Hall_Map)[
"root"] ;
65 cout << hd_msg <<
" Building Detector from Geometry STL Map..." << endl << endl;
71 if(VERB > 2) cout << hd_msg <<
" Mapping Physical Detector..." << endl << endl;
73 for(map<string, detector>::iterator i = Hall_Map->begin(); i!=Hall_Map->end(); i++)
75 if(VERB > 3) cout << hd_msg <<
" Scanning Detector " << i->first <<
" - existance: " << i->second.exist << endl;
78 detector mother = FindDetector(i->second.mother);
80 while(mother.
name !=
"akasha" && mother.
name !=
"notfound")
84 if(VERB > 2) cout << hd_msg <<
"\t" << i->second.mother <<
" is not activated. Its child " << i->second.name
85 <<
" will be disactivated as well." << endl;
88 mother = FindDetector(mother.
mother);
90 if(i->first !=
"root") i->second.scanned = 0;
97 vector<string> relatives;
99 for( map<string, detector>::iterator i = Hall_Map->begin(); i!=Hall_Map->end(); i++)
102 if(i->second.exist == 0)
continue;
106 if(i->first !=
"root") relatives.push_back(i->second.name);
108 while(relatives.size() > 0)
110 detector kid = FindDetector(relatives.back());
114 if(mom.name !=
"akasha" && mom.name ==
"notfound")
116 cout << hd_msg <<
" Mom <" << mom.name<<
"> was not created for <" << kid.
name <<
">. " 117 <<
" We have a No Child Left Behind policy. Exiting. " << endl << endl;
122 if(VERB > 3 || kid.
name.find(catch_v) != string::npos)
124 for(
unsigned int ir=0; ir<relatives.size()-1; ir++) cout <<
"\t";
125 cout << hd_msg <<
" Checking " << kid.
name <<
", child of " << mom.name
126 <<
", for a living ancestor. " 127 <<
" This Geneaology Depth is " << relatives.size() <<
"." << endl;
131 if(kid.
scanned == 0 && mom.scanned == 1)
133 if(VERB > 3 || kid.
name.find(catch_v) != string::npos)
135 for(
unsigned int ir=0; ir<relatives.size()-1; ir++) cout <<
"\t";
136 cout << hd_msg <<
" Found: " << kid.
name 137 <<
" is not built yet but its mommie " << mom.name <<
" is." 138 <<
" Building " << kid.
name <<
" of type: " << kid.
type <<
"..." << endl;
142 if(kid.
type.find(
"CopyOf") == 0)
146 string operands(kid.
type, 6, kid.
type.size());
151 detector dorig = FindDetector(original);
156 relatives.push_back(original);
157 if(VERB > 3 || kid.
name.find(catch_v) != string::npos)
159 for(
unsigned int ir=0; ir<relatives.size()-1; ir++) cout <<
"\t";
160 cout << hd_msg << kid.
name <<
" is copied volume. " 161 <<
" Must build: " << original <<
" first " << endl;
167 BuildDetector(kid.
name);
172 else if(kid.
type.find(
"Operation:") == 0)
175 if(kid.
type.find(
"Operation:~") == 0 || kid.
type.find(
"Operation:@") == 0 ) sstart = 11;
178 string operands(kid.
type, sstart, kid.
type.size());
180 string firstop, secondop, tmpop;
181 ops >> firstop >> tmpop >> secondop;
185 detector dsecondop = FindDetector(secondop);
188 relatives.push_back(secondop);
189 if(VERB > 3 || kid.
name.find(catch_v) != string::npos)
191 for(
unsigned int ir=0; ir<relatives.size()-1; ir++) cout <<
"\t";
192 cout << hd_msg << kid.
name <<
" is the result of an operation. " 193 <<
" Must build: " << secondop <<
" first " << endl;
196 detector dfirstop = FindDetector(firstop);
199 relatives.push_back(firstop);
200 if(VERB > 3 || kid.
name.find(catch_v) != string::npos)
202 for(
unsigned int ir=0; ir<relatives.size()-1; ir++) cout <<
"\t";
203 cout << hd_msg << kid.
name <<
" is the result of an operation. " 204 <<
" Must build: " << firstop <<
" first " << endl;
211 BuildDetector(kid.
name);
218 BuildDetector(kid.
name);
225 if(kid.
scanned == 0 && mom.scanned == 0)
227 relatives.push_back(kid.
mother);
231 if(kid.
scanned == 1 && relatives.size())
233 if(VERB > 3 || kid.
name.find(catch_v) != string::npos)
234 cout << hd_msg <<
" " << kid <<
" is built." << endl << endl;
236 relatives.pop_back();
250 const int nEntries_Mirror = 2;
251 double PhotonEnergy_Mirror[nEntries_Mirror] = { 1.034*eV, 5.144*eV };
253 vector<G4OpticalSurface*> Mirror_Surfaces;
254 vector<G4MaterialPropertiesTable*> Mirror_MPT;
255 vector<G4LogicalBorderSurface*> Mirrors;
256 vector<G4LogicalSkinSurface*> SMirrors;
264 for( map<string, detector>::iterator i = Hall_Map->begin(); i!=Hall_Map->end(); i++)
267 if(i->second.identity.size())
268 if(i->second.identity[0].name ==
"Mirror" && i->second.identity[0].rule ==
"WithSurface:")
270 string name = i->first;
272 string model[2] = {
"unified",
"LUT"};
273 string finish[2] = {
"polished",
"ground"};
274 string surfaces[2] = {
"dielectric_metal",
"dielectric_dielectric"};
275 string material =
"";
276 double refraction = 1.0;
277 double efficiency = 1.0;
278 double reflection = 1.0;
283 for(
unsigned int j=0; j<i->second.identity.size(); j++)
287 if(i->second.identity[j].name ==
"WithBorderVolume:")
289 borderv = i->second.identity[j].rule;
295 if(i->second.identity[j].rule ==
"WithSurface:")
297 surfaceType = i->second.identity[j].id;
303 if(i->second.identity[j].name ==
"With" && i->second.identity[j].rule ==
"Finish:")
305 finishType = i->second.identity[j].id;
310 if(i->second.identity[j].name ==
"Refraction" && i->second.identity[j].rule ==
"Index:")
312 refraction = i->second.identity[j].id/1000000.0;
316 if(i->second.identity[j].name ==
"With" && i->second.identity[j].rule ==
"Reflectivity:")
318 reflection = i->second.identity[j].id/1000000.0;
322 if(i->second.identity[j].name ==
"With" && i->second.identity[j].rule ==
"Efficiency:")
324 efficiency = i->second.identity[j].id/1000000.0;
330 if(i->second.identity[j].name ==
"With" && i->second.identity[j].rule ==
"Model:")
332 modelType = i->second.identity[j].id;
336 if( i->second.identity[j].name ==
"WithMaterial:" )
338 material = i->second.identity[j].rule;
340 if(VERB > 3 || name.find(catch_v) != string::npos)
341 cout << hd_msg <<
" Using properties of material " << material <<
" for mirror boundary of volume name " << name << endl;
347 if(!(*Hall_Map)[borderv].GetPhysical() && borderv !=
"MirrorSkin")
349 cout << hd_msg <<
" Border volume " << borderv <<
" is not found for volume " << name <<
". Exiting." << endl;
353 string mirror_surf =
"Mirror_Surface_for_" + name +
"_and_" + borderv;
354 if(borderv ==
"MirrorSkin")
356 mirror_surf =
"Mirror_Skin_Surface_for_" + name;
360 Mirror_Surfaces.push_back(
new G4OpticalSurface(mirror_surf));
363 bool MPT_exists =
false;
364 if( material !=
"" && ( (*mats)[material] )->GetMaterialPropertiesTable() )
366 Mirror_MPT.push_back( ( (*mats)[material] )->GetMaterialPropertiesTable() );
371 Mirror_MPT.push_back(
new G4MaterialPropertiesTable());
375 if(surfaceType == 0) Mirror_Surfaces.back()->SetType(dielectric_metal);
376 if(surfaceType == 1) Mirror_Surfaces.back()->SetType(dielectric_dielectric);
379 if(finishType == 0) Mirror_Surfaces.back()->SetFinish(polished);
380 if(finishType == 1) Mirror_Surfaces.back()->SetFinish(ground);
383 if(modelType == 0) Mirror_Surfaces.back()->SetModel(unified);
384 if(modelType == 1) Mirror_Surfaces.back()->SetModel(LUT);
387 double r_index[2] = {refraction, refraction};
388 double reflect[2] = {reflection, reflection};
389 double efficie[2] = {efficiency, efficiency};
390 double spike[2] = {1.0, 1.0};
391 double slobe[2] = {0.0, 0.0};
392 double sback[2] = {0.0, 0.0};
393 double sdiff[2] = {0.0, 0.0};
397 Mirror_MPT.back()->AddProperty(
"RINDEX", PhotonEnergy_Mirror, r_index, nEntries_Mirror);
398 Mirror_MPT.back()->AddProperty(
"REFLECTIVITY", PhotonEnergy_Mirror, reflect, nEntries_Mirror);
399 Mirror_MPT.back()->AddProperty(
"EFFICIENCY", PhotonEnergy_Mirror, efficie, nEntries_Mirror);
400 Mirror_MPT.back()->AddProperty(
"SPECULARSPIKECONSTANT", PhotonEnergy_Mirror, spike, nEntries_Mirror);
401 Mirror_MPT.back()->AddProperty(
"SPECULARLOBECONSTANT", PhotonEnergy_Mirror, slobe, nEntries_Mirror);
402 Mirror_MPT.back()->AddProperty(
"BACKSCATTERCONSTANT", PhotonEnergy_Mirror, sback, nEntries_Mirror);
403 Mirror_MPT.back()->AddProperty(
"DIFFUSELOBECONSTANT", PhotonEnergy_Mirror, sdiff, nEntries_Mirror);
406 Mirror_Surfaces.back()->SetMaterialPropertiesTable(Mirror_MPT.back());
408 if(borderv==
"MirrorSkin")
410 SMirrors.push_back(
new G4LogicalSkinSurface(name,
411 (*Hall_Map)[name].GetLogical(), Mirror_Surfaces.back()));
416 Mirrors.push_back(
new G4LogicalBorderSurface(name,
417 (*Hall_Map)[borderv].GetPhysical(),
418 (*Hall_Map)[name].GetPhysical(), Mirror_Surfaces.back()));
422 if(VERB > 3 || name.find(catch_v) != string::npos)
424 cout << hd_msg <<
" " << name <<
" is a mirror:" << endl;
425 cout <<
" > Border Volume: " << borderv << endl;
426 cout <<
" > Surface Type: " << surfaces[surfaceType] << endl;
427 cout <<
" > Finish: " << finish[finishType] << endl;
428 cout <<
" > Refraction Index: " << refraction << endl;
429 cout <<
" > Reflectivity: " << reflection << endl;
430 cout <<
" > Efficiency: " << efficiency << endl;
431 cout <<
" > Model: " << model[modelType] << endl;
434 Mirror_MPT.back()->DumpTable();
442 const G4int RICHmirror_Len=7;
443 G4double RICHmirror_PhoE[RICHmirror_Len]=
444 { 1.9074*eV, 2.0664*eV, 2.2543*eV, 3.5424*eV, 4.1328*eV, 4.9594*eV, 6.1992*eV };
445 G4double RICHmirror_Ref[RICHmirror_Len]=
446 { 0.88, 0.89, 0.90, 0.90, 0.88, 0.85, 0.74 };
447 G4double RICHmirror_PhoE2[2]={ 1.9074*eV, 6.1992*eV };
448 G4double RICHmirror_Eff[2] ={ 0., 0. };
450 G4MaterialPropertiesTable* RICHmirror_MPT =
new G4MaterialPropertiesTable();
451 RICHmirror_MPT->AddProperty(
"REFLECTIVITY", RICHmirror_PhoE, RICHmirror_Ref, RICHmirror_Len);
452 RICHmirror_MPT->AddProperty(
"EFFICIENCY", RICHmirror_PhoE2, RICHmirror_Eff, 2);
454 G4OpticalSurface* RICHmirror_OptSurf =
new G4OpticalSurface(
"RICHmirror_OptSurf");
455 RICHmirror_OptSurf->SetType(dielectric_metal);
456 RICHmirror_OptSurf->SetFinish(polished);
457 RICHmirror_OptSurf->SetModel(unified);
458 RICHmirror_OptSurf->SetMaterialPropertiesTable(RICHmirror_MPT);
468 return (*Hall_Map)[
"root"].GetPhysical();
471 #include "G4UserLimits.hh" 475 string hd_msg = gemcOpt.args[
"LOG_MSG"].args +
" Sensitivity: >> ";
476 double VERB = gemcOpt.args[
"HIT_VERBOSITY"].arg ;
477 string catch_v = gemcOpt.args[
"CATCH"].args;
484 G4SDManager* SDman = G4SDManager::GetSDMpointer();
485 if (!SDman)
throw "Can't get G4SDManager";
487 if(VERB > 5 || detect.
name.find(catch_v) != string::npos)
488 cout << hd_msg <<
" " << detect.
name <<
" is sensitive." << endl;
491 map<string, MSensitiveDetector*>::iterator itr = SeDe_Map.find(sensi);
492 if(itr == SeDe_Map.end())
494 if(VERB > 3 || detect.
name.find(catch_v) != string::npos)
495 cout << endl << hd_msg <<
" Sensitive detector <" << sensi
496 <<
"> doesn't exist yet. Adding <" << sensi <<
">. " << endl;
501 SeRe_Map[sensi] =
new G4Region(sensi);
502 SePC_Map[sensi] =
new G4ProductionCuts;
503 SePC_Map[sensi] ->SetProductionCut(SeDe_Map[sensi]->SDID.ProdThreshold);
504 SeRe_Map[sensi]->SetProductionCuts(SePC_Map[sensi]);
506 if(VERB > 3 || detect.
name.find(catch_v) != string::npos)
507 cout << hd_msg <<
" Max Step for Sensitive detector <" << sensi
508 <<
">: " << SeDe_Map[sensi]->SDID.MaxStep/mm <<
" mm." << endl
509 << hd_msg <<
" Production Cut for Sensitive detector <" << sensi
510 <<
">: " << SeDe_Map[sensi]->SDID.ProdThreshold/mm <<
" mm." << endl << endl;
513 SeDe_Map[sensi]->Hall_Map = Hall_Map;
515 SDman->AddNewDetector( SeDe_Map[sensi]);
521 detect.
SetUserLimits(
new G4UserLimits(SeDe_Map[sensi]->SDID.MaxStep, SeDe_Map[sensi]->SDID.MaxStep));
523 map<string, G4Region*>::iterator itrRE = SeRe_Map.find(sensi);
524 if(itrRE != SeRe_Map.end()) SeRe_Map[sensi]->AddRootLogicalVolume(detect.
GetLogical());
527 cout << hd_msg <<
" Attention: " << sensi <<
" doesn't exist in the sensitive detector list. Aborting. " << endl;
538 string hd_msg = gemcOpt.args[
"LOG_MSG"].args +
" Magnetic Field: >> ";
539 double VERB = gemcOpt.args[
"MGN_VERBOSITY"].arg ;
540 string catch_v = gemcOpt.args[
"CATCH"].args;
541 string field = gemcOpt.args[
"NO_FIELD"].args;
543 if(field ==
"all" || detect.
name.find(field) != string::npos)
550 if(VERB > 5 || detect.
name.find(catch_v) != string::npos)
551 cout << hd_msg <<
" " << detect.
name <<
" is inside " << magf <<
" magnetic field." << endl;
553 map<string, MagneticField>::iterator itr = FieldMap->find(magf);
554 if(itr == FieldMap->end())
556 cout << hd_msg <<
" Magnetic Field <" << magf
557 <<
"> is not defined. Exiting." << endl;
560 if(itr->second.get_MFM() == NULL)
562 cout << hd_msg <<
" Magnetic Field <" << magf
563 <<
"> doesn't exist yet. Adding <" << magf <<
">. " << endl;
564 itr->second.create_MFM();
567 if(itr->second.get_MFM() != NULL)
571 if(VERB > 6 || detect.
name.find(catch_v) != string::npos)
572 cout << hd_msg <<
" Field <" << magf <<
"> assigned to " << detect.
name <<
"." << endl;
582 cout <<
"Updating geometry... " << endl;
583 G4RunManager::GetRunManager()->GeometryHasBeenModified();
586 detector MDetectorConstruction::FindDetector(
string name)
588 map<string, detector>::iterator it = Hall_Map->find(name);
589 if(it != Hall_Map->end())
593 notfound.
name =
"notfound";
594 notfound.mother =
"notfound";
600 void MDetectorConstruction::BuildDetector(
string name)
605 if(kid.
name !=
"notfound" || mom.
name !=
"notfound")
608 (*Hall_Map)[kid.
name].create_solid(gemcOpt, Hall_Map);
610 if((*Hall_Map)[kid.
name].create_logical_volume(mats, gemcOpt))
613 (*Hall_Map)[kid.
name].create_physical_volumes(gemcOpt, mom.
GetLogical());
614 IsSensitive((*Hall_Map)[kid.
name], gemcOpt);
615 HasMagfield((*Hall_Map)[kid.
name], gemcOpt);
617 (*Hall_Map)[kid.
name].scanned = 1;
620 if(kid.
name ==
"notfound" )
621 cout <<
" Attention: " << kid.
name <<
" not found. " << endl;
622 if(mom.
name ==
"notfound" )
623 cout <<
" Attention: " << mom.
name <<
" not found. " << endl;
G4VPhysicalVolume * Construct()
MDetectorConstruction(gemc_opts Opts)
G4LogicalVolume * GetLogical()
Returns Logical Volume pointer.
string sensitivity
Defines the Sensitive Detector. possible choices: "no" "hits collection name".
string mother
Mother Volume name.
void AssignMFM(G4FieldManager *MFM)
Assigns Magnetic Field Manager to LogicV.
string name
Name of the volume. Since this is the key of the STL map, it has to be unique.
void IsSensitive(detector, gemc_opts)
void SetUserLimits(G4UserLimits *L)
string magfield
Magnetic Field. The string "no" means that the field is inherited from the mother volume...
void HasMagfield(detector, gemc_opts)
int exist
detector ON/OFF switch
string type
solid type. This follows the GEANT4 definitions
int scanned
for use during construction
void setSensitivity(G4VSensitiveDetector *SD)
Assign the sensitive detector to the Logical Volume.