177{
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
194
195 if (verboseLevel > 3) {
196 G4cout <<
"G4LivermoreComptonModel::SampleSecondaries() E(MeV)= "
199 }
200
201
202 if (photonEnergy0 <= lowEnergyLimit)
203 {
207 return ;
208 }
209
210 G4double e0m = photonEnergy0 / electron_mass_c2 ;
212
213
217
218 G4double epsilon0Local = 1. / (1. + 2. * e0m);
219 G4double epsilon0Sq = epsilon0Local * epsilon0Local;
220 G4double alpha1 = -std::log(epsilon0Local);
221 G4double alpha2 = 0.5 * (1. - epsilon0Sq);
222
223 G4double wlPhoton = h_Planck*c_light/photonEnergy0;
224
225
231
232 do
233 {
235 {
236
238 epsilonSq = epsilon * epsilon;
239 }
240 else
241 {
242 epsilonSq = epsilon0Sq + (1. - epsilon0Sq) *
G4UniformRand();
243 epsilon = std::sqrt(epsilonSq);
244 }
245
246 oneCosT = (1. - epsilon) / ( epsilon * e0m);
247 sinT2 = oneCosT * (2. - oneCosT);
248 G4double x = std::sqrt(oneCosT/2.) / (wlPhoton/cm);
250 gReject = (1. - epsilon * sinT2 / (1. + epsilonSq)) * scatteringFunction;
251
253
255 G4double sinTheta = std::sqrt (sinT2);
257 G4double dirx = sinTheta * std::cos(phi);
258 G4double diry = sinTheta * std::sin(phi);
260
261
262
263
264
265
266
267 G4int maxDopplerIterations = 1000;
269 G4double photonEoriginal = epsilon * photonEnergy0;
273
275
276 do
277 {
278 ++iteration;
279
282
283 eMax = photonEnergy0 - bindingE;
284
285
286
288
289 G4double pDoppler = pSample * fine_structure_const;
290 G4double pDoppler2 = pDoppler * pDoppler;
292 G4double var3 = var2*var2 - pDoppler2;
293 G4double var4 = var2 - pDoppler2 * cosTheta;
294 G4double var = var4*var4 - var3 + pDoppler2 * var3;
295 if (var > 0.)
296 {
298 G4double scale = photonEnergy0 / var3;
299
300 if (
G4UniformRand() < 0.5) { photonE = (var4 - varSqrt) * scale; }
301 else { photonE = (var4 + varSqrt) * scale; }
302 }
303 else
304 {
305 photonE = -1.;
306 }
307 } while ( iteration <= maxDopplerIterations &&
308
309
310
311
312 (photonE > eMax ) );
313
314
315
316
317 if (iteration >= maxDopplerIterations)
318 {
319 photonE = photonEoriginal;
320 bindingE = 0.;
321 }
322
323
324
326 photonDirection1.rotateUz(photonDirection0);
328
330
331 if (photonEnergy1 > 0.)
332 {
334 }
335 else
336 {
337 photonEnergy1 = 0.;
340 }
341
342
343 G4double eKineticEnergy = photonEnergy0 - photonEnergy1 - bindingE;
344
345
346 if(eKineticEnergy < 0.0) {
347 bindingE = photonEnergy0 - photonEnergy1;
348
349 } else {
350 G4double eTotalEnergy = eKineticEnergy + electron_mass_c2;
351
352 G4double electronE = photonEnergy0 * (1. - epsilon) + electron_mass_c2;
353 G4double electronP2 = electronE*electronE - electron_mass_c2*electron_mass_c2;
356 if (electronP2 > 0.)
357 {
358 cosThetaE = (eTotalEnergy + photonEnergy1 )* (1. - epsilon) / std::sqrt(electronP2);
359 sinThetaE = -sqrt((1. - cosThetaE) * (1. + cosThetaE));
360 }
361
362 G4double eDirX = sinThetaE * std::cos(phi);
363 G4double eDirY = sinThetaE * std::sin(phi);
365
367 eDirection.rotateUz(photonDirection0);
369 eDirection,eKineticEnergy) ;
370 fvect->push_back(dp);
371 }
372
373
374
375 if(fAtomDeexcitation && iteration < maxDopplerIterations) {
378 size_t nbefore = fvect->size();
382 size_t nafter = fvect->size();
383 if(nafter > nbefore) {
384 for (size_t i=nbefore; i<nafter; ++i) {
385 bindingE -= ((*fvect)[i])->GetKineticEnergy();
386 }
387 }
388 }
389 }
390 if(bindingE < 0.0) { bindingE = 0.0; }
392}
G4double RandomSelectMomentum(G4int Z, G4int shellIndex) const
const G4ThreeVector & GetMomentumDirection() const
G4ParticleDefinition * GetDefinition() const
G4double GetKineticEnergy() const
static G4Electron * Electron()
const G4Material * GetMaterial() const
const G4String & GetName() const
void SetProposedKineticEnergy(G4double proposedKinEnergy)
void ProposeMomentumDirection(G4double Px, G4double Py, G4double Pz)
G4double BindingEnergy(G4int Z, G4int shellIndex) const
G4int SelectRandomShell(G4int Z) const
G4bool CheckDeexcitationActiveRegion(G4int coupleIndex)
virtual const G4AtomicShell * GetAtomicShell(G4int Z, G4AtomicShellEnumerator shell)=0
void GenerateParticles(std::vector< G4DynamicParticle * > *secVect, const G4AtomicShell *, G4int Z, G4int coupleIndex)
virtual G4double FindValue(G4double x, G4int componentId=0) const =0
const G4Element * SelectRandomAtom(const G4MaterialCutsCouple *, const G4ParticleDefinition *, G4double kineticEnergy, G4double cutEnergy=0.0, G4double maxEnergy=DBL_MAX)
void ProposeTrackStatus(G4TrackStatus status)
void ProposeLocalEnergyDeposit(G4double anEnergyPart)