55 :
G4VEmModel(nam),fParticleChange(0),isInitialised(false),
56 crossSectionHandler(0),formFactorData(0)
58 lowEnergyLimit = 250 * eV;
59 highEnergyLimit = 100 * GeV;
72 if(verboseLevel > 0) {
73 G4cout <<
"Livermore Polarized Rayleigh is constructed " <<
G4endl
75 << lowEnergyLimit / eV <<
" eV - "
76 << highEnergyLimit / GeV <<
" GeV"
85 if (crossSectionHandler)
delete crossSectionHandler;
86 if (formFactorData)
delete formFactorData;
101 if (verboseLevel > 3)
102 G4cout <<
"Calling G4LivermorePolarizedRayleighModel::Initialise()" <<
G4endl;
104 if (crossSectionHandler)
106 crossSectionHandler->
Clear();
107 delete crossSectionHandler;
113 crossSectionHandler->
Clear();
114 G4String crossSectionFile =
"rayl/re-cs-";
115 crossSectionHandler->
LoadData(crossSectionFile);
118 G4String formFactorFile =
"rayl/re-ff-";
120 formFactorData->
LoadData(formFactorFile);
125 if (verboseLevel > 2)
126 G4cout <<
"Loaded cross section files for Livermore Polarized Rayleigh model" <<
G4endl;
130 if (verboseLevel > 0) {
131 G4cout <<
"Livermore Polarized Rayleigh model is initialized " <<
G4endl
138 if(isInitialised)
return;
140 isInitialised =
true;
151 if (verboseLevel > 3)
152 G4cout <<
"Calling CrossSectionPerAtom() of G4LivermorePolarizedRayleighModel" <<
G4endl;
154 if (GammaEnergy < lowEnergyLimit || GammaEnergy > highEnergyLimit)
return 0.0;
168 if (verboseLevel > 3)
169 G4cout <<
"Calling SampleSecondaries() of G4LivermorePolarizedRayleighModel" <<
G4endl;
173 if (photonEnergy0 <= lowEnergyLimit)
189 G4double outcomingPhotonCosTheta = GenerateCosTheta(photonEnergy0, Z);
190 G4double outcomingPhotonPhi = GeneratePhi(outcomingPhotonCosTheta);
191 G4double beta=GeneratePolarizationAngle();
211 zDir=outcomingPhotonCosTheta;
212 xDir=std::sqrt(1-outcomingPhotonCosTheta*outcomingPhotonCosTheta);
214 xDir*=std::cos(outcomingPhotonPhi);
215 yDir*=std::sin(outcomingPhotonPhi);
222 G4ThreeVector outcomingPhotonPolarization(xPrime*std::cos(beta) + yPrime*std::sin(beta));
232G4double G4LivermorePolarizedRayleighModel::GenerateCosTheta(
G4double incomingPhotonEnergy,
G4int zAtom)
const
252 const G4double xFactor = (incomingPhotonEnergy*cm)/(h_Planck*c_light);
260 if (incomingPhotonEnergy > 5.*MeV)
271 fCosTheta = (1.+cosTheta*cosTheta)/2.;
275 x = xFactor*std::sqrt((1.-cosTheta)/2.);
278 fValue = formFactorData->
FindValue(x, zAtom-1);
280 fValue = formFactorData->
FindValue(0., zAtom-1);
293G4double G4LivermorePolarizedRayleighModel::GeneratePhi(
G4double cosTheta)
const
306 sin2Theta=1.-cosTheta*cosTheta;
311 cosPhi = std::cos(phi);
312 phiProbability= 1. - sin2Theta*cosPhi*cosPhi;
321G4double G4LivermorePolarizedRayleighModel::GeneratePolarizationAngle(
void)
const
338 photonPolarization =
photon.GetPolarization();
339 photonMomentumDirection =
photon.GetMomentumDirection();
341 if ((!photonPolarization.
isOrthogonal(photonMomentumDirection, 1e-6)) || photonPolarization.
mag()==0.)
354 photonPolarization=e1+e2;
356 else if (photonPolarization.
howOrthogonal(photonMomentumDirection) != 0.)
361 photonPolarization=photonPolarization.
perpPart(photonMomentumDirection);
364 return photonPolarization.
unit();
G4DLLIMPORT std::ostream G4cout
Hep3Vector orthogonal() const
Hep3Vector cross(const Hep3Vector &) const
bool isOrthogonal(const Hep3Vector &v, double epsilon=tolerance) const
Hep3Vector perpPart() const
double howOrthogonal(const Hep3Vector &v) const
const G4ThreeVector & GetMomentumDirection() const
G4ParticleDefinition * GetDefinition() const
G4double GetKineticEnergy() const
virtual void SampleSecondaries(std::vector< G4DynamicParticle * > *, const G4MaterialCutsCouple *, const G4DynamicParticle *, G4double tmin, G4double maxEnergy)
virtual void Initialise(const G4ParticleDefinition *, const G4DataVector &)
virtual ~G4LivermorePolarizedRayleighModel()
G4ParticleChangeForGamma * fParticleChange
G4LivermorePolarizedRayleighModel(const G4ParticleDefinition *p=0, const G4String &nam="LivermorePolarizedRayleigh")
virtual G4double ComputeCrossSectionPerAtom(const G4ParticleDefinition *, G4double kinEnergy, G4double Z, G4double A=0, G4double cut=0, G4double emax=DBL_MAX)
void SetProposedKineticEnergy(G4double proposedKinEnergy)
void ProposePolarization(const G4ThreeVector &dir)
void ProposeMomentumDirection(G4double Px, G4double Py, G4double Pz)
G4double FindValue(G4int Z, G4double e) const
void LoadData(const G4String &dataFile)
virtual G4double FindValue(G4double x, G4int componentId=0) const =0
virtual G4bool LoadData(const G4String &fileName)=0
void SetHighEnergyLimit(G4double)
G4ParticleChangeForGamma * GetParticleChangeForGamma()
G4double LowEnergyLimit() const
G4double HighEnergyLimit() const
const G4Element * SelectRandomAtom(const G4MaterialCutsCouple *, const G4ParticleDefinition *, G4double kineticEnergy, G4double cutEnergy=0.0, G4double maxEnergy=DBL_MAX)
void InitialiseElementSelectors(const G4ParticleDefinition *, const G4DataVector &)
void ProposeTrackStatus(G4TrackStatus status)
void ProposeLocalEnergyDeposit(G4double anEnergyPart)