6 #include "nug4/G4Base/DetectorConstruction.h"
8 #include "CLHEP/Geometry/Transform3D.h"
9 #include "CLHEP/Vector/Rotation.h"
10 #include "CLHEP/Vector/ThreeVector.h"
11 #include "Geant4/G4LogicalVolume.hh"
12 #include "Geant4/G4PVPlacement.hh"
13 #include "Geant4/G4RotationMatrix.hh"
14 #include "Geant4/G4ThreeVector.hh"
15 #include "Geant4/G4Types.hh"
16 #include "Geant4/G4VPhysicalVolume.hh"
26 #include "art/Framework/Services/Registry/ServiceHandle.h"
27 #include "cetlib_except/exception.h"
28 #include "messagefacility/MessageLogger/MessageLogger.h"
35 : G4VUserParallelWorld(name), fUseLitePhotons(useLitePhotons)
45 mf::LogInfo(
"OpDetReadoutGeometry")
49 G4VPhysicalVolume* ParallelWorld = GetWorld();
52 std::vector<G4LogicalVolume*> OpDetVolumes;
53 std::vector<G4Transform3D> OpDetTransformations;
56 G4VPhysicalVolume* WorldPhysical = g4b::DetectorConstruction::GetWorld();
59 std::vector<G4Transform3D> EmptyVector;
74 if (OpDetVolumes.size() > 0) {
77 for (
unsigned int i = 0; i != OpDetVolumes.size(); i++) {
78 std::stringstream VolumeName;
80 VolumeName.str(
"OpDetVolume_");
83 G4Transform3D TheTransform = OpDetTransformations.at(i);
85 G4VSolid* TheSolid = OpDetVolumes.at(i)->GetSolid();
86 G4Material* TheMaterial = OpDetVolumes.at(i)->GetMaterial();
87 G4LogicalVolume* TheLogVolume =
88 new G4LogicalVolume(TheSolid, TheMaterial, VolumeName.str().c_str());
90 TheLogVolume->SetSensitiveDetector(TheSD);
92 G4PVPlacement* ThePlacement =
new G4PVPlacement(
93 TheTransform, VolumeName.str().c_str(), TheLogVolume, ParallelWorld,
false, 0);
103 std::vector<G4LogicalVolume*> OpParamVolumesFound;
104 std::vector<G4Transform3D> OpParamTransformationsFound;
106 art::ServiceHandle<sim::LArG4Parameters const> lgp;
108 std::vector<std::string> OpParamModels = lgp->OpticalParamModels();
109 std::vector<std::string> OpParamVolumes = lgp->OpticalParamVolumes();
110 std::vector<int> OpParamOrientations = lgp->OpticalParamOrientations();
112 std::vector<std::vector<std::vector<double>>> OpParamParameters = lgp->OpticalParamParameters();
114 if ((OpParamModels.size() != OpParamVolumes.size()) ||
115 (OpParamModels.size() != OpParamOrientations.size()) ||
116 (OpParamModels.size() != OpParamParameters.size())) {
117 throw cet::exception(
"OpDetReadoutGeometry")
118 <<
"sizes of OpParam specification vectors do not match\n";
121 for (
size_t imodel = 0; imodel != OpParamVolumes.size(); ++imodel) {
124 OpParamVolumes.at(imodel),
127 OpParamTransformationsFound);
128 mf::LogInfo(
"OpDetReadoutGeometry")
129 <<
"Found " << OpParamVolumesFound.size() <<
" volumes of name "
130 << OpParamVolumes.at(imodel) <<
" to attach optical parameterization "
131 << OpParamModels.at(imodel) << std::endl;
137 std::stringstream SDName(
"");
138 SDName << OpParamModels.at(imodel) <<
"_" << imodel;
141 OpParamModels.at(imodel),
142 OpParamOrientations.at(imodel),
143 OpParamParameters.at(imodel));
145 if (OpParamVolumesFound.size() > 0) {
146 for (
unsigned int ivol = 0; ivol != OpParamVolumes.size(); ivol++) {
147 std::stringstream VolumeName;
149 VolumeName.str(
"OpParamVolume_");
152 G4Transform3D TheTransform = OpParamTransformationsFound.at(ivol);
154 G4VSolid* TheSolid = OpParamVolumesFound.at(ivol)->GetSolid();
155 G4Material* TheMaterial = OpParamVolumesFound.at(ivol)->GetMaterial();
156 G4LogicalVolume* TheLogVolume =
157 new G4LogicalVolume(TheSolid, TheMaterial, VolumeName.str().c_str());
159 G4PVPlacement* ThePlacement =
new G4PVPlacement(
160 TheTransform, VolumeName.str().c_str(), TheLogVolume, ParallelWorld,
false, 0);
162 TheLogVolume->SetSensitiveDetector(ParamSD);
165 ThePlacement->GetTranslation();
174 std::vector<G4Transform3D> TransformSoFar,
175 std::vector<G4LogicalVolume*>& OpDetVolumes,
176 std::vector<G4Transform3D>& OpDetTransformations)
180 G4ThreeVector Translation = PhysicalVolume->GetObjectTranslation();
181 G4RotationMatrix Rotation = PhysicalVolume->GetObjectRotationValue();
182 G4Transform3D NextTransform(Rotation, Translation);
184 TransformSoFar.push_back(NextTransform);
187 G4String OpDetNameUnderscore = OpDetName +
"_";
188 G4String VolumeName = PhysicalVolume->GetName();
189 if ((VolumeName == OpDetName) ||
190 (VolumeName.find(OpDetNameUnderscore, 0, OpDetNameUnderscore.length()) == 0)) {
193 G4ThreeVector Trans(0, 0, 0);
194 G4RotationMatrix Rot(0, 0, 0);
195 G4Transform3D TotalTransform(Rot, Trans);
199 for (std::vector<G4Transform3D>::iterator it = TransformSoFar.begin();
200 it != TransformSoFar.end();
202 CLHEP::Hep3Vector trans = (*it).getTranslation();
203 CLHEP::HepRotation rot = (*it).getRotation();
204 TotalTransform = TotalTransform * (*it);
207 OpDetVolumes.push_back(PhysicalVolume->GetLogicalVolume());
208 OpDetTransformations.push_back(TotalTransform);
212 G4LogicalVolume* LogicalVolume = PhysicalVolume->GetLogicalVolume();
215 G4int NumberDaughters = LogicalVolume->GetNoDaughters();
216 for (G4int i = 0; i != NumberDaughters; ++i) {
218 G4VPhysicalVolume* Daughter = LogicalVolume->GetDaughter(i);
221 FindVolumes(Daughter, OpDetName, TransformSoFar, OpDetVolumes, OpDetTransformations);
void FindVolumes(G4VPhysicalVolume *, G4String, std::vector< G4Transform3D >, std::vector< G4LogicalVolume * > &, std::vector< G4Transform3D > &)
Store parameters for running LArG4.
G4String fOpDetSensitiveName
std::vector< G4Transform3D > fOpDetTransformations
OpDetReadoutGeometry(G4String OpDetSensitiveName, const G4String name="OpDetReadoutGeometry", bool useLitePhotons=false)
bool const fUseLitePhotons
Pass-through option for sensitive detector.
std::vector< G4LogicalVolume * > fOpDetVolumes
virtual ~OpDetReadoutGeometry()
void AddPhysicalVolume(G4VPhysicalVolume *)
static OpDetLookup * Instance()
OpDetLookup * TheOpDetLookup