38class RMGVertexConfinement :
public RMGVVertexGenerator {
52 G4ThreeVector volume_center = G4ThreeVector(0, 0, 0);
53 double sphere_inner_radius = 0;
54 double sphere_outer_radius = -1;
55 double cylinder_inner_radius = 0;
56 double cylinder_outer_radius = -1;
57 double cylinder_height = -1;
58 double cylinder_starting_angle = 0;
59 double cylinder_spanning_angle = CLHEP::twopi;
60 double box_x_length = -1;
61 double box_y_length = -1;
62 double box_z_length = -1;
76 kIntersectPhysicalWithGeometrical,
91 void BeginOfRunAction(
const G4Run* run)
override;
92 void EndOfRunAction(
const G4Run* run)
override;
109 void AddGeometricalVolume(GenericGeometricalSolidData& data) {
110 fGeomVolumeData.emplace_back(data);
114 void SetSamplingMode(
SamplingMode mode) { fSamplingMode = mode; }
115 void SetFirstSamplingVolumeType(
VolumeType type) { fFirstSamplingVolumeType = type; }
116 void SetWeightByMass(
bool mode) { fWeightByMass = mode; }
117 void SetWeightByMassIsotope(
int z,
int n) {
118 fWeightByMass =
true;
119 fWeightByMassIsotopeZ = z;
120 fWeightByMassIsotopeN = n;
123 std::vector<GenericGeometricalSolidData>& GetGeometricalSolidDataList() {
124 return fGeomVolumeData;
137 struct SampleableObject {
139 SampleableObject() =
default;
140 SampleableObject(
const SampleableObject&) =
default;
155 G4RotationMatrix rot,
158 bool is_native_sampleable =
false,
159 bool on_surface =
false
163 ~SampleableObject() =
default;
170 [[nodiscard]]
bool IsInside(
const G4ThreeVector& vertex)
const;
189 [[nodiscard]]
bool Sample(
190 G4ThreeVector& vertex,
192 bool force_containment_check,
210 G4ThreeVector& vertex,
212 size_t max_intersections
245 void GetDirection(G4ThreeVector& dir, G4ThreeVector& pos)
const;
247 void RecalcMass(
int z,
int n);
251 G4RotationMatrix rotation;
252 G4ThreeVector translation;
258 bool surface_sample =
false;
259 bool native_sample =
false;
260 size_t max_num_intersections = 0;
266 struct SampleableObjectCollection {
268 SampleableObjectCollection() =
default;
269 ~SampleableObjectCollection() { data.clear(); }
281 [[nodiscard]]
bool IsInside(
const G4ThreeVector& vertex)
const;
284 [[nodiscard]]
size_t size()
const {
return data.size(); }
286 template<
typename... Args>
void emplace_back(Args&&... args);
287 [[nodiscard]]
bool empty()
const {
return data.empty(); }
289 void clear() { data.clear(); }
290 void insert(SampleableObjectCollection& other) {
291 for (
size_t i = 0; i < other.size(); ++i) this->emplace_back(other.at(i));
292 this->total_volume += other.total_volume;
293 this->total_mass += other.total_mass;
294 this->total_surface += other.total_surface;
297 void recalc_total(
bool weigh_by_mass,
int mass_isotope_z,
int mass_istotope_n);
299 std::vector<SampleableObject> data;
300 double total_volume = 0;
301 double total_mass = 0;
302 double total_surface = 0;
307 void InitializePhysicalVolumes();
308 void InitializeGeometricalVolumes(
bool use_excluded_volumes);
309 bool ActualGenerateVertex(G4ThreeVector& v);
311 std::vector<std::string> fPhysicalVolumeNameRegexes;
312 std::vector<std::string> fPhysicalVolumeCopyNrRegexes;
314 std::vector<GenericGeometricalSolidData> fGeomVolumeData;
315 std::vector<GenericGeometricalSolidData> fExcludedGeomVolumeData;
317 static G4Mutex fGeometryMutex;
326 static bool fVolumesInitialized;
329 VolumeType fFirstSamplingVolumeType = VolumeType::kUnset;
330 bool fWeightByMass =
false;
331 int fWeightByMassIsotopeZ = 0;
332 int fWeightByMassIsotopeN = 0;
334 bool fOnSurface =
false;
335 bool fForceContainmentCheck =
false;
336 bool fLastSolidExcluded =
false;
337 size_t fSurfaceSampleMaxIntersections = 0;
341 std::chrono::nanoseconds fVertexGenerationTime{};
343 std::vector<std::unique_ptr<G4GenericMessenger>> fMessengers;
344 void SetSamplingModeString(std::string mode);
345 void SetFirstSamplingVolumeTypeString(std::string type);
347 void AddGeometricalVolumeString(std::string solid);
348 void AddExcludedGeometricalVolumeString(std::string solid);
350 GenericGeometricalSolidData& SafeBack(
351 std::optional<GeometricalSolidType> solid_type = std::nullopt
358 void SetGeomVolumeCenter(
const G4ThreeVector& v) { this->SafeBack().volume_center = v; }
359 void SetGeomVolumeCenterX(
double x) { this->SafeBack().volume_center.setX(x); }
360 void SetGeomVolumeCenterY(
double y) { this->SafeBack().volume_center.setY(y); }
361 void SetGeomVolumeCenterZ(
double z) { this->SafeBack().volume_center.setZ(z); }
363 void SetGeomSphereInnerRadius(
double r) {
364 this->SafeBack(GeometricalSolidType::kSphere).sphere_inner_radius = r;
366 void SetGeomSphereOuterRadius(
double r) {
367 this->SafeBack(GeometricalSolidType::kSphere).sphere_outer_radius = r;
370 void SetGeomCylinderInnerRadius(
double r) {
371 this->SafeBack(GeometricalSolidType::kCylinder).cylinder_inner_radius = r;
373 void SetGeomCylinderOuterRadius(
double r) {
374 this->SafeBack(GeometricalSolidType::kCylinder).cylinder_outer_radius = r;
376 void SetGeomCylinderHeight(
double h) {
377 this->SafeBack(GeometricalSolidType::kCylinder).cylinder_height = h;
379 void SetGeomCylinderStartingAngle(
double a) {
380 this->SafeBack(GeometricalSolidType::kCylinder).cylinder_starting_angle = a;
382 void SetGeomCylinderSpanningAngle(
double a) {
383 this->SafeBack(GeometricalSolidType::kCylinder).cylinder_spanning_angle = a;
386 void SetGeomBoxXLength(
double x) {
387 this->SafeBack(GeometricalSolidType::kBox).box_x_length = x;
389 void SetGeomBoxYLength(
double y) {
390 this->SafeBack(GeometricalSolidType::kBox).box_y_length = y;
392 void SetGeomBoxZLength(
double z) {
393 this->SafeBack(GeometricalSolidType::kBox).box_z_length = z;
396 void DefineCommands();