Program Structure
Getting Started with Geant4
Defining the main() Program
The contents of main() will vary according to the needs of a given simulation application and therefore must be supplied by the user
First you must include all of the files you will be calling into the main() method
#include "G4RunManager.hh" #include "G4UImanager.hh"
#include "ExG4DetectorConstruction01.hh" #include "ExG4PhysicsList00.hh" #include "ExG4ActionInitialization01.hh"
Secondly construct the default run manager
G4RunManager* runManager = new G4RunManager;
Then you need to set the mandatory initialization classes
runManager->SetUserInitialization(new ExG4DetectorConstruction01); runManager->SetUserInitialization(new ExG4PhysicsList00); runManager->SetUserInitialization(new ExG4ActionInitialization01); //this code initializes G4DetectorConstruction, G4PhysicsList, G4ActionInitialization
Initialization of the G4 kernel
runManager->Initialize();
The next step for a simple main() method would be getting the pointer to the UI(User Interface) manager and set verbosities
G4UImanager* UI = G4UImanager::GetUIpointer(); UI->ApplyCommand("/run/verbose 1"); UI->ApplyCommand("/event/verbose 1"); UI->ApplyCommand("/tracking/verbose 1")
Starting the run process
int numberOfEvent = 3; //you can put however many events you would like this example is set at 3. runManager->BeamOn(numberOfEvent);
Then you need to terminate the job and close the main() method
delete runManager; return 0; }
Detector Geometry
A detector geometry in Geant4 is made of a number of volumes. The largest of these volumes is called the world volume.
World Volume
This world volume must contain all other volumes within the detector geometry. Other volumes that are created, must be included inside the world volume. The most simple and efficient shape to describe this world volume would be a box. Each volume is created by describing its shape and its physical characteristics, and then placing it inside a containing volume. When a volume is placed within another volume, we call the former volume the daughter volume and the latter the mother volume. The coordinate system used to specify where the daughter volume is placed, is the coordinate system of the mother volume.
- To describe a volume's shape, we use the concept of a solid. A solid is a geometrical object that has a shape and specific values for each of that shape's dimensions. A cube with a side of 10 centimeters and a cylinder of radius 30 cm and length 75 cm are examples of solids.
- To describe a volume's full properties, we use a logical volume. It includes the geometrical properties of the solid, and adds physical characteristics: the material of the volume; whether it contains any sensitive detector elements; the magnetic field; etc.
- To position the volume. To do this you create a physical volume, which places a copy of the logical volume inside a larger, containing, volume.
Our code to create the World volume:
G4double world_sizeXY = 1.2*env_sizeXY; G4double world_sizeZ = 1.2*env_sizeZ; G4Material* world_mat = nist->FindOrBuildMaterial("G4_AIR"); G4Box* solidWorld = new G4Box("World", //its name 0.5*world_sizeXY, 0.5*world_sizeXY, 0.5*world_sizeZ); //its size G4LogicalVolume* logicWorld = new G4LogicalVolume(solidWorld, //its solid world_mat, //its material "World"); //its name G4VPhysicalVolume* physWorld = new G4PVPlacement(0, //no rotation G4ThreeVector(), //at (0,0,0) logicWorld, //its logical volume "World", //its name 0, //its mother volume false, //no boolean operation 0, //copy number checkOverlaps); //overlaps checking
The Envelope (The world within the world)
The Envelope is a smaller volume that exists within the world volume. While the world volume is created to house all inner volumes, the envelope is where the experiment occurs. The envelope can be thought of as a box within a box, as it is essentially a smaller box within the world box. Within the envelope, other volumes (including materials) can be placed, and particles can be allowed to pass through. Although the volumes are described as a box, they can be other shapes as well, such as a cylinder. The code for creating boxes and cylinders can be found here.
The code for creating the envelope is near identical to the code for creating the world. The only difference is that the volume is given a different name, and the dimensions should be small enough to fit inside the world. Inside the envelope, other volumes and even materials with varying properties can be placed. This will be discussed in the next section.
Creating the Geometry inside the Envelope
Inside the envelope you can conduct many types of experiments. For our experiment we have placed two scoring volumes inside our envelope. Remember, each volume is created by describing its shape and its physical characteristics, and then placing it inside a containing volume; Please Refer to The Envelope (The world within the world) A sample code of someone creating the envelope: A shape In this section of code we are defining the shape in our chosen coordinate system, which is Cartesian. Follow the comments throughout the code for a better understanding:
G4Material* shape1_mat = nist->FindOrBuildMaterial("MATERIAL"); G4ThreeVector pos1 = G4ThreeVector(x, y ,z); // whatever shape you want G4double shape1_dya = cm, shape1_dyb = cm; G4double shape1_dxa = cm, shape1_dxb = cm; G4double shape1_dz = cm; G4Trd* solidShape1 = new G4Trd("Shape1", //its name 0.5*shape1_dxa, 0.5*shape1_dxb, 0.5*shape1_dya, 0.5*shape1_dyb, 0.5*shape1_dz); //its size G4LogicalVolume* logicShape1 = new G4LogicalVolume(solidShape1, //its solid shape1_mat, //its material "Shape1"); //its name new G4PVPlacement(0, //no rotation pos1, //at position logicShape1, //its logical volume "Shape1", //its name logicEnv, //its mother volume false, //no boolean operation 0, //copy number checkOverlaps); //overlaps checking
Next is the creation of the scintillators
How to Specify the Material in the Detector Geometry
So within the Envelope we constructed these volumes, volumes however can be filled with a material. Geant4 does a great job in allowing the user extreme customization. I say this because, I can literally fill up these volumes with whatever I would like as long as it is in the G4Material class. The G4Material class describes the macroscopic properties of matter:
- density,
- state,
- temperature,
- pressure,
- as well as macroscopic quantities like radiation length, mean free path, dE/dx, etc
The G4Material class is the one which is visible to the rest of the toolkit, and is used by the tracking, the geometry, and the physics. It contains all the information relative to the eventual elements and isotopes of which it is made, at the same time hiding the implementation details. We defined our volumes within our envelope and then went on to tell the program what material we would like in each volume. This is the section of code we used:
G4Material* shape1_mat = nist->FindOrBuildMaterial("G4_POLYETHYLENE"); G4Material* shape2_mat = nist->FindOrBuildMaterial("G4_POLYETHYLENE"); //"nist" is calling the data from the National Institute of Technology
This is a list of elements, compounds, space ISS materials, bio-chemical materials, HEP, and nuclear materials here
How to Specify Particles
In our experiment we declared our particle which is a muon because we are interested in the particles withing cosmic ray's The G4ParticleTable class is provided as a dictionary of particles. Various utility methods are provided, such as:
FindParticle(G4String name); // find the particle by name FindParticle(G4int PDGencoding) // find the particle by PDG encoding .
G4ParticleTable is defined as a singleton object, and the static method G4ParticleTable::GetParticleTable() provides its pointer. However in our code we declared a muon by
G4ParticleTable* particleTable = G4ParticleTable::GetParticleTable(); G4String particleName; G4ParticleDefinition* particle = particleTable->FindParticle(particleName="mu+"); fParticleGun->SetParticleDefinition(particle); //fParticleGun->SetParticleMomentumDirection(G4ThreeVector(xcosine,ycosine,zcosine)); // fParticleGun->SetParticleEnergy(e0);
Particles are registered automatically during construction. The user has no control over particle registration.
Dictionary of Particles
The G4ParticleTable class is provided as a dictionary of particles. Various utility methods are provided, such as:
FindParticle(G4String name); // find the particle by name
FindParticle(G4int PDGencoding) // find the particle by PDG encoding . G4ParticleTable is defined as a singleton object, and the static method G4ParticleTable::GetParticleTable() provides its pointer.
As for heavy ions (including hyper-nuclei), objects are created dynamically by requests from users and processes. The G4ParticleTable class provides methods to create ions, such as:
G4ParticleDefinition* GetIon( G4int atomicNumber, G4int atomicMass, G4double excitationEnergy);
How to Specify Physics processes
Physics processes describe how particles interact with materials. Geant4 provides seven major categories of processes:
- electromagnetic,
- hadronic,
- transportation,
- decay,
- optical,
- photolepton_hadron, and
- parameterisation.
All physics processes are derived from the G4VProcess base class. Its virtual methods
- AtRestDoIt,
- AlongStepDoIt, and
- PostStepDoIt
G4VProcess
G4VProcess is the base class for all physics processes. Each physics process must implement virtual methods of G4VProcess which describe the interaction (DoIt) and determine when an interaction should occur (GPIL). In order to accommodate various types of interactions G4VProcess provides three DoIt methods:
G4VParticleChange* AlongStepDoIt( const G4Track& track, const G4Step& stepData )
This method is invoked while G4SteppingManager is transporting a particle through one step. The corresponding AlongStepDoIt for each defined process is applied for every step regardless of which process produces the minimum step length. Each resulting change to the track information is recorded and accumulated in G4Step. After all processes have been invoked, changes due to AlongStepDoIt are applied to G4Track, including the particle relocation and the safety update. Note that after the invocation of AlongStepDoIt, the endpoint of the G4Track object is in a new volume if the step was limited by a geometric boundary. In order to obtain information about the old volume, G4Step must be accessed, since it contains information about both endpoints of a step.
G4VParticleChange* PostStepDoIt( const G4Track& track, const G4Step& stepData )
This method is invoked at the end point of a step, only if its process has produced the minimum step length, or if the process is forced to occur. G4Track will be updated after each invocation of PostStepDoIt, in contrast to the AlongStepDoIt method.
G4VParticleChange* AtRestDoIt( const G4Track& track, const G4Step& stepData )
This method is invoked only for stopped particles, and only if its process produced the minimum step length or the process is forced to occur.
For each of the above DoIt methods G4VProcess provides a corresponding pure virtual GPIL method:
G4double PostStepGetPhysicalInteractionLength( const G4Track& track, G4double previousStepSize, G4ForceCondition* condition )
This method generates the step length allowed by its process. It also provides a flag to force the interaction to occur regardless of its step length.
G4double AlongStepGetPhysicalInteractionLength( const G4Track& track, G4double previousStepSize, G4double currentMinimumStep, G4double& proposedSafety, G4GPILSelection* selection )
This method generates the step length allowed by its process.
G4double AtRestGetPhysicalInteractionLength( const G4Track& track, G4ForceCondition* condition )
This method generates the step length in time allowed by its process. It also provides a flag to force the interaction to occur regardless of its step length.
Other pure virtual methods in G4VProcess follow:
virtual G4bool IsApplicable(const G4ParticleDefinition&)
returns true if this process object is applicable to the particle type.
virtual void PreparePhysicsTable(const G4ParticleDefinition&) and
virtual void BuildPhysicsTable(const G4ParticleDefinition&)
is messaged by the process manager, whenever cross section tables should be prepared and rebuilt due to changing cut-off values. It is not mandatory if the process is not affected by cut-off values.
virtual void StartTracking() and
virtual void EndTracking()
are messaged by the tracking manager at the beginning and end of tracking the current track.
How to specify the type of Physics process
The user must create a class derived from G4VUserPhysicsList and implement the pure virtual method ConstructProcess(). For a Physics process you must register the G4Transportation class with all particle classes. The AddTransportation() method is listed and provided in G4VUserPhysicsList class.
void MyPhysicsList::ConstructProcess() { // Define transportation process AddTransportation(); }
How to Generate a Primary Action
G4userPrimaryGeneratorAction is one of the mandatory classes available for deriving your own concrete class. In your concrete class, you have to specify how a primary event should be generated. Actual generation of primary particles will be done by concrete classes of G4VPrimaryGenerator.
void S1PrimaryGeneratorAction::GeneratePrimaries(G4Event* anEvent) {
Selection of the Generator
In the constructor of your G4VUserPrimaryGeneratorAction, you should instantiate the primary generator(s). If necessary, you need to set some initial conditions for the generator(s). This is an example of a constructor
S1PrimaryGeneratorAction::S1PrimaryGeneratorAction()
- G4VUserPrimaryGeneratorAction(),
//inside this constructor you should have some code calling your generator(s)
G4Primary Generator
G4ParticleGun is a generator provided by Geant4. We called This class generates primary particle(s) with a given momentum and position. It does not provide any sort of randomizing. The constructor of G4ParticleGun takes an integer which causes the generation of one or more primaries of exactly same kinematics. It is a rather frequent user requirement to generate a primary with randomized energy, momentum, and/or position. Such randomization can be achieved by invoking various set methods provided by G4ParticleGun. Geant4 provides various random number generation methods with various distributions (see Section 3.2). Within your Primary Generator Action you must establish your conditions of your experiment {Example}
- establish a random position on both top and bottom of your geometry within your envelope
xtop = (G4UniformRand()*(Variables->getGeometryX()*0.5)); ytop = (G4UniformRand()*(Variables->getGeometryY()*0.5)); xbottom = (G4UniformRand()*(Variables->getGeometrytX()*0.5)); ybottom = = (G4UniformRand()*(Variables->getGeometryY()*0.5));
- establish how far below the bottom geometry the particles should start
G4double bottomOfBottomGeo = (Variables->getGeoZ()*-0.5)+Variables->getBottomGeoPos(); zinitial = (bottomOfBottomGeo - 1.0);
- establish the components of the vector to fire along to hit both random points
baseX = (xtop-xbottom); baseY = (ytop-ybottom); heightZ = (Variables->getTopGeoPos() - Variables->getBottomGeoPos());
G4ParticleGun Generator
G4ParticleGun is a generator provided by Geant4. This class generates primary particle(s) with a given momentum and position. It does not provide any sort of randomizing. The constructor of G4ParticleGun takes an integer which causes the generation of one or more primaries of exactly same kinematics. It is a rather frequent user requirement to generate a primary with randomized energy, momentum, and/or position. G4ParticleGun is normally found in one of your constructors within your PrimaryGeneratorAction.
fParticleGun = new G4ParticleGun(n_particle);
Next you must decribe the default Particle Kinematics:
G4ParticleTable* particleTable = G4ParticleTable::GetParticleTable(); G4String particleName = "nameofparticlehere"; G4ParticleDefinition* particle = particleTable->FindParticle(particleName); fParticleGun->SetParticleDefinition(particle);