File indexing completed on 2025-02-23 09:22:43
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032 #include "RE02DetectorConstruction.hh"
0033
0034 #include "RE02NestedPhantomParameterisation.hh"
0035
0036 #include "G4Box.hh"
0037 #include "G4Colour.hh"
0038 #include "G4LogicalVolume.hh"
0039 #include "G4Material.hh"
0040 #include "G4NistManager.hh"
0041 #include "G4PSCellFlux3D.hh"
0042 #include "G4PSEnergyDeposit3D.hh"
0043 #include "G4PSFlatSurfaceCurrent3D.hh"
0044 #include "G4PSFlatSurfaceFlux3D.hh"
0045 #include "G4PSNofStep3D.hh"
0046 #include "G4PSPassageCellFlux3D.hh"
0047 #include "G4PVParameterised.hh"
0048 #include "G4PVPlacement.hh"
0049 #include "G4SDChargedFilter.hh"
0050 #include "G4SDManager.hh"
0051 #include "G4SDParticleFilter.hh"
0052 #include "G4SDParticleWithEnergyFilter.hh"
0053 #include "G4SystemOfUnits.hh"
0054 #include "G4VisAttributes.hh"
0055 #include "G4ios.hh"
0056
0057
0058
0059
0060
0061
0062
0063
0064
0065
0066
0067
0068
0069
0070
0071
0072
0073
0074
0075
0076
0077
0078
0079
0080
0081
0082
0083
0084
0085
0086
0087
0088
0089
0090
0091
0092
0093
0094
0095
0096
0097
0098
0099
0100
0101 RE02DetectorConstruction::RE02DetectorConstruction() : G4VUserDetectorConstruction()
0102 {
0103
0104 fPhantomSize.setX(200. * mm);
0105 fPhantomSize.setY(200. * mm);
0106 fPhantomSize.setZ(400. * mm);
0107 fNx = fNy = fNz = 100;
0108 fInsertLead = TRUE;
0109 }
0110
0111
0112 RE02DetectorConstruction::~RE02DetectorConstruction()
0113 {
0114 ;
0115 }
0116
0117
0118 G4VPhysicalVolume* RE02DetectorConstruction::Construct()
0119 {
0120
0121
0122
0123
0124
0125
0126
0127 G4NistManager* NISTman = G4NistManager::Instance();
0128 G4Material* air = NISTman->FindOrBuildMaterial("G4_AIR");
0129 G4Material* water = NISTman->FindOrBuildMaterial("G4_WATER");
0130 G4Material* lead = NISTman->FindOrBuildMaterial("G4_Pb");
0131
0132
0133
0134 G4cout << G4endl << "The materials defined are : " << G4endl << G4endl;
0135 G4cout << *(G4Material::GetMaterialTable()) << G4endl;
0136
0137
0138
0139
0140
0141
0142
0143
0144
0145 G4ThreeVector worldSize = G4ThreeVector(200 * cm, 200 * cm, 200 * cm);
0146
0147 G4Box* solidWorld =
0148 new G4Box("world", worldSize.x() / 2., worldSize.y() / 2., worldSize.z() / 2.);
0149 G4LogicalVolume* logicWorld = new G4LogicalVolume(solidWorld, air, "World", 0, 0, 0);
0150
0151
0152
0153 G4VPhysicalVolume* physiWorld = new G4PVPlacement(0,
0154 G4ThreeVector(),
0155 logicWorld,
0156 "World",
0157 0,
0158 false,
0159 0);
0160
0161
0162
0163
0164
0165
0166
0167
0168
0169
0170 G4ThreeVector phantomSize = fPhantomSize;
0171
0172 G4Box* solidPhantom =
0173 new G4Box("phantom", phantomSize.x() / 2., phantomSize.y() / 2., phantomSize.z() / 2.);
0174 G4LogicalVolume* logicPhantom = new G4LogicalVolume(solidPhantom, water, "Phantom", 0, 0, 0);
0175
0176 G4RotationMatrix* rot = new G4RotationMatrix();
0177
0178 G4ThreeVector positionPhantom;
0179
0180 new G4PVPlacement(rot,
0181 positionPhantom,
0182 logicPhantom,
0183 "Phantom",
0184 logicWorld,
0185 false,
0186 0);
0187
0188
0189
0190
0191
0192 G4cout << "<-- RE02DetectorConstruction::Construct-------" << G4endl;
0193 G4cout << " Water Phantom Size " << fPhantomSize / mm << G4endl;
0194 G4cout << " Segmentation (" << fNx << "," << fNy << "," << fNz << ")" << G4endl;
0195 G4cout << " Lead plate at even copy # (0-False,1-True): " << IsLeadSegment() << G4endl;
0196 G4cout << "<---------------------------------------------" << G4endl;
0197
0198
0199 G4int nxCells = fNx;
0200 G4int nyCells = fNy;
0201 G4int nzCells = fNz;
0202
0203 G4ThreeVector sensSize;
0204 sensSize.setX(phantomSize.x() / (G4double)nxCells);
0205 sensSize.setY(phantomSize.y() / (G4double)nyCells);
0206 sensSize.setZ(phantomSize.z() / (G4double)nzCells);
0207
0208
0209
0210
0211
0212 G4String yRepName("RepY");
0213 G4VSolid* solYRep =
0214 new G4Box(yRepName, phantomSize.x() / 2., sensSize.y() / 2., phantomSize.z() / 2.);
0215 G4LogicalVolume* logYRep = new G4LogicalVolume(solYRep, water, yRepName);
0216
0217 new G4PVReplica(yRepName, logYRep, logicPhantom, kYAxis, fNy, sensSize.y());
0218
0219 G4String xRepName("RepX");
0220 G4VSolid* solXRep =
0221 new G4Box(xRepName, sensSize.x() / 2., sensSize.y() / 2., phantomSize.z() / 2.);
0222 G4LogicalVolume* logXRep = new G4LogicalVolume(solXRep, water, xRepName);
0223
0224 new G4PVReplica(xRepName, logXRep, logYRep, kXAxis, fNx, sensSize.x());
0225
0226
0227
0228
0229
0230
0231 G4String zVoxName("phantomSens");
0232 G4VSolid* solVoxel = new G4Box(zVoxName, sensSize.x() / 2., sensSize.y() / 2., sensSize.z() / 2.);
0233 fLVPhantomSens = new G4LogicalVolume(solVoxel, water, zVoxName);
0234
0235
0236 std::vector<G4Material*> phantomMat(2, water);
0237 if (IsLeadSegment()) phantomMat[1] = lead;
0238
0239
0240
0241
0242 RE02NestedPhantomParameterisation* paramPhantom =
0243 new RE02NestedPhantomParameterisation(sensSize / 2., nzCells, phantomMat);
0244
0245 new G4PVParameterised("PhantomSens",
0246 fLVPhantomSens,
0247 logXRep,
0248 kUndefined,
0249 nzCells,
0250 paramPhantom);
0251
0252
0253
0254
0255
0256
0257
0258
0259 G4VisAttributes* boxVisAtt = new G4VisAttributes(G4Colour(1.0, 1.0, 1.0));
0260 logicWorld->SetVisAttributes(boxVisAtt);
0261
0262
0263
0264 G4VisAttributes* phantomVisAtt = new G4VisAttributes(G4Colour(1.0, 1.0, 0.0));
0265 logicPhantom->SetVisAttributes(phantomVisAtt);
0266
0267
0268 G4VisAttributes* yRepVisAtt = new G4VisAttributes(G4Colour(0.0, 1.0, 0.0));
0269 logYRep->SetVisAttributes(yRepVisAtt);
0270 G4VisAttributes* xRepVisAtt = new G4VisAttributes(G4Colour(0.0, 1.0, 0.0));
0271 logXRep->SetVisAttributes(xRepVisAtt);
0272
0273
0274 fLVPhantomSens->SetVisAttributes(G4VisAttributes::GetInvisible());
0275
0276 return physiWorld;
0277 }
0278
0279 void RE02DetectorConstruction::ConstructSDandField()
0280 {
0281
0282
0283
0284
0285
0286 G4SDManager* pSDman = G4SDManager::GetSDMpointer();
0287
0288
0289 G4String phantomSDname = "PhantomSD";
0290
0291
0292
0293
0294
0295
0296 G4MultiFunctionalDetector* mFDet = new G4MultiFunctionalDetector(phantomSDname);
0297 pSDman->AddNewDetector(mFDet);
0298 fLVPhantomSens->SetSensitiveDetector(mFDet);
0299
0300
0301
0302
0303
0304
0305
0306
0307
0308 G4String fltName, particleName;
0309
0310
0311 G4SDParticleFilter* protonFilter =
0312 new G4SDParticleFilter(fltName = "protonFilter", particleName = "proton");
0313
0314
0315 G4SDParticleFilter* electronFilter = new G4SDParticleFilter(fltName = "electronFilter");
0316 electronFilter->add(particleName = "e+");
0317 electronFilter->add(particleName = "e-");
0318
0319
0320 G4SDChargedFilter* chargedFilter = new G4SDChargedFilter(fltName = "chargedFilter");
0321
0322
0323
0324
0325
0326
0327
0328
0329
0330 G4String psName;
0331 G4PSEnergyDeposit3D* scorer0 = new G4PSEnergyDeposit3D(psName = "totalEDep", fNx, fNy, fNz);
0332 G4PSEnergyDeposit3D* scorer1 = new G4PSEnergyDeposit3D(psName = "protonEDep", fNx, fNy, fNz);
0333 scorer1->SetFilter(protonFilter);
0334
0335
0336
0337 G4PSNofStep3D* scorer2 = new G4PSNofStep3D(psName = "protonNStep", fNx, fNy, fNz);
0338 scorer2->SetFilter(protonFilter);
0339
0340
0341
0342 G4PSPassageCellFlux3D* scorer3 =
0343 new G4PSPassageCellFlux3D(psName = "chargedPassCellFlux", fNx, fNy, fNz);
0344 G4PSCellFlux3D* scorer4 = new G4PSCellFlux3D(psName = "chargedCellFlux", fNx, fNy, fNz);
0345 G4PSFlatSurfaceFlux3D* scorer5 =
0346 new G4PSFlatSurfaceFlux3D(psName = "chargedSurfFlux", fFlux_InOut, fNx, fNy, fNz);
0347 scorer3->SetFilter(chargedFilter);
0348 scorer4->SetFilter(chargedFilter);
0349 scorer5->SetFilter(chargedFilter);
0350
0351
0352
0353
0354
0355 mFDet->RegisterPrimitive(scorer0);
0356 mFDet->RegisterPrimitive(scorer1);
0357 mFDet->RegisterPrimitive(scorer2);
0358 mFDet->RegisterPrimitive(scorer3);
0359 mFDet->RegisterPrimitive(scorer4);
0360 mFDet->RegisterPrimitive(scorer5);
0361
0362
0363
0364
0365
0366
0367
0368
0369
0370
0371
0372
0373
0374 for (G4int i = 0; i < 4; i++) {
0375 std::ostringstream name;
0376 name << "gammaSurfCurr" << std::setfill('0') << std::setw(3) << i;
0377 G4String psgName = name.str();
0378 G4double kmin = std::pow(10., (G4double)i) * keV;
0379 G4double kmax = std::pow(10., (G4double)(i + 1)) * keV;
0380
0381 G4SDParticleWithEnergyFilter* pkinEFilter =
0382 new G4SDParticleWithEnergyFilter(fltName = "gammaE filter", kmin, kmax);
0383 pkinEFilter->add("gamma");
0384 pkinEFilter->show();
0385
0386 G4PSFlatSurfaceCurrent3D* scorer =
0387 new G4PSFlatSurfaceCurrent3D(psgName, fCurrent_InOut, fNx, fNy, fNz);
0388 scorer->SetFilter(pkinEFilter);
0389 mFDet->RegisterPrimitive(scorer);
0390 }
0391 }