0% found this document useful (0 votes)
29 views111 pages

Geant 4

Uploaded by

gogoihritik
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
29 views111 pages

Geant 4

Uploaded by

gogoihritik
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 111

Detector Simulation and Event Reconstruction

• Event Generation (GEN): e.g., GINIE, Pythia8, HYJING – Common in most of the neutrino,
pp, heavy ion experiment
– Will cover separately
• Detector simulation -matter particle interaction (SIM) : GEANT – common for almost all HEP
expt
– Need to know how GEANT4 does this
• Digitisation (DIGI): Specific to a particular experiment, based on electronics…..
– This is suppose to be the same as it is (will be) in data
• Reconstruction of particle (RECO): Try to get back the generation/particle level information
– Charged particle, e.g., muon, pion….
• Track finder, common principle, but detector specific
• Track fit, almost all HEP uses Kalman Filter algorithm
– Neutral hadron, basic clustering algorithm (common), but optimization, noise rejection, ghost
removal…., which are specific to a detector .

Use these reconstructed objects to find Higgs boson, QGP, neutrino mixing
parameters……
1
Use of Detector Simulation and Geant4
Detector Simulation is extensively used in nuclear and high energy physics
experiments:
• To design the detector to satisfy some of the goals of a given experiment.
• Helps in developing reconstruction algorithms and trigger logics.
• Is used to generate large amounts of signal and background events for use in
physics analysis once data comes to study signal/background separation.
• To understand/demonstrate analysis procedures and methods based on data to
derive calibrations, efficiencies, resolutions for high level physics objects.
• Is used to derive directly calibrations, efficiencies, resolutions for high level
objects in cases where data are biased or not available.
• Geant4 is a toolkit and several applications in High Energy, Nuclear, Space
physics as well as Medical Application can build their simulation code using this
– Three (ATLAS, CMS and LHC-b) out of Four LHC experiments use
exclusively Geant4 inside their simulation code
– It is used in many nuclear physics application including neutron spallation
– ESA has developed many space applications based on Geant4
– Largest number of applications of Geant4 is in the area of medical physics 2
Geant4-toolkit
• GEneration ANd Tracking (early 70’s) with Fortran code - Geant3
• GEometry ANd Tracking (now)
– Dec ‘94 : Project start
– Apr ‘97 : First alpha release
– July ‘98 : First beta release
– Dec ‘98 : First Geamt4 public release –version 1.0
– …………………
– Dec 4th ‘15 : Geant4 version 10.2 release (patch-03 released 29th June 2016)
– Dec 9th ‘16 : Geant4 version 10.3 (patch-01, released 24th February 2017)
• The official Geant4 web pages http://www.cern.ch/geant4
Many more details are in “Geant4 Beginner Course” in Jan 2014 @Queen's
University - Belfast (Northern Ireland)
https://agenda.infn.it/conferenceOtherViews.py?view=standard&confId=7186
https://hep.kisti.re.kr/indico/conferenceDisplay.py?ovw=True&confId=214
More tutorials : http://geant4.cern.ch/support/training.shtml

Will not talk anything about MultiThread, Scroring, Biasing,….. 3


Geant4 Toolkit and User Application
 Geant4 is a toolkit (= a collection of tools)
 i.e. you cannot “run” it out of the box

 You must write an application, which uses Geant4 tools

 Consequences:
 There are no such concepts as “Geant4 defaults”

 You must provide the necessary information to configure your


simulation
 You must deliberately choose which Geant4 tools to use

 Guidance: many examples are provided


 basic/advanced/extended Examples: overview of Geant4 tools

 Advanced/extendent Examples: Geant4 tools in real-life applications


What Geant simulation Tool Kit Provides ?
– Modular Geometry
– Particle table with particle properties
– Physics processes with cross sections, final state products, kinematics of
particles produced in interactions,….
– Stepping through detector material and finding out what is to be done in
which step
– Provision of I/O capability : allows the User to access the transportation
process and retrieve the results (USER ACTIONS)
• at the beginning and end of the transport
• at the end of each step in transportation
• if a particle reaches a sensitive detector ……

What is special about GEANT ?


– Particle transport is automatically taken care of – good interface between
geometry and tracking
– Covers physics over a wide energy region – applicable to space science,
high energy and nuclear physics, medical imaging
5
Users responsibility
 What you MUST do:
 Describe your experimental set-up, detector geometry with material definition
 Provide the primary particles input to your simulation, Interface event
generators to the simulation tool kit
 Decide which particles and physics models you want to use out of those
available in Geant4 and the precision of your simulation (cuts to produce and
track secondary particles)
G4VUserDetectorConstruction -- describe the experimental set-up
G4VUserPhysicsList -- select the physics you want to activate
G4VUserPrimaryGeneratorAction -- generate primary events
 You may also want
 To interact with Geant4 kernel to control your simulation
 Identify components of the detector which will generate signals and attributes
requires to compute these
 To visualise your simulation configuration or results
 Convert energy deposits to detector signals
 To produce histograms, tuples etc. to be further analysed
An example of (sequential) main()
{
// Construct the default run manager
G4RunManager* runManager = new G4RunManager;
// Set mandatory user initialization classes
MyDetectorConstruction* detector = new MyDetectorConstruction;
runManager->SetUserInitialization(detector);
MyPhysicsList* physicsList = new MyPhysicsList;
runManager->SetUserInitialization(myPhysicsList);

// Set mandatory user action classes


runManager->SetUserAction(new MyPrimaryGeneratorAction);

// Set optional user action classes


MyEventAction* eventAction = new MyEventAction();
runManager->SetUserAction(eventAction);
MyRunAction* runAction = new MyRunAction();
runManager->SetUserAction(runAction);

delete runManager; // Don’t forget to delete the G4RunManager at the end
}
Initialisation
m a in Run m anage r user d etecto r u s e r p h y sic s
c o n s t r u c t io n l is t

1 : in i t i a l iz e Carry out the


2 : co nst ruc t
construction of
detector geometry
3 : m a t e ria l c o n s t r u c t io n
including all material
properties
4 : g e o m e t r y c o n s t r u c t io n
5 : w o r ld v o l u m e

6 : c o n st ru c t

7 : p h y sic s p r o c e s s c o n s t r u c t io
• Complete tables of particles with their static properties
• Initialise physics processes, prepare tables of cross sections,
8 : set cu ts
ranges etc in view of approximations and cuts
• Take the input and output attributes and appropriate action
Beam On
• Geometry has to be closed before event loop starts
m a in Ru n M a n a g e r Ge o m e t ry Ev e n t Eve nt
m a n ag e r g e n e ra t o r M an a g e r
1 : Be am On
2 : c lo s e
Generate primary
events according to
3 : g e n e ra t e o n e e v e n t distributions relevant
to your experiment

4 : process o ne eve nt

5 : open
Geant4 concept

Given concrete (dummy)


Geant4 kernel implementation. User MAY
G4RunManager
give an alternative
implementation

VGeometry VPhysics VPrimary RunAction EvtAction StepAction

Only virtual interface


provided  users
MyGeom MyPhysics MyPrimary MUST implement their MyStep
concrete
implementation
Supported platform
• Linux systems : Scientific Linux CERN 6 with gcc 4.7.X, 64 bit
– Geant4 has also been successfully compiled on other Linux distributions, including
Debian, Ubuntu and openSUSE (not officially supported)
• MacOSX systems : Mac OS X 10.8 (Lion with clang 3.3), 64bit
– Geant4 has also been successfully compiled on Mac OS X 10.7 (Lion) with clang 3.1
(Apple), (not officially supported)
• Windows systems : Windows 7 with Visual Studio 11 (VS2010).

Check current Geant4 supported platforms in http://geant4.web.cern.ch/geant4/

11
Required software
• The Geant4 toolkit source code (10.00)
• C++ compiler
– It is usually installed on your Linux. If not, you need to install it (not shown here)
• CMake 2.6.4 or higher
– for clang, Cmake 2.8.2 or higher is required
• CLHEP library
– an internal version is now supplied with the geant4 source (since 9.5 version)
• The Geant4 data files
– an automatic procedure can retrieve them (with CMake)

12
cmake Geant4 installation
 cmake version greater than 2.8.3

 Locate the source folder Ex: /home/Username/geant4.10.00

 Create the build folder Ex: /home/Username/geant4.10.00-build

 Create the install folder Ex: /home/Username/geant4.10.00-install

 To configure, change into the build directory and run CMake:

cmake DCMAKE_INSTALL_PREFIX=/home/Username/geant4.10.00-
install/ /home/Username/geant4.10.00

 Define and/or activate the additional features/package you require using the
same cmake interface

 make -jN

 make install
Building an application with cmake
• First step: create a build directory for the specific application (suggestion: build that
alongside the application source directory):

• Change to this build directory and run CMake to generate the Makefiles needed to
build the B1 application. Pass CMake two arguments:

• CMake will now run to configure the build and generate Makefiles.:

14
Building an application with cmake
• The following files have been generated:

• Once the Makefile is available we can do: make –j8


• The following output should be displayed:

• Execute with command : ./exampleB1


15
Units in Geant4
• All unit needs to be specified, no c=ħ=1, but define those variables inside the
code, that you do not need to remember this
• By default, units are
• Length : mm (not cm)
• Time : ns
• Energy : MeV (not GeV)
• Angle : Radian
• Temperature : Kelvin
• All are defined inside
$CLHEP_BASE_DIR/Units/CLHEP/Units/SystemOfUnits.h
• Do not confused with SI units
$G4INSTALL/source/global/management/include/G4SIunits.hh, which will be
used in track reconstruction algorithm

Though internally, a convention of unit system is used, the recommendation s not


to remember them and use the units explicitly :
double length = 5.8*cm;
double angle = 30.0*degree;
cout <<length/cm; G4BestUnit(egap, “Energy”); G4BestUnit(elen, “Length”);
$CLHEP_BASE_DIR/Units/CLHEP/Units/SystemOfUnits.h
// This file has been provided to CLHEP by Geant4 (simulation toolkit for HEP).
// The basic units are :
// millimetre (millimetre)
// nanosecond (nanosecond)
// Mega electron Volt (MeV)
// positron charge (eplus)
// degree Kelvin (kelvin)
// the amount of substance (mole)
// luminous intensity (candela)
// radian (radian) • Whereas in G4SIunits.hh
// steradian (steradian) // meter
// second
// kilogram
// ampere
// degree kelvin
// the amount of substance (mole)
// luminous intensity (candela)
// radian
// steradian
$CLHEP_BASE_DIR/Units/CLHEP/Units/SystemOfUnits.h
static const double millimetre = 1.;
static const double millimeter2 = millimeter*millimeter;
static const double millimeter3 = millimeter*millimeter*millimeter;

static const double centimeter = 10.*millimetre;


static const double centimeter2 = centimeter*centimeter;
static const double centimeter3 = centimeter*centimeter*centimeter;

static const double meter = 1000.*millimetre;


static const double meter2 = meter*meter;
static const double meter3 = meter*meter*meter;

static const double kilometer = 1000.*meter;


static const double kilometer2 = kilometer*kilometer;
static const double kilometer3 = kilometer*kilometer*kilometer;

static const double parsec = 3.0856775807e+16*meter;


………………………..
static const double eplus = 1. ;// positron charge
static const double e_SI = 1.602176487e-19;// positron charge in coulomb
static const double coulomb = eplus/e_SI;// coulomb = 6.24150 e+18 * eplus
Description of detector
• Derive your own concrete class from G4VUserDetectorConstruction abstract base class.
• Implement Construct() and ConstructSDandField() methods
– 1) Construct all necessary materials
– 2) Define shapes/solids
– 3) Define logical volumes
– 4) Place volumes of your detector geometry
– 5) Associate (magnetic) field to geometry (optional)
– 6) Instantiate sensitive detectors / scorers and set them to corresponding logical volumes
(optional)
– 7) Define visualization attributes for the detector elements (optional)
– 8) Define regions (optional)
• Set your construction class to G4RunManager or G4MTRunManager

19
Defining a Material
• Material has a Name, effective Atomic Number and Weight, Density, Radiation (X 0) and
absorption (λ)
– Can be defined by specifying the attributes
– If X0, λ are not known but the chemical composition is known, one can furnish these
information and GEANT can compute the required attributes
• Can in addition define the state, isotopic properties, ….
– Define pseudo-elements
• G4Material (name, Z, A, Density, State, Temperature, Pressure)
– Define a mixture of elements in atomic or weighted proportion
• G4Element (Name, Symbol, A,Z)
• G4Material (name, Z, A, Density, State, Temperature, Pressure)
– AddElement(Element, nAtom)
– AddElement(Element, fraction)
– Defining a mixture of materials by weighted proportion
• AddMaterial(Matrial, fraction)

Air in the Tracking (thin gaps) may be different in tracking properties from
Air between coil and yoke (large gap)
Defining a Material
G4double A, Z;
G4Element* eln = new G4Element(“Nitrogen”, “N”, Z=7., A=14.01*g/mole);
G4Element* elo = new G4Element(“Oxygen”, “O”, Z=8., A=16.00*g/mole);
G4Material* air = new G4Material(“Air”, 1.205E03*g/cm3, 2);
air →AddElement(eln, 0.7);
air →AddElement(elo, 0.3);
Defines the material Air consisting of two constituent elements Nitrogen and
Oxygen in a given weight proportion. The elements Nitrogen and Oxygen are
defined with their appropriate A, Z values.
National Institute of Standards (NIST) database for materials is imported inside
Geant4, http://physics.nist.gov/PhysRefData
• G4NistManager* mat = G4NistManager :: Instance();
• G4Element* S = mat  FindOrBuildElement (“S”);
• G4Material * Butane = mat FindOrBuildMaterial (“G4-Butane”);
Some UI commands …
/material/nist/printElement  print defined elements
/material/nist/listMaterials print defined materials
RPC Gas mixture
// define Elements

G4Element* S = mat->FindOrBuildElement("S");
G4Element* F = mat->FindOrBuildElement("F");
SF6 = new G4Material("SF6",density = 0.006164*g/cm3, ncomponents=2);
SF6->AddElement(S, natoms=1);
SF6->AddElement(F, natoms=6);

G4Material* Butane = mat->FindOrBuildMaterial("G4_BUTANE");


G4Material* Freon = mat->FindOrBuildMaterial("G4_FREON-13B1");

G4Material* ActiveMaterial = new G4Material("rpcgas",density= 0.00418*g/cm3,


ncomponents=3);
ActiveMaterial->AddMaterial(Freon, fractionmass=95.15*perCent);
ActiveMaterial->AddMaterial(Butane, fractionmass=4.51*perCent);
ActiveMaterial->AddMaterial(SF6, fractionmass=0.34*perCent);

22
Isotopes
• If you define an element, it is treated by default as if it has the natural isotope abundance
– even if the g/mole value you enter is quite different from the natural abundance
– Hadronic code knows only how to deal with specific nuclides, not elements
• Example : make nuclear fuel UF6

• First define Uranium isotopes


– G4Isotope* isoU235 = new G4Isotope("U235", z=92, a=235, 235.044*g/mole);
– G4Isotope* isoU238 = new G4Isotope("U238", z=92, a=238, 238.051*g/mole);
• Then define the corresponding enriched uranium element from the two isotopes
– G4Element* el_enrichedU = new G4Element("enriched U", "U", ncomp=2);
– el_enrichedU->AddIsotope(isoU235, abundance=5.*perCent);
– el_enrichedU->AddIsotope(isoU238, abundance=95.*perCent);
• Make some fluorine too
– G4Element* elF = new G4Element(”fluorine", “F", 9.,18.998*g/mole);
• Finally add this element to a material
– G4Material* fuel = new G4Material(”nuclear fuel”, density=5.09*g/cm3, ncomp=2,
kStateSolid, 640*kelvin, 1.5e7*pascal);
• fuel->AddElement(el_enrichedU, 1);
• fuel->AddElement(elF, 6); 23
Describe the detector
• A detector geometry is made of a number of
volumes
• The largest volume is called World volume
– It must contain all other volumes
• Derive your own concrete class from
– G4VUserDetectorConstruction abstract base
class.
• Implementing the method Construct():

• Modularize it according to each detector component:


– Define shapes/solids required to describe the geometry
– Construct all necessary materials
– Construct and place volumes of your detector geometry
– Define sensitive detectors and identify detector volumes which to associate them
– Associate magnetic field to detector regions
– Define visualization attributes for the detector elements 24
Components of detector geometry
• Three conceptual layers
– G4VSolid -- shape, size
– G4LogicalVolume -- daughter physical volumes, material, sensitivity, magnetic field, etc.
– G4VPhysicalVolume -- position, rotation

25
Defining a volume
• There are several ways to defining solids
– Constructed Solids Geometry (CSG) Solids : G4Box,
G4Trd, G4Trap, G4Tubs, G4Cones, G4Sphere,
G4Polycon, ……
– Boundary Represented (BREPS) Solids : defined via the
description of their boundaries, much slower navigation,
G4BtrpSolidPcone, G4BREPSolidPolyhydra
– Boolean : Solids made out of adding, subtracting,
intersecting several solids : G4RotateSolid
– STEP : To import from the CAD system

Though internally, a convention of unit system is used, the recommendation is not


to remember them and use the units explicitly :
double length = 5.8*cm;
double angle = 30.0*degree;
cout <<length/cm; G4BestUnit(egap, “Energy”); G4BestUnit(elen, “Length”);
Constructed Solid Geometry (CSG) Solids
Rectangular parallelepiped
G4Box(const G4String& pName,
G4double pX, //half length in X, 30
G4double pY, // half length in Y, 40
G4double pZ) // half length in Z, 60

Cylindrical Section or Tube:

G4Tubs(const G4String& pName,


G4double pRMin, //Inner radius, 10
G4double pRMax, // Outer radius, 15
G4double pDz, // Half length in Z, 20
G4double pSPhi, // Starting Phi angle in radian, 1.75π
G4double pDPhi); // Angle of segment in radians, 0.25π
Constructed Solid Geometry (CSG) Solids

G4Cons G4CutTubs G4Para G4Trd

G4Sphere G4Orb G4Torus G4Paraboloid G4Polyhedra

Consult to Section 4.1.2 of Geant4 Application Developers Guide for all available shapes. 28
Constructed Solid Geometry (CSG) Solids

G4GenericPolyCone
(increasing Z)
G4Ellipsoid G4PolyCons G4Tetrahedra G4Hyperbolic
G4EllipticalTube (decreasing Z)

G4Ellipticalcone G4TwistedTube G4TwistedBox G4TwistedTrap G4ExtrudedSolid29


Solid made by Boolean operations
• Solids can be combined using Boolean operations:
– G4UnionSolid, G4SubtractionSolid, G4IntersectionSolid
– Requires: 2 solids, 1 Boolean operation, and an (optional) transformation for the 2nd
solid
– 2nd solid is positioned relative to the coordinate system of the 1st solid
– Result of Boolean operation becomes a solid. Thus the third solid can be combined to
the resulting solid of first operation.
• Solids to be combined can be either CSG or other Boolean solids.
• Note: tracking cost for the navigation in a complex Boolean solid is proportional to the
number of constituent CSG solids

30
Solids made by Boolean operations
G4Box* box = new G4Box("Box",20*mm,30*mm,40*mm);
G4Tubs* cyl = new G4Tubs("Cylinder",0,50*mm,50*mm,0,twopi); // r: 0 mm -> 50 mm
// z: -50 mm -> 50 mm
// phi: 0 -> 2 pi
G4UnionSolid* union = new G4UnionSolid("Box+Cylinder", box, cyl);
G4IntersectionSolid* intersection = new G4IntersectionSolid("Box*Cylinder", box, cyl);
G4SubtractionSolid* subtraction = new G4SubtractionSolid("Box-Cylinder", box, cyl);

G4RotationMatrix* yRot = new G4RotationMatrix; // Rotates X and Z axes only


yRot->rotateY(M_PI/4.*rad); // Rotates 45 degrees
G4ThreeVector zTrans(0, 0, 50);
G4UnionSolid* unionMoved = new G4UnionSolid("Box+CylinderMoved", box, cyl, yRot,
zTrans);

// Now we build the same solid using the alternative method


G4RotationMatrix invRot = *(yRot->invert());
G4Transform3D transform(invRot, zTrans);
G4UnionSolid* unionMoved =
new G4UnionSolid("Box+CylinderMoved", box, cyl, transform);
32
G4FieldManager*, G4SensitiveDetector* ,G4UserLimit*
• A logical volume is made up with a Solid and a Material (pointer must be non null), contains
all information of volume except position and orientation
– Shapes and dimension (G4VSolid), Material, sensitivity, visualization attributes, Position
of daughter volumes, Magnetic field, User limits, Region
• Same Solid and Material can be used to defined different logical volume, to represent
different medium in different part of the detector
• Magnetic field can be associated with a logical volume, but in general global magnetic field is
used
• G4SensitiveDetector can be associated later on (a practice)
• G4UserLimit : Managing tracking steps, also associated separately 33
Creates a PhysicalVolume by positioning copy copyNumber of LogicalVolume daughter inside
the mother volume mother with a translation vector (G4ThreeVector) and a rotation matrix
(G4RotationMatrix* pRotation). For the top level volume (defining the World reference
system) the reference Mother Volume is a Null 34
Placement & PhysicalVolume
G4PhysicalVolume* volume = new G4PVPlacement(
G4RotationMatrix* rot, //rotation of mother frame
G4ThreeVector(xpos*cm, ypos*cm, zpos*cm), //center of daughter wrt to mother
G4LogicalVolume* daughter, // logical volume of daughter
Const G4String* NAME, // its name
G4LogicvalVolume* pMotherLog, // logical volume of its mother
G4bool pMany=false, // no boolean operation,Not used,
G4Int copyNumber, // copy/replica number
G4Bool pSurfchk=false); // optional overlap check, require lots of CPU time

One useful way of defining daughter volume is by dividing an existing mother volume into n
equal parts along a chosen axis (Cartesian, Cylindrical, Polar)

If one needs to define the rotation matrix by specifying θi, φi of the three axes of daughter in
mothers frame,
G4ThreeVector nAxis( sin(thetaN*deg)*cos(phiN*deg), sin(thetaN*deg)*sin(phiN*deg),
(cos(thetaN*deg));
G4RotationMatrix* rot = new GeRotationMatrix();
rot->rotateAxes(xAxis, yAxis, Zaxis); // rot->rotateZ(45*degree)
rot->invert();
Deleting a logical volume does not delete its daughter volumes
Physical Volumes
• Placement volume : it is one positioned volume
– One physical volume object represents one “real” volume.
• Repeated volume : a volume placed many times
– One physical volume object represents any number of “real”
volumes.
– reduces use of memory.
– Parameterised
• repetition w.r.t. copy number
– Replica and Division
• simple repetition along one axis
• A mother volume can contain either
– many placement volumes
– or, one repeated volume

36
Geometrical Hierarchy
• Mother and daughter volumes
– A volume is placed in its mother volume
– When a daughter is positioned inside a mother, the extent inside the mother occupied
by the daughter gets filled up with the material/medium of the daughter
• Position and rotation of the daughter volume is described with respect to the local
coordinate system of the mother volume
• The origin of the mother's local coordinate system is at the center of the mother
volume
• Daughter volumes cannot protrude from the mother volume
• Daughter volumes cannot overlap
• The logical volume of mother knows the daughter volumes it contains
– It is uniquely defined to be their mother volume

37
Geometrical Hierarchy
• One logical volume can be placed more than once. One or
more volumes can be placed in a mother volume
• Note that the mother-daughter relationship is an
information of G4LogicalVolume
– If the mother volume is placed more than once, all
daughters by definition appear in each placed physical
volume
• The world volume must be a unique physical volume
which fully contains with some margin all the other
volumes (root volume of the hierarchy)
– The world volume defines the global coordinate system.
The origin of the global coordinate system is at the
center of the world volume
– Position of a track is given with respect to the global
coordinate system

38
Physical Volumes
• G4PVPlacement 1 Placement = One Placement Volume
– A volume instance positioned once in its mother volume
• G4PVParameterised 1 Parameterized = Many Repeated Volumes
– Parameterized by the copy number
• Shape, size, material, sensitivity, vis attributes, position and rotation can be
parameterized by the copy number.
• You have to implement a concrete class of G4VPVParameterisation.
– Reduction of memory consumption
– Currently: parameterization can be used only for volumes that either
• a) have no further daughters, or
• b) are identical in size & shape (so that grand-daughters are safely fit inside).
• G4PVReplica 1 Replica = Many Repeated Volumes
– Daughters of same shape are aligned along one axis
– Daughters fill the mother completely without gap in between.
• G4PVDivision 1 Division = Many Repeated Volumes
– Daughters of same shape are aligned along one axis and fill the mother.
– There can be gaps between mother wall and outmost daughters.
– No gap in between daughters.
39
G4VParameterised
G4PVParameterised(const G4String& pName,

G4LogicalVolume* pLogical,

G4LogicalVolume* pMother,

const EAxis pAxis,

const G4int nReplicas,

G4VPVParameterisation* pParam

G4bool pSurfChk=false);

• Replicates the volume nReplicas times using the parameterization pParam, within the
mother volume pMother

• pAxis is a “suggestion” to the navigator along which Cartesian axis replication of


parameterized volumes dominates.

– kXAxis, kYAxis, kZAxis : one-dimensional optimization

– kUndefined : three-dimensional optimization 40


G4VParameterised Physical Volumes
• User should implement a class derived from G4VPVParameterisation abstract base
class and define following as a function of copy number
– where it is positioned (transformation, rotation)
• Optional:
– the size of the solid (dimensions)
– the type of the solid, material, sensitivity, vis attributes
• All daughters must be fully contained in the mother.
• Daughters should not overlap to each other.
• Limitations:
– Applies to simple CSG solids only
– Granddaughter volumes allowed only for special cases
– Consider parameterised volumes as “leaf” volumes
• Typical use-cases
– Complex detectors
• with large repetition of volumes, regular or irregular
– Medical applications
• the material in animal tissue is measured as cubes with varying material
41
G4VParameterisation : an example
G4VSolid* solidChamber = new G4Box("chamber", 100*cm, 100*cm, 10*cm);
G4LogicalVolume* logicChamber =new G4LogicalVolume (solidChamber, ChamberMater,
"Chamber", 0, 0, 0);
G4VPVParameterisation* chamberParam = new ChamberParameterisation();
G4VPhysicalVolume* physChamber = new G4PVParameterised("Chamber", logicChamber,
logicMother, kZAxis, NbOfChambers, chamberParam);

class ChamberParameterisation : public G4VPVParameterisation {


public:
ChamberParameterisation();
virtual ~ChamberParameterisation();
virtual void ComputeTransformation // position, rotation
(const G4int copyNo, G4VPhysicalVolume* physVol) const;
virtual void ComputeDimensions // size
(G4Box& trackerLayer, const G4int copyNo,
const G4VPhysicalVolume* physVol) const;
virtual G4VSolid* ComputeSolid // shape
(const G4int copyNo, G4VPhysicalVolume* physVol);
virtual G4Material* ComputeMaterial // material, sensitivity, visAtt
(const G4int copyNo, G4VPhysicalVolume* physVol,
const G4VTouchable *parentTouch=0); // G4VTouchable should not be used for ordinary
parameterization
}; 42
G4VParameterisation : an example
G4VSolid* ChamberParameterisation::ComputeSolid
(const G4int copyNo, G4VPhysicalVolume* physVol)
{
G4VSolid* solid;
if(copyNo == …) { solid = myBox;
} else if { (copyNo == …) {solid = myTubs;

}
return solid;
}
G4Material* ChamberParameterisation:: ComputeMaterial // material, sensitivity, visAtt
(const G4int copyNo, G4VPhysicalVolume* physVol,
const G4VTouchable *parentTouch=0);
{
G4Material* mat;
if(copyNo == …) {
mat = material1;
physVol->GetLogicalVolume()->SetVisAttributes( att1 );
}

return mat;
} 43
G4VParameterisation : an example
void ChamberParameterisation::ComputeTransformation
(const G4int copyNo, G4VPhysicalVolume* physVol) const
{
G4double Xposition = … // w.r.t. copyNo
G4ThreeVector origin(Xposition,Yposition,Zposition);
physVol->SetTranslation(origin);
physVol->SetRotation(0);
}
void ChamberParameterisation::ComputeDimensions
(G4Box& trackerChamber, const G4int copyNo,
const G4VPhysicalVolume* physVol) const
{
G4double XhalfLength = … // w.r.t. copyNo
trackerChamber.SetXHalfLength(XhalfLength);
trackerChamber.SetYHalfLength(YhalfLength);
trackerChamber.SetZHalfLength(ZHalfLength);
}

44
Replicated Volume
• The mother volume is completely filled with replicas, all of which
are the same size (width) and shape.
• Replication may occur along:
– Cartesian axes (X, Y, Z) – slices are considered perpendicular
to the axis of replication
• Coordinate system at the center of each replica
– Radial axis (Rho) – cons/tubs sections centered on the origin
and un-rotated
• Coordinate system same as the mother
– Phi axis (Phi) – phi sections or wedges, of cons/tubs form
• Coordinate system rotated such as that the X axis bisects the
angle made by each wedge

45
G4PVReplica
G4PVReplica(const G4String &pName,
G4LogicalVolume *pLogical,
G4LogicalVolume *pMother,
const EAxis pAxis,
const G4int nReplicas,
const G4double width,
const G4double offset=0.);
• offset may be used only for tube/cone segment

• Features and restrictions:

– Replicas can be placed inside other replicas

– Normal placement volumes can be placed inside replicas, assuming no


intersection/overlaps with the mother volume or with other replicas

– No volume can be placed inside a radial replication

– Parameterised volumes cannot be placed inside a replica 46


Replica – axis, width, offset
• Cartesian axes - kXaxis, kYaxis, kZaxis

– Center of n-th daughter is given as

• width*(nReplicas-1)*0.5+n*width

– Offset shall not be used

• Radial axis – kRaxis

– Center of n-th daughter is given az

• width*(n+0.5)+offset

– Offset must be the inner radius of the mother

• Phi axis – kPhi

– Center of n-th daughter is given as

• width*(n+0.5)+offset

– Offset must be the starting angle of the mother


47
G4PVReplica : an example
G4double tube_dPhi = 2.* M_PI * rad;
G4VSolid* tube = new G4Tubs("tube",20*cm,50*cm,30*cm,0.,tube_dPhi);
G4LogicalVolume * tube_log = new G4LogicalVolume(tube, Air, "tubeL", 0,
0, 0);
G4VPhysicalVolume* tube_phys = new G4PVPlacement(0,G4ThreeVector(-
200.*cm,0.,0.), "tubeP", tube_log, world_phys, false, 0);
G4double divided_tube_dPhi = tube_dPhi/6.;
G4VSolid* div_tube = new G4Tubs("div_tube", 20*cm, 50*cm, 30*cm,
-divided_tube_dPhi/2., divided_tube_dPhi);
G4LogicalVolume* div_tube_log = new
G4LogicalVolume(div_tube,Pb,"div_tubeL",0,0,0);
G4VPhysicalVolume* div_tube_phys = new G4PVReplica("div_tube_phys",
div_tube_log, tube_log, kPhi, 6, divided_tube_dPhi);

48
Division : An example
Construct Geometry of a
cylindrical drift chamber with 8
sector each having 5 cells
Y
X

Z
Coding
Debugging of geometry overlap
• Built-in run-time commands to activate verification tests for the user geometry are defined
• to start verification of geometry for overlapping regions based on a standard grid setup,
limited to the first depth level
– geometry/test/run or geometry/test/grid_test
• applies the grid test to all depth levels (may require lots of CPU time!)
– geometry/test/recursive_test
• shoots lines according to a cylindrical pattern
– geometry/test/cylinder_test
• to shoot a line along a specified direction and position
– geometry/test/line_test
• to specify position for the line_test
– geometry/test/position
• to specify direction for the line_test
– geometry/test/direction

But, better to check once inside the G4VPlacement function


51
Detecting Overlaps and visualisation
Best option to visualise but for complicated and many layers; Use:
/geometry/test/grid-test true/false(only one depth)
/geometry/test/cylinder-test true/false
visx = G4VisAttributes(true, G4Color(1, 1, 1))
visxSetVisibility(G4bool)
visxSetColor(G4Color)
Logic Name SetVisAttributes(visx)
G4VisAttributes SetLineStyle(G4VisAttributes::unbroken, dashed, dotted)
SetLinewidth(G4Double )
SetForceWireframe(G4Bool) //only edges
SetForceSolid(G4Bool) //Force to visualised with surfaces
SetForceHuxEdgeVisible(G4Bool) //Force to look curved surface of polygon/sphere
SetForceLineSegmentsPerCircle(G4Int N) //Segment N*360
Controlling visualization
• Geant4 code stays basically the same no matter which driver you use
– Visualization is performed either with commands or from C++ code
• For the present tutorial, we confine ourselves to command-driven visualization.
• Some visualization drivers work directly from Geant4
– OpenGL
– OpenInventor
– RayTracer
– ASCIITree
• For other visualization drivers, you first have Geant4 produce a file, and then you have
that file rendered by another application (which may have GUI control)
– HepRepFile
– DAWNFILE
– VRML2FILE
– gMocrenFile
• You can open more than one driver at a time
– For example, do a quick check in OpenGL, then save the same event for a beautiful
DAWN plot
53
A variety of choices

Comput. Phys. Comm. 178 (2008) 331-365 54


Qt Driver with OpenGL visualization
• Recent developments focused on Qt User Interface and Visualization

55
• /vis/open OGL 600x600−0+0 OpenGL
• Features
– Control directly from Geant4
– Uses GL libraries that are already included on
most Linux and Windows systems
– Rendered, photorealistic image with some
interactive features
• zoom, rotate, translate
– Fast response (can usually exploit full potential of
graphics hardware)
• Save as pixel graphics or vector EPS

• /vis/open OIX or /vis/open IOWin32


OpenInventor
• /vis/open HepRepFile - HepRep
• /vis/open DAWNFILE -DAWN
• /vis/open VRML1FILE or -VRML
• /vis/open VRML2FILE OTHERS
• /vis/open RayTracer -RayTracer
• /vis/open Atree -ASCIITree 56
Physics processes
Nuclear reactor
Physics Processes
• Geant4 does not have any default particles or processes.
– Even for the particle transportation, you have to define it explicitly.
• Derive your own concrete class from G4VUserPhysicsList abstract base class.
– Define all necessary particles
– Define all necessary processes and assign them to proper particles
– Define cut-off ranges applied to the world (and each region)
• Primarily, the user’s task is choosing a “pre-packaged” physics list, that
combines physics processes and models that are relevant to a typical
application use-cases.
– If “pre-packaged” physics lists do not meet your needs, you may add or
alternate some processes/models.
– If you are brave enough, you may implement your physics list.

58
Definition of a particle
• Geant4 provides the G4ParticleDefinition definition class to represent a large
number of elementary particles and nuclei, organized in six major categories:
– lepton, meson, baryon, boson, short-lived and ion
• Each particle is represented by its own class, which is derived from
– G4ParticleDefinition
• Proprieties characterizing individual particles are “read only” and can not be
changed directly

• User must define all particles type which are used in the application:
– not only primary particles but also all other particles which may appear as
secondaries generated by the used physics processes

59
Basic concept of Particles
particles/leptons/src/G4Electron.cc
There are three levels of class to // Arguments for constructor are as follows
describe particles in Geant4: // name mass width charge
// 2*spin parity C-conjugation
• G4ParticleDefinition // 2*Isospin 2*Isospin3 G-parity
– define a particle : aggregates // type lepton number baryon number PDG encoding
information to characterize a // stable lifetime decay table
particle’s properties (name, // shortlived subType anti_encoding
mass, spin, etc…) magneticMoment
• G4VDynamicParticle
– describe a particle interacting
with materials : aggregates
information to describe the
dynamic of particles (energy,
momentum, polarization, etc…)
• G4VTrack
– describe a particle travelling in
space and time : includes all the
information for tracking in a
detector simulation (position,
step, current volume, track ID,
parent ID, etc…) 60
Particles in Geant
• Particles are specified by Name and/or a code
• Uses PDG encoding and the list are rather large
• Particles are characterised by their static properties : mass, spin, lifetime, decay modes,
lepton/baryon number ….
• In principle, only stable and long lived particles (τ >10−13 s) are needed in the simulation
toolkit. The remaining particles need not be created in particle-medium interaction. This,
however, sets some limitation on the hadron physics model.
• Most commonly used particles are somewhat unique and each such particle is described by a
static object
– G4Gamma::GammaDefinition();
– G4Gamma:Gamma();
• Several particles are described through name, PDG code, e.g., Gluons, Quarks, Di-Quarks,
Leptons, Mesons, Baryons, … These are invoked through
– G4ParticleTable::FindParticle(code/name)
• Some ions and short lived particle are created by the process. They are activated also through
special methods in G4ParticleTable

Particles are to be initiated at the same time as the physics process initiation
PhysicsList::ConstructParticle()
// mesons
// pseudo-particles G4PionPlus::PionPlusDefinition();
G4Geantino::GeantinoDefinition(); G4PionMinus::PionMinusDefinition();
G4ChargedGeantino::ChargedGeantinoDefinition(); G4PionZero::PionZeroDefinition();
G4Eta::EtaDefinition();
// gamma G4EtaPrime::EtaPrimeDefinition();
G4Gamma::GammaDefinition(); G4KaonPlus::KaonPlusDefinition();
G4KaonMinus::KaonMinusDefinition();
// optical photon G4KaonZero::KaonZeroDefinition();
G4OpticalPhoton::OpticalPhotonDefinition(); G4AntiKaonZero::AntiKaonZeroDefinition();
G4KaonZeroLong::KaonZeroLongDefinition();
// leptons G4KaonZeroShort::KaonZeroShortDefinition();
G4Electron::ElectronDefinition();
G4Positron::PositronDefinition(); // barions
G4Proton::ProtonDefinition();
G4MuonPlus::MuonPlusDefinition();
G4AntiProton::AntiProtonDefinition();
G4MuonMinus::MuonMinusDefinition();
G4Neutron::NeutronDefinition();
G4AntiNeutron::AntiNeutronDefinition();
G4NeutrinoE::NeutrinoEDefinition();
G4AntiNeutrinoE::AntiNeutrinoEDefinition(); // ions
G4NeutrinoMu::NeutrinoMuDefinition(); G4Deuteron::DeuteronDefinition();
G4AntiNeutrinoMu::AntiNeutrinoMuDefinition(); G4Triton::TritonDefinition();
G4He3::He3Definition();
Σ±, Ξ−, Ω− , ±, B±, D±, Ds±, Λc+, Σc+, Σc++,Ξc+ G4Alpha::AlphaDefinition();
with antiparticle etc G4GenericIon::GenericIonDefinition();
62
Primary Generator Action
 MyPrimaryGeneratorAction :: MyPrimaryGeneratorAction()
 particleGun = new G4ParticleGun(n_particle) ; //G4ParticleGun
 MyPrimaryGeneratorAction :: GeneratePrimaries(G4Event * anEvent)
 G4ParticleTable * particleTable = G4ParticleTable :: GetParticleTable();
 G4ParticleDefinition* particle = particleTable FindParticle(particlenName =
“gamma”)
 FindParticle(22)
particleGun  SetParticleDefinition(particle)
particleGun  SetParticleMomentumDirection(G4ThreeVector(1, 1, 1))
particleGun  SetParticleEnergy(10*GeV)
particleGun  SetParticlePosition(G4ThreeVector(10*cm, 10*mm, 1*m))
(All these can be given through random number, or from external event generator)
particleGun  GeneratePrimaryVertex(anEvent)
Vertex must be within detector volume.
Physics processes
When a particle starts its journey through the detector, there will be several competing
processes the particle can go through. They are broadly divided into three categories:

• Transportation : Moving along a straight line (neutral or media with no em field) or along
a curve (charged in magnetic field) crossing volume boundaries
– It is treated as other processes. This process has to be registered during initialisation and
particles should know how to be transported
• It is called in G4VModularPhysicsList::ConstructProcess()
• // add transportation with ordering = ( -1, "first", "first" )
• pmanager ->AddProcess(theTransportationProcess);
• pmanager ->SetProcessOrderingToFirst(theTransportationProcess, idxAlongStep);
• pmanager ->SetProcessOrderingToFirst(theTransportationProcess, idxPostStep);
• Continuous Process : Particle kinematics get modified but the particle remains its identity
(continuous energy loss, multiple scattering, bremsstrahlung …)
• Discrete Process : Particle undergoes interaction or decays producing new particles and
may lose its own identity
– There are many discrete processes in em, weak and strong interactions. Gradually
updating these list
• Processes need to be registered at the initialisation time (by default all processes are off)
and activated during tracking particles
ConstructProcess(): A default one
Default constructor of XXPhysicsList() //e.g., basic/B3/src/B3PhysicsList.cc
G4int ver = 1; SetVerboseLevel(ver);
// EM Physics
RegisterPhysics(new G4EmStandardPhysics(ver));
// Synchroton Radiation & GN Physics
RegisterPhysics(new G4EmExtraPhysics(ver));
// Decays
RegisterPhysics(new G4DecayPhysics(ver))
// Hadron physics
RegisterPhysics(new G4HadronElasticPhysics(ver) );
RegisterPhysics(new G4HadronPhysicsQGSP_BERT_HP(ver)); //Inelastic
// Ion Physics
RegisterPhysics(new G4IonPhysics(ver));
// Radioactive decay
RegisterPhysics(new G4RadioactiveDecayPhysics(ver)) 65
G4VUserPhysicsList :
• ConstructParticle():
– choose the particles you need in your simulation, define all of them here
• ConstructProcess() :
– for each particle, assign all the physics processes relevant to your simulation
• What's a process ?
– a class that defines how a particle should interact with matter, or decays
» it's where the physics is!
• SetCuts() :
– set the range cuts for secondary production
• What's a range cut ?
– a threshold on particle production
» Particle unable to travel at least the range cut value are not produced

66
Geant4 hadronic models

Quantum Molecular Dynamics)


Low Energy
Nuclear Data

C++ version of Liege Intermolecular Cascade Model

67
Geant4 EM Packages
• Standard • Low-energy
– γ, e± up to 100 TeV – Livermore library γ, e− from 10 eV up to 1
– hadrons up to 100 TeV GeV
– ions up to 100 TeV – Livermore library based polarized processes
• Muons – PENELOPE (PENetration and Energy LOss
– up to 1 PeV of Positrons and Electrons) code rewrite , γ, e−
– energy loss propagator , e+ from 100 eV up to 1 GeV
• X-rays – hadrons and ions up to 1 GeV
– X-ray and optical photon – atomic de-excitation (fluorescence + Auger)
production proc. • Geant4-DNA
• High-energy – microdosimetry models for radiobiology
– processes at high energy (E>10GeV) (Geant4-DNA project) from 0.025 eV to 10
MeV
– physics for exotic particles
• Microelectronics
• Polarisation
– Applicable to the « G4_Si » NIST material
– simulation of polarized beams
• Electrons: 50 eV – 50 keV
• Optical
• Protons: 50 keV/u – 23 MeV/u
– optical photon interactions
• Utils
– general EM interfaces 68
EM component of a Reference Physics Lists
• The default EM physics constructor is standard
– G4EmStandardPhysics
– Examples: FTFP_BERT, QGSP_FTFP_BERT
– Corresponding classes exist in physics_list sublibrary
• Following extensions are available in Geant4 10.2:
– EMV – G4EmStandardPhysics_option1
– EMX – G4EmStandardPhysics_option2
– EMY – G4EmStandardPhysics_option3
– EMZ – G4EmStandardPhysics_option4
– LIV – G4EmLivermorePhysics
– PEN – G4EmPenelopePhysics
– GS – G4EmStandardPhysicsGS – new
• Physics lists with these extensions are not exist like a class but are created by
G4PhysListFactory
– See $G4INSTALL/examples/extended/hadronic/Hadr00 and other examples
• Without using G4PhysicsFactory
– $G4INSTALL/examples/basic/B4c/exampleB4c.cc (e.g., via
$G4INSTALL/source/physics_list/lists/include/FTFP_BERT.icc) 69
Setting up particle and physics list
:: ConstructParticle()
G4VUserPhysicsList
:: ConstructProcess()
:: ConstructEM(), ConstructHad(), ConstructGeneral(),…… Order AtRestDoIt
while( (*theParticleIterator)() ){ Order AlongStepDoIt
Order PostStepDoIt
G4ParticleDefinition* particle = theParticleIterator->value();
G4ProcessManager* pmanager = particle->GetProcessManager();
Inclusion of processes for “e+”
G4String particleName = particle->GetParticleName();
inside ConstructEM(). Also
If (particleName==“e+”)
1. Production of e+e pairs and
 pmanager  AddProcess (new G4eMultipleScattering(), -1, 1, 1);
2.Nuclear interaction in
 pmanager  AddProcess (new G4eIonization(), -1, 2, 2);
hadronic sub-package
 pmanager  AddProcess (new G4Brehmstrahlung(), -1, 3, 3);
 pmanager  AddProcess (new G4eplusAnnihilation(), 1, -1, 4); // ,,, …..
 RemoveProcess(G4VProcess * aprocess) or (G4VInt index)
//Swithch on or off processes
G4ProcessTable* process = G4ProcessTable::GetProcessTable();
G4ProcessManager* pmanager = particle->GetProcessManager(); //Need appropriate
particle for appropriate pmanager
process->Remove(process->FindProcess("muBrems",pmanager), pmanager);
process->Insert(new G4MultipleScattering(),pmanager);
Deep Inelastic Scattering
• Example : extended/electromagnetic/TestEm17/src/MuNuclearBuilder.cc

• G4MuonNuclearProcess* muNucProcess = new G4MuonNuclearProcess();


• G4MuonVDNuclearModel* muNucModel = new G4MuonVDNuclearModel();
• muNucProcess->RegisterMe(muNucModel);

• pManager = G4MuonPlus::MuonPlus()->GetProcessManager();
• pManager->AddDiscreteProcess(muNucProcess);

• pManager = G4MuonMinus::MuonMinus()->GetProcessManager();
• pManager->AddDiscreteProcess(muNucProcess);

71
Hadronic process : Code Example
G4ParticleDefinition* proton= retrieve the
G4Proton::ProtonDefinition(); process manager
G4ProcessManager* protonProcessManager = for proton
proton->GetProcessManager();

// Elastic scattering create the process


G4HadronElasticProcess* protonElasticProcess = for elastic
new G4HadronElasticProcess(); scattering

G4LElastic* protonElasticModel = get the LE parametrized


new G4LElastic(); model for elastic scattering

protonElasticProcess-> register the model to the


RegisterMe(protonElasticModel); process

protonProcessManager-> attach the process to


AddDiscreteProcess(protonElasticProcess); proton
An example code inside ConstructHad()
Hadronics process : Code example
...
// Inelastic scattering creates the process
G4ProtonInelasticProcess* protonInelasticProcess for inelastic
= new G4ProtonInelasticProcess(); scattering

G4LEProtonInelastic* protonLEInelasticModel gets the LEP model


= new G4LEProtonInelastic();
Model 1

up to 20 GeV
protonLEInelasticModel->
SetMaxEnergy(20.0*GeV);
protonInelasticProcess-> registers LEP model to
RegisterMe(protonLEInelasticModel); the process
G4HEProtonInelastic* protonHEInelasticModel =
Model 2

new G4HEProtonInelastic(); gets the HEP model


protonHEInelasticModel->SetMinEnergy(20.0*GeV); from 20 GeV
protonInelasticProcess
->RegisterMe(protonHEInelasticModel); registers HEP model to
the process
A detail example : advanced/underground_physics/src/DMXPhysicsList.cc
Production threshold : cuts
 The particle transport ends if the particle
 is slowed down to zero kinetic energy (and it doesn't have any interaction at rest)

 disappears in some interaction

 reaches the end of the simulation volume

• Each simulation developer must answer the question: how low can you go?
– should I produce (and track) everything or consider thresholds?
• This is a balancing act :
The best compromise

need to go low enough to Maximize the Maximize the


get the physics you're accuracy simulation time
interested in performances

can't go too low because some


processes have infrared divergence
causing huge CPU time 74
Production thresholds : cuts
• The traditional Monte Carlo solution is to impose an absolute cutoff in energy:
– particles are stopped when this energy is reached
– remaining energy is dumped at that point
• But, such a cut may cause imprecise stopping location and deposition of energy
• There is also a particle dependence
– range of 10 keV p in silicon is different from range of 10 keV e in silicon,
which is a few microns
• And a material dependence
– suppose you have a detector made of alternating sheets of Pb and plastic
scintillator
– if the cutoff is OK for Pb, it will likely be wrong for the scintillator which does
the actual energy deposition measurement

75
Production thresholds : cuts
• In Geant4 there are no tracking cuts
– particles are tracked down to a zero range/kinetic energy
• Only production cuts exist
– i.e. cuts allowing a particle to be born or not
– Applied to: gamma, electron, positron, proton
• Why are production cuts needed ?
• Some electromagnetic processes involve infrared divergences
– this leads to a huge number of smaller and smaller energy photons/electrons
(such as in Bremsstrahlung, -ray production)
– production cuts limit this production to particles above the threshold
– the remaining, divergent part is treated as a continuous effect (i.e. AlongStep
action)

76
Production thresholds : cuts
• Geant4 solution: impose a “range” production threshold
– this threshold is a distance, not an energy
– default = 0.7 mm
• This value can be specified in the optional SetCuts() method of the user physics list or via
UI commands :
• for e.g., to set a range cut of 10 micrometers, one can use /run/setCut 0.01 mm
or, for a given particle type (for e.g. electron) /run/setCutForAGivenParticle e 0.01 mm
– the primary particle loses energy by producing secondary electrons or gammas
– if primary no longer has enough energy to produce secondaries which travel at
least 1mm, two things happen:
• discrete energy loss ceases (no more secondaries produced)
• the primary is tracked down to zero energy using continuous energy loss
• Stopping location is therefore correct
• Only one value of production threshold distance is needed for all materials because
it corresponds to different energies depending on material.

77
Production thresholds : cuts
500 MeV p in LAr-Pb
sampling calorimeter
LAr Pb LAr Pb LAr Pb LAr Pb

LAr Pb LAr Pb

Cut = 455 keV Cut = 2 MeV


(range in LAr = 1.5 mm)

Production range = 1.5 mm

455 KeV electron energy in liquid Ar


Threshold in range : 1.5mm 2 MeV electron energy in Pb

78
Production and user cuts
 G4ProductionCutsTable :: GetProductionCutsTable () SetEnergyRange(10*eV, 100*TeV)
• SetCutswithDefault(): MyPhysicsList.cc ::SetCuts()
– SetCutValue(0.7*cm, “gamma”)
– SetCutValue(0.7*cm, “e+”)
– SetCutValue(0.7*cm, “e-”); // DumpCutValuesTable(); list of all
 G4Region * region = G4RegionStore :: GetInstance()  GetRegion(“Calor_EBlock”)
 G4ProductionCuts * cuts = new G4ProductionCuts;
• cutsSetProductionCut(1*mm, index), index=0,1,2 for , e and e+. All others are used in 1
• Instead of index cut can pass through G4ParticleDefinition or “pName”
• cuts  SetProductionCut(0.01*mm); //for all particles
• cuts  SetProductionCut(0.1*mm, G4ProductionCuts :: GetIndex(“gamma”));
• region  SetProductionCuts(cuts)
 G4UserLimits *limits = new G4UserLimits ()
• region  SetUserLimits(limits  SetMaxAllowedStep(5e-2*mm))
Event loop - Tracking
• Heart of any detector simulation is tracking
• Tracks (particles with kinematic
information) are put in a stack
(at the beginning of an event all
primary particles are
transferred) through
StackingManager on request
from EventManager
• Trace particles through detector
media and take care of the
particle-medium interaction
• Store energy deposits in media
which can transform deposited
energy to detectable signal
• Store relevant parameters which
can be used for further analysis.
• Keep track of all particles,
primary and secondary
Example of an Event and Tracks
• Stack is operated in a Last In Fast Out (LIFO) mod. Take out the last particle
from the stack (current track) having information on particle type, 4-momenta,
position and time

(ParentID = 3)
(ParentID = 1)

 Tracking order follows ‘last in first out’ rule:


T1 -> T4 -> T3 -> T6 -> T7 -> T5 -> T8 -> T2
Tracking
• Looked at the list of processes available to it and estimate the limiting step length
from each of these processes,
– Boundary crossing assuming linear transport
– Limit from maximum turning angle
– Limit from multiple scattering
– Limit from continuous energy loss
– Limit from decay length
– Limit from each of the discrete interaction processes
• Choose the minimum of these steps sizes as the current step size and remember
the limiting process
• Take a step – first transportation – if the limiting process is not boundary
crossing, special treatment has to be applied (cutstep)
• Tracking is continued for a given track till it stops or get killed or it goes out of
the experimental setup
• Tracking is continued for a given event till the tracking stack is empty
Tracking
• Here a Step has two points and also
‘delta’ information of a particle
(energy loss in that step, time spent in
the step, ….)

• Each point knows the volume. In case a step is limited by a volume boundary, the
end point physically stands on the boundary, and it logically belongs to the next
volume.
• It does not make two steps at a boundary
• At each end of step a control is given to the method
• UserSteppingAction of an object G4UserSteppingAction (or a class derived
from it and registered to the ActionManager)
• If it is a sensitive detector, a control is given to the method ProcessHits of the
appropriate sensitive detector (for the logical volume)
• Any process (including processes supplied by user) will be asked to take
appropriate action AlognStep, PostStep, AtRest.
• User can also take action on a track either at the start of tracking or at the end
Tracking
• It provides a more careful and detailed approach in swimming particles in an
electromagnetic field

• The equation of motion is integrated over a path length using


a Runga-Kutta method or some variations of this.
• In a uniform field, analytical solution exists and are used. In a
nearly uniform field, perturbation is applied
• The path is calculated using a chosen integration method and If CD is too large
then it is broken into linear chord segments that closely (>Delta intersection) , a
approximate the curve path. new intersection on the
• The chords are used to interrogate the navigator to find out chord AD will be
whether the track has crossed a volume boundary calculated.
Delta one step : the accuracy for the endpoint of 'ordinary' integration steps, those
which do not intersect a volume boundary
Inclusion of ElectroMagnetic field in the Detector
Difficult to have mapping of EM field in all position. In practice, read three components of
electric and magnetic field in many grid points (either is ascii format or in database) and using
interpolation/extrapolation routine calculate this in all point.
called by G4VUserDetectorConstruction::Construct(), // a virtual member of virtual G4VPhyVol*
G4FieldManager * fieldMgr =
G4TransportationManager :: GetTransportationManager() GetFieldManager();
G4UniformField * magfield = new G4UniformField(G4ThreeVector(0, 1.0*Tesla, 0));
fieldMgr  SetDetectorField(magfield); //set magnetic field map
MyElectroMagneticField * myField = new MyElectroMagneticField();
fieldMgr  SetDetectorField(myField);
An alternative field manager can be associated with any logical volume:
G4FieldManager* localFieldMgr = new G4FieldManager(myField);
logVolume->setFieldManager(localFieldMgr, true/false);
The field is propagated to all the daughter volumes / field assigned to daughters w/o their own
field manager
void MyElectroMagneticField::GetFieldValue(const double x[3], double B[6]) const ;
// returns EM field at any point, do interpolation/extrapolation here
Equation of motion in ElectroMagnetic

Setup equation of motion in magnetic field:


• G4EqMagElectricField * fEquation = new G4EqMagElectricField(inoicalField) ;
• G4MagIntegratorStepper * pStepper = new G4ClassicalRK4(fEquation)
• G4MagInt_Driver * pIntgrDriver = new G4MagInt_Driver(1e-5*mm, pStepper,
pStepper GetNumberOfVariables());
• G4ChordFinder * pChordFinder = new G4ChordFinder(pIntgrDriver);
pChordFinder  SetDeltaChord(1e-3*mm); //Maximum miss distance
fieldMgr  SetChordFinder(pChordFinder);
fieldMgr  SetDeltaOneStep(1e-3*mm);
fieldMgr  SetDeltaIntersection(1e-4*mm);

Different FieldManager can use different maximum miss distance, delta one step
and delta intersection in different regions.
Propagation in EM field
 G4PropagationInField * fieldPropagator =
G4TransportationManager ::
GetTransportationManager()GetPropagationInField();
fieldPropagator  SetMinimumEpsilonStep(1e-5*mm); // impose a minimum
relative error - and take precedence over DeltaOneStep. of the position/momentum
inaccuracy
fieldPropagator  SetMaximuilomEpsilonStep(1e-2*mm); //maximum relative
error
//Parameters must scale with problem size
fieldPropagator  SetLargestAcceptableStep(10*m); // A particle
could then take large spiral steps,.
minimum step size : strong fields or integration problems → very small steps, protect
that
User Action
• Apart from describing the detector in terms of passive and active elements, the user
has to take care of certain things in simulation, during the time of tracking and post
tracking.
• Take care of the secondaries produced in the discrete processes
• Store transient Hits at the time of tracking with information to be used for producing
detector response later
• Compute detector response in all sensitive detector starting from the Hits stored in
the event
– Group hits for individual readout channel
– Convert energy loss to pulse height; position and time to drift time, …
– Position signal into a number of readout channels; generate wire # /pad # / strip #
– Take care of special effect; non-uniformity, attenuation, ….
– See effect due to merging; saturation, multi-hit capability, ..
– Add background due to other physics process: electronic noise, radio activity, beam
induced, …
– Put in detector efficiency, intrinsic resolution
run.mac : User Interface (UI)
• bin/Linux-g++/XX_field run.mac 1
• # Avoid putting too many volumes in a Mother Volume
• # Use this open statement instead for OpenGL in immediate mode.
• /vis/open OGLIX
• /vis/viewer/set/viewpointThetaPhi 90 0
• /vis/viewer/zoom .4
• /vis/scene/add/trajectories 1000 //view particles
 G4UIdirectory
• /XX/gun/pid 13
• /XX/gun/rndm on  G4UIcmdWithAnInteger * Run
• /XX/gun/energy 12  G4UIcmdWithBool *
• /XX/gun/ensmear 0.5  G4UIcmdWithString *
• /XX/gun/Incdir 0.87, 0, 0.5
 G4UIcmsWithADouble
• /XX/gun/phsmear -3141.5
– #/process/eLoss/minKinEnergy 1.0 MeV  G4UIcmdWithDoubleAndUnit *
– #/process/eLoss/maxKinEnergy 50 TeV IncEnergycmd
– /gun/number 2  G4UIcmdWith3VectorAndUnit *
– /run/beamOn 10
IncDirectioncmd
– #Idle> help
The User Interface
• Class XXPrimaryGeneratorAction : public G4VUserPrimaryGeneratorAction
void SetIncEnergy(G4Double p) {incEnergy = p;}
void SetIncPosition(G4ThreeVector p) {incDirection = p;}

• XXPrimaryGeneratorMessenger * genMessenger;
Default constructor:
• genMessenger = new XXPrimaryGeneratorMessenger(this)
• Class XXPrimaryGeneratorMessenger : public G4UIMessenger
public : XXPrimaryGeneratorMessenger(XXPrimaryGeneratorAction*
XXGun ) : XXAction (XXGun) { …….
private : XXPrimaryGeneratorAction * XXAction
The User Interface
Constructor:
IncEnergycmd = new G4UIcmdWithDoubleAndUnit(“XX/gun/energy”, this)
 SetGuidance(“Set incident energy of particle”);
 SetParameterName(“Energy”, true, true);
must provide

 SetDefaultUnit(“GeV”);
 SetRange(“Energy>0. && Energy<1000.0);
 SetDefaultValue(12 );
 SetUnitCandidates(“eV keV MeV GeV TeV PeV”);
 void XXPrimaryGeneratorMessenger :: SetNewValue (G4UIcommand *
command, G4String newValue) { // …….
if(command == IncEnergyCmd) {
XXAction  SetIncEnergy(IncEnergyCmdGetNewDoubleValue(newValue)); }
User Action
• During tracking, user gets control at several places:
– For secondaries produced in discrete processes, appropriate action is to be
taken in G4UserStackingAction
– For steps inside a sensitive detector store hits using information from Step and
TouchableHistory in the method ProcessHit of G4SensitiveDetector
– For deciding to store track information for future use, use the methods
PreUserTrackingAction and PostUserTrackingAction of
G4UserTrackingAction
– For steps inside any medium, sensitive or not, user can take action in
G4UserSteppingAction::UserSteppingAction(const G4Step*)
– Finally storing informations of an Event, after the completion of tracking can
be interfaced in G4UserAction through the methods BeginOfEventAction and
EndOfEventAction
Sensitive Detector
• G4SDManager* SDman = G4SDManager :: GetSDMPointer();
 XXCal0SD* Cal0SD = new XXCal0SD(“XXXX”);
 SDman  AddNewDetector(cal0SD);
 LogicGASR SetSensitiveDetector(Cal0SD) // Logical volume
associated with Cal0SD, a derived class of G4VSensitiveDetector

• G4Region * aRegion0 = new G4Region(“Calor_EBlock”)


 LogicGASRSetRegion(aRegion0)
 aRegion0AddRootLogicalVolume (LogicGASR)

 aRegion0SetProductionCuts (prdcuts)
 This same “Calor_EBlock” string is used to change cuts in this
sensitive region in XXPhysicsList.cc
Helper classes and member functions
• G4HCofThisEvent //Class which stores hits collections generated at one event
• GetHC(); // pointer of hit collection.
• GetNumberOfCollection();
• AddHitsCollection(G4Int HCID, G4VHitsCollection* aHC);
• G4TouchableHistory : public G4VTouchable; // geometrical hierarchy, including its
net resultant local->global transform. Pointers for geometry
• G4Int depth = G4HistoryDepth();
• G4Int GetReplicaNumber (depth);
• G4VPhysicaVolume* G4VVolume(depth);
• G4VSolid* GetSolid(depth);
• inline const G4NavigationHistory * GetHistory(); // for transformation of local to
global & vice versa
• G4SDManager :: GetSDMPointer(); //extract static pointer of all sensitive detector
G4VHit:
 XXCal0Hit : public G4VHit SetEdep()
{G4Double edep; // Energy deposit AddEdep()
G4ThreeVector pos; // Position where energy deposit GetEdep()
G4ThreeVector mom; // Momentum of tracks SetTime()
G4Double toff; // Global time of energy deposit SetHitId()
Unsigned long HitId;}// Detector ID

 typedef G4THitsCollection<XXCal0Hit>XXCal0HitsCollection;
 extern G4Allocator<XXCal0Hit>XXCal0HitAllocator; //C-style (malloc)
space allocator to, but not used in the code
Sensitive Detector:
 XXCal0SD : public G4VSensitiveDetector
:: Initialise (G4HCofThisEvent * HCE)
:: G4Bool ProcessHits (G4Step * astep, G4TouchableHistory * hist);
:: EndOfevent ( G4HCofThisEvent * HCE);
Sensitive Detector and Hit information
G4HCofThisEvent //Class which G4LogicalVolume logic
stores hits collections generated at one G4LogicalVolume logic1
event
G4LogicalVolume logic2
Helper class
G4SDManager :: class XXcal0SD : public
GetSDMPointer(); //extract G4VSensitiveDetector //extract signal in
static pointer of all sensitive sensitive detector
detector XXcal0SD1 : public G4VSensitiveDetector
XXcal0SD2 : public G4VSensitiveDetector

XXCal0Hit : public G4VHit


//Collection of information (Hit)
for a particular sensitive detector
XXCal0Hit 1: public G4VHit
XXCal0Hit 2: public G4VHit
class XXcal0SD : public G4VSensitiveDetector
• private : XXcal0HitsCollection *cal0Collection;
• Default constructor : CollectionName.insert (HCname = “cal0Collect”); //Same string in
XXEventAction::BeginOfEventAction; colNam="cal0Collect"
• XXcal0SD::Initialise(G4HCofThisEvent * HCE) {
• Static int HCID = -1
• cal0Collection = new XXcal0HitsCollection (“SensitiveDetectorName”, CollectionName[0]);
• if ( HCID < 0 )
– HCID = G4SDManager :: GetSDMPointer  GetCollectionID(CollectionName[0]);
– HCE  AddHitsCollection(HCID, cal0Collection);
• XXcal0SD::ProcessHits(G4Step * astep, G4TouchableHistory *)
– edep = astep  GetTotalEnergyDeposit()/keV
o G4TouchableHistory * theTouchable = (G4TouchableHistory *)(astep  GetPrestepPoint 
GetTouchable());
o Int level = theTouchable  GetHistoryDepth(); //depth in geometry structure
Int ireplica = theTouchable  GetReplicaNumber(0  level - 1); //replica number
For all steps calculate all these, irrespective of sensitive detector or not :
XXSteppingAction:public GeUserSteppingAction
:: UserSteppingAction (const G4Step* astep)
class XXcal0SD : public G4VSensitiveDetector
– G4VLogicalVolume* alog = aStep->GetTrack()->GetVolume()->GetLogicalVolume();
– G4double edep = aStep->GetTotalEnergyDeposit(); ->GetNonIonizingEnergyDeposit();
– G4StepPoints apt = astep  GetPreStepPoint(); //starting point of this step
– apt = astep GetProcessDefinedStep() //G4VProcess * ;// 0 => step is defined by user limit step
– apt2 = astep  GetPostStepPoint(); //end point of this step
– atime =apt  GetGlobalTime()/ns; // Time since event is created
–  GetLocalTime()/ns; // Time since track is created
–  GetProperTime()/ns; // Time since track is created(rest frame of particle)
– atrk  GetTrackID() , GetParentID(), GetKineticEnergy(), GetTotalEnergy(), GetMomentum();
– G4ThreeVector glbpos = 0.5*(apt GetPosition() + apt2 GetPosition());
– G4ThreeVector localpos = theTouchable GetHistory() GetTopTransform() (.invert()).
TransformPoint(glbpos);
• int level = theTouchable->GetHistoryDepth();

• G4int tmpint = theTouchable->GetCopyNumber( 8 ) ;


• G4int nInCH = tmpint%8; // theTouchable->GetCopyNumber( 7 ) ;
• G4int nInMO = int(tmpint/8); // theTouchable->GetCopyNumber( 6 ) ;
• G4int nInLA = theTouchable->GetCopyNumber( 9 ) ;
• G4int nInDT = theTouchable->GetCopyNumber( 10 ) ;
Digitisation
– Int detid = INOM (2) + Layer(8) + module(3) + chamber(3) + X-strip(7) + Y-strip(7);
– unsigned long detid = nInDT; //2bit
– detid<<=8;
– detid +=nInLA;
– detid<<=3;
– detid +=nInMO;
– detid<<=3;
– detid +=nInCH;
– detid<<=7;
– detid +=nInX[ix];
– detid<<=7;
– detid +=nInY[iy];

– Int oldcellid =−1; for (int ij=0; ij<Incell; ij++) { if (detId==cellDetId[ij]) { oldcellId=ij;}
– If (oldcellId==−1 && Incell <NumberofCell -1) {
• XXcaloHit* newHit = new IcalocaloHit();
• newHit->SetEDep(edep); SetTime(atime); //Corrected pathlength in strip
• Setpos(glbpos), SetMom(amom);
• Incell = caloCollection insert(newHit); cellDetId[Incell-1] = detid; } else {
• (*calocollection)[oldCellId]  AddEdep(edep); SetTime(min(atime, oldHit->GetTime()); }
XXEventAction : Action at the end
• XXEventAction : public G4UserEventAction
• Private :G4int cal0CollID, cal1CollID, cal2CollID; //Different Hit collection ID, initialised
with -1;
• BeginOfEventAction(const G4Event* evt) {
• G4SDManager * SDman = G4SDManager::GetSDMpointer();
• cal0CollID = SDman->GetCollectionID(colNam="cal0Collect"); //Same string in
XXcal0SD, HCname = “cal0Collect”); // return the same HCID (in XXcal0SD ) of the
sensitive Detector , same ID can be obtained using GetCollectionID(G4VHitCollection* )
• EndOfEventAction (const G4Event* evt) {
• G4HCofThisEvent* HCE = evt->GetHCofThisEvent();
• evtNo = evt->GetEventId(); XXcal0HitsCollection* EHC0 = 0;
• If (HCE) { EHC0 = (XXcal0HitCollection*)(HCE->GetHC(cal0collID);
• If (EHC0) { n_hits = EHC0->entries();
• for (int ij=0; ij<n_hit; ij++) { totE +=(*EHC0)[ij]->GetEdep()/keV; (*EHC0)[ij]-
>GetHitId(); (*EHC0)[ij]->GetPos(); (*EHC0)[ij]->GetTime();
Secondary Particle in steppingAction/XXSD
• const std::vector<const G4Track*>* secondary =
aStep->GetSecondaryInCurrentStep();
• for (size_t lp=0; lp<(*secondary).size(); lp++) {
particle = (*secondary)[lp]->GetDefinition();
G4String name = particle->GetParticleName();
G4String type = particle->GetParticleType();
G4double charge = particle->GetPDGCharge();
G4double energy = (*secondary)[lp]->GetKineticEnergy();
G4String volumeName = (*secondary)[lp] -> GetVolume() -> GetName();
G4String proc = (*secondary)[lp]-> GetCreatorProcess()-> GetProcessName();

101
G4Track & G4StackedTrack
– G4Track * atrk = astep  G4Track(); //Pointer to the particle, which is interacting
– atrk  GetDynamicParticle() //G4DynamicParticle *
– atrk GetDefinition() //G4ParticleDefinition *
– atrk GetCreatorProcess() //G4VProcess

– atrk  GetVertexPosition();

– atrk  GetVertexMomentumDirection();

– atrk  GetLogicalVolumeAtVertex();

– atrk  GetGlobalTime();  same as prestep time

 G4StackedTrack : G4Track * GetTrack(); //a G4Track object in the form of bi-


directional linked list, using G4StackManager.cc
• G4StackedTrack * GetPrevious()
• G4StackedTrack * GetNext()
Histogram & rootuple creation
B4RunAction::B4RunAction() : G4UserRunAction() { // get analysis manager
G4AnalysisManager* analysisManager = G4AnalysisManager::Instance();
analysisManager->OpenFile(“testexample.root”); // Create directories B4Analysis.hh
//analysisManager->SetHistoDirectoryName("histograms");
//analysisManager->SetNtupleDirectoryName("ntuple"); #ifndef B4Analysis_h
analysisManager->SetVerboseLevel(1); #define B4Analysis_h
analysisManager->SetFirstHistoId(1); //default 0
// analysisManager->SetFirstNtupleId(1); #include “g4root.hh”
#endif
// Creating histograms
analysisManager->CreateH1("1","Edep in absorber", 100, 0., 800*MeV); Include this file or
analysisManager->CreateH1("2","Edep in gap", 100, 0., 100*MeV); simply
analysisManager->CreateH1("3","trackL in absorber", 100, 0., 1*m); #include “g4root.hh”
analysisManager->CreateH1("4","trackL in gap", 100, 0., 50*cm); in EventAction and
RunAction file
// Creating ntuple
analysisManager->CreateNtuple("B4", "Edep and TrackL");
analysisManager->CreateNtupleFColumn("Labs");
analysisManager->CreateNtupleDColumn("Eabs");
analysisManager->CreateNtupleDColumn("Egap"); //If you want to fill objects
analysisManager->CreateNtupleFColumn("Lgap"); //with different frequency
analysisManager->FinishNtuple();
} 103
Histogram & rootuple : filling & saving
void B4aEventAction::EndOfEventAction(const G4Event*
event) {
// get analysis manager
G4AnalysisManager* analysisManager =
void
G4AnalysisManager::Instance();
B4RunAction::EndOfRunActio
n(const G4Run* /*run*/) {
// fill histograms
G4AnalysisManager*
analysisManager->FillH1(1, fEnergyAbs);
analysisManager =
analysisManager->FillH1(2, fEnergyGap);
G4AnalysisManager::Instance()
analysisManager->FillH1(3, fTrackLAbs);
;
analysisManager->FillH1(4, fTrackLGap);
.......
analysisManager->Write();
// fill ntuple
analysisManager->CloseFile();
analysisManager->FillNtupleFColumn(0, fTrackLAbs);
}
analysisManager->FillNtupleDColumn(1, fEnergyAbs);
analysisManager->FillNtupleDColumn(2, fEnergyGap);
analysisManager->FillNtupleFColumn(3, fTrackLGap); Run/B4a –m run2.mac
analysisManager->AddNtupleRow();
}

104
Histogram & rootuple : collecting information
class B4aSteppingAction : public G4UserSteppingAction {
include/B4aEventAction.hh
------------------------------------------------------------------------------------
class B4aEventAction : public
B4aSteppingAction::B4aSteppingAction(
G4UserEventAction {
const B4DetectorConstruction* detectorConstruction,
B4aEventAction* eventAction)
void
: G4UserSteppingAction(), fDetConstruction(detectorConstruction),
B4aEventAction::AddAbs(G4
fEventAction(eventAction) { }
double de, G4float dl) {
fEnergyAbs += de;
void B4aSteppingAction::UserSteppingAction(const G4Step* step) {
fTrackLAbs += dl;
// get volume of the current step
}
G4VPhysicalVolume* volume
= step->GetPreStepPoint()->GetTouchableHandle()->GetVolume();
void
B4aEventAction::AddGap(G
// energy deposit and step length
4double de, G4float dl) {
G4double edep = step->GetTotalEnergyDeposit();
fEnergyGap += de;
G4float stepLength = step->GetStepLength();
fTrackLGap += dl;
}
if ( volume == fDetConstruction->GetAbsorberPV() ) {
private:
fEventAction->AddAbs(edep, stepLength);
G4double fEnergyAbs;
}
G4double fEnergyGap;
G4float fTrackLAbs;
if ( volume == fDetConstruction->GetGapPV() ) {
G4float fTrackLGap;
fEventAction->AddGap(edep, stepLength);
}
}
105
Multiple ntuple in same file : Booking
analysisManager->SetFirstNtupleId(1);
analysisManager->CreateNtuple("B4", "Edep and TrackL"); Need to include a
pAnalysis->fNtColId[0] = analysisManager->CreateNtupleDColumn("Eabs"); new static pointer
pAnalysis->fNtColId[1] = analysisManager->CreateNtupleDColumn("Egap"); pAnalysis to keep
pAnalysis->fNtColId[2] = analysisManager->CreateNtupleDColumn("Labs"); track of all
pAnalysis->fNtColId[3] = analysisManager->CreateNtupleDColumn("Lgap"); “columnId”,
analysisManager->FinishNtuple(); fNtCollid[]
//Create one ntuple
Can store Integer
analysisManager -> CreateNtuple("b4a", "Primary");
pAnalysis->fNtColId[4] = analysisManager -> CreateNtupleDColumn("Eabs1"); variable also
analysisManager -> FinishNtuple();
But,
//Create Second ntuple only rowwise
analysisManager-> CreateNtuple("b4b", "Secondary"); ntuple,
pAnalysis->fNtColId[5] = analysisManager -> CreateNtupleDColumn("Labs1"); not columnwise
analysisManager -> FinishNtuple(); ntuple
//creating third ntuple
analysisManager -> CreateNtuple("b4c", "Tertiary"); More details in
pAnalysis->fNtColId[6] = analysisManager -> CreateNtupleDColumn("Egap2"); ../examples/advanc
pAnalysis->fNtColId[7] = analysisManager -> CreateNtupleDColumn("Labs2"); ed/radioprotection
pAnalysis->fNtColId[8] = analysisManager -> CreateNtupleDColumn("Lgap2");
analysisManager -> FinishNtuple(); 106
Multiple ntuple in same file : Filling
analysisManager->FillNtupleDColumn(1, pAnalysis->fNtColId[0], Energycal0);
analysisManager->FillNtupleDColumn(1, pAnalysis->fNtColId[1], EnergyGap);
analysisManager->FillNtupleDColumn(1, pAnalysis->fNtColId[2], TrackLcal0);
analysisManager->FillNtupleDColumn(1, pAnalysis->fNtColId[3], TrackLGap);
analysisManager->AddNtupleRow(1);

analysisManager->FillNtupleDColumn(2, pAnalysis->fNtColId[4], Energycal0);


analysisManager->AddNtupleRow(2);

analysisManager->FillNtupleDColumn(3, pAnalysis->fNtColId[5], TrackLcal0);


analysisManager->AddNtupleRow(3);
analysisManager->FillNtupleDColumn(3, pAnalysis->fNtColId[5], TrackLGap);
analysisManager->AddNtupleRow(3); //Filled second time the same ntuple

analysisManager->FillNtupleDColumn(4, pAnalysis->fNtColId[6], EnergyGap);


analysisManager->FillNtupleDColumn(4, pAnalysis->fNtColId[7], TrackLcal0);
analysisManager->FillNtupleDColumn(4, pAnalysis->fNtColId[8], TrackLGap);
analysisManager->AddNtupleRow(4);
analysisManager->AddNtupleRow(4); //Multiple filling (e.g., multitrack)
analysisManager->AddNtupleRow(4);

107
Tracing back ancestors : used static pointer
1. Define a structure in include/MultiSimAnalysis.hh
struct trackinfo {
G4int fTrackID;
G4int fParentID;
G4int fprocessId;
G4String Interaction;
G4String ParticleName;
G4double PDGCharge;
G4int PDGEncoding;
G4ThreeVector momentum;
G4ThreeVector vertexPosition;
G4double globalTime;
}; // May add more variable for the material/logicalvol name etc, where it is
produced
vector<trackinfo> alltrkinfo;

2. src/XXEventAction.cc (in ::BeginOfEventAction(const G4Event* evt)


clear the list
pAnalysis->alltrkinfo.clear()
108
Tracing back ancestors
3. src/XXSteppingAction.cc ::UserSteppingAction(const G4Step* aStep)
where store all information of any tracks in the process.
const G4Track* track = aStep->GetTrack();
int trkId = track->GetTrackID();
bool isfilled = false;
for (unsigned int ij=0; ij<pAnalysis->alltrkinfo.size(); ij++) {
if (pAnalysis->alltrkinfo[ij].fTrackID == trkId) {
isfilled =true; break;
}
}
if (!isfilled) {
trackinfo tmptrkinfo;
tmptrkinfo.fTrackID = track->GetTrackID();
tmptrkinfo.fParentID = track->GetParentID();
if (track->GetCreatorProcess()) {
tmptrkinfo.fprocessId = track->GetCreatorProcess()->GetProcessType();
tmptrkinfo.Interaction = track->GetCreatorProcess()->GetProcessName();
} else {
tmptrkinfo.fprocessId = -1;
tmptrkinfo.Interaction = "void";
}
109
Tracing back ancestors
3. src/XXSteppingAction.cc ::UserSteppingAction(const G4Step* aStep)
where store all information of any tracks in the process.
tmptrkinfo.ParticleName = track->GetDefinition()->GetParticleName();
tmptrkinfo.PDGCharge = track->GetDefinition()->GetPDGCharge();
tmptrkinfo.PDGEncoding = track->GetDefinition()->GetPDGEncoding();
tmptrkinfo.momentum = track->GetMomentum()/(GeV);
tmptrkinfo.vertexPosition = glbpos/(cm);
tmptrkinfo.globalTime = aStep->GetPreStepPoint()->GetGlobalTime()/(ns);

pAnalysis->alltrkinfo.push_back(tmptrkinfo);

4. src/XXcal0SD.cc

G4bool XXcal0SD::ProcessHits(G4Step* aStep, G4TouchableHistory*)


Here loop over all parents, and while parent, grandparent ... is muon/or any
other particle, it will identify it.
const G4Track* track = aStep->GetTrack();
int parenId = track->GetParentID();
int iloop = 0;
110
Tracing back ancestors
4. while (parenId>0 && track->GetDefinition()->GetPDGEncoding()==11) {
for (unsigned int ij=0; ij<pAnalysis->alltrkinfo.size(); ij++) { int parenId = track-
if (parenId==pAnalysis->alltrkinfo[ij].fTrackID) { >GetParentID();
if (iloop==0) { int iloop = 0;
cout <<"Parti "<<iloop<<" "<< track->GetTrackID()<<" "
<< track->GetParentID()<<" " << track->GetDefinition()->GetPDGEncoding()<<" "
<< (track->GetCreatorProcess()) ? track->GetCreatorProcess()->GetProcessName() :
"null "<<" "
<< aStep->GetPreStepPoint()->GetPosition()<<" "<< track->GetMomentum()<<" "
<< aStep->GetPreStepPoint()->GetGlobalTime()/(ns)<<endl;
iloop++;
}

cout <<"namex "<<iloop<<" "<< pAnalysis->alltrkinfo[ij].fTrackID<<" "


<< pAnalysis->alltrkinfo[ij].fParentID<<" "<< pAnalysis->alltrkinfo[ij].PDGEncoding<<" "
<< pAnalysis->alltrkinfo[ij].Interaction<<" "<< pAnalysis->alltrkinfo[ij].vertexPosition<<" "
<< pAnalysis->alltrkinfo[ij].momentum<<" "<< pAnalysis->alltrkinfo[ij].globalTime<<endl;

parenId = pAnalysis->alltrkinfo[ij].fParentID;
break;
}}}
111

You might also like