190 if((isIonTrack && ((trackZ<=0 && trackL==0) || trackA<=trackZ)) ||
191 (nucleusA>1 && (nucleusZ<=0 || nucleusA<=nucleusZ))) {
193 theResult.SetStatusChange(
isAlive);
201 if(trackA<=1 && nucleusA<=1 && (trackPDG!=-2212 && trackPDG!=-2112)) {
202 return theBackupModelNucleon->ApplyYourself(aTrack, theNucleus);
207 const G4int theMaxProjMassINCL = theInterfaceStore->GetMaxProjMassINCL();
208 if(trackA > theMaxProjMassINCL && nucleusA > theMaxProjMassINCL) {
209 if(!complainedAboutBackupModel) {
210 complainedAboutBackupModel =
true;
211 std::stringstream ss;
212 ss <<
"INCL++ refuses to handle reactions between nuclei with A>"
213 << theMaxProjMassINCL
214 <<
". A backup model ("
215 << theBackupModel->GetModelName()
216 <<
") will be used instead.";
217 theInterfaceStore->EmitBigWarning(ss.str());
219 return theBackupModel->ApplyYourself(aTrack, theNucleus);
223 const G4double cascadeMinEnergyPerNucleon = theInterfaceStore->GetCascadeMinEnergyPerNucleon();
226 && trackKinE < cascadeMinEnergyPerNucleon) {
227 if(!complainedAboutPreCompound) {
228 complainedAboutPreCompound =
true;
229 std::stringstream ss;
230 ss <<
"INCL++ refuses to handle nucleon-induced reactions below "
231 << cascadeMinEnergyPerNucleon / MeV
232 <<
" MeV. A PreCoumpound model ("
233 << thePreCompoundModel->GetModelName()
234 <<
") will be used instead.";
235 theInterfaceStore->EmitBigWarning(ss.str());
237 return thePreCompoundModel->ApplyYourself(aTrack, theNucleus);
241 const G4double theNucleusMass = theIonTable->GetIonMass(nucleusZ, nucleusA);
243 const G4double theTrackEnergy = trackKinE + theTrackMass;
244 const G4double theTrackMomentumAbs2 = theTrackEnergy*theTrackEnergy - theTrackMass*theTrackMass;
245 const G4double theTrackMomentumAbs = ((theTrackMomentumAbs2>0.0) ? std::sqrt(theTrackMomentumAbs2) : 0.0);
250 fourMomentumIn.
setE(theTrackEnergy + theNucleusMass);
251 fourMomentumIn.
setVect(theTrackMomentum);
254 const G4bool inverseKinematics = AccurateProjectile(aTrack, theNucleus);
260 G4Nucleus *theTargetNucleus = &theNucleus;
261 if(inverseKinematics) {
265 if(oldProjectileDef != 0 && oldTargetDef != 0) {
269 if(newTargetA > 0 && newTargetZ > 0) {
271 theTargetNucleus =
new G4Nucleus(newTargetA, newTargetZ, newTargetL);
274 G4DynamicParticle swappedProjectileParticle(oldTargetDef, (*toInverseKinematics) * theProjectile4Momentum);
277 G4String message =
"badly defined target after swapping. Falling back to normal (non-swapped) mode.";
278 theInterfaceStore->EmitWarning(message);
282 G4String message =
"oldProjectileDef or oldTargetDef was null";
283 theInterfaceStore->EmitWarning(message);
318 std::list<G4Fragment> remnants;
320 const G4int maxTries = 200;
328 const G4double kineticEnergy = toINCLKineticEnergy(*aProjectileTrack);
333 const G4INCL::EventInfo eventInfo = theINCLModel->processEvent(theSpecies, kineticEnergy,
336 -theTargetNucleus->
GetL());
343 if(inverseKinematics) {
363 momentum *= toLabFrame;
365 if(inverseKinematics) {
366 momentum *= *toDirectKinematics;
372 fourMomentumOut += momentum;
383 theResult.AddSecondary(secondary);
386 G4String message =
"the model produced a particle that couldn't be converted to Geant4 particle.";
387 theInterfaceStore->EmitWarning(message);
396 if(( Z == 0 &&
S == 0 &&
A > 1 ) ||
397 ( Z == 0 &&
S != 0 &&
A < 4 ) ||
398 ( Z != 0 &&
S != 0 &&
A == Z + std::abs(
S) )) {
399 std::stringstream ss;
400 ss <<
"unphysical residual fragment : Z=" << Z <<
" S=" <<
S <<
" A=" <<
A
401 <<
" skipping it and resampling the collision";
402 theInterfaceStore->EmitWarning(ss.str());
411 eventInfo.
jxRem[i]*hbar_Planck,
412 eventInfo.
jyRem[i]*hbar_Planck,
413 eventInfo.
jzRem[i]*hbar_Planck
424 const G4double scaling = remnant4MomentumScaling(nuclearMass, kinE, px, py, pz);
427 if(std::abs(scaling - 1.0) > 0.01) {
428 std::stringstream ss;
429 ss <<
"momentum scaling = " << scaling
430 <<
"\n Lorentz vector = " << fourMomentum
431 <<
")\n A = " <<
A <<
", Z = " << Z <<
", S = " <<
S
432 <<
"\n E* = " << excitationE <<
", nuclearMass = " << nuclearMass
433 <<
"\n remnant i=" << i <<
", nRemnants=" << eventInfo.
nRemnants
437 <<
", in " << (inverseKinematics ?
"inverse" :
"direct") <<
" kinematics.";
438 theInterfaceStore->EmitWarning(ss.str());
442 fourMomentum *= toLabFrame;
445 if(inverseKinematics) {
446 fourMomentum *= *toDirectKinematics;
450 fourMomentumOut += fourMomentum;
454 if(dumpRemnantInfo) {
455 G4cerr <<
"G4INCLXX_DUMP_REMNANT: " << remnant <<
" spin: " << spin <<
G4endl;
457 remnants.push_back(remnant);
462 const G4int nSecondaries = (
G4int)theResult.GetNumberOfSecondaries();
463 for(
G4int j=0; j<nSecondaries; ++j)
delete theResult.GetSecondary(j)->GetParticle();
485 const G4LorentzVector violation4Momentum = fourMomentumOut - fourMomentumIn;
486 const G4double energyViolation = std::abs(violation4Momentum.
e());
487 const G4double momentumViolation = violation4Momentum.
rho();
489 std::stringstream ss;
490 ss <<
"energy conservation violated by " << energyViolation/MeV <<
" MeV in "
493 <<
" inelastic reaction, in " << (inverseKinematics ?
"inverse" :
"direct") <<
" kinematics. Will resample.";
494 theInterfaceStore->EmitWarning(ss.str());
496 const G4int nSecondaries = (
G4int)theResult.GetNumberOfSecondaries();
497 for(
G4int j=0; j<nSecondaries; ++j)
delete theResult.GetSecondary(j)->GetParticle();
502 std::stringstream ss;
503 ss <<
"momentum conservation violated by " << momentumViolation/MeV <<
" MeV in "
506 <<
" inelastic reaction, in " << (inverseKinematics ?
"inverse" :
"direct") <<
" kinematics. Will resample.";
507 theInterfaceStore->EmitWarning(ss.str());
509 const G4int nSecondaries = (
G4int)theResult.GetNumberOfSecondaries();
510 for(
G4int j=0; j<nSecondaries; ++j)
delete theResult.GetSecondary(j)->GetParticle();
518 }
while(!eventIsOK && nTries < maxTries);
521 if(inverseKinematics) {
522 delete aProjectileTrack;
523 delete theTargetNucleus;
524 delete toInverseKinematics;
525 delete toDirectKinematics;
529 std::stringstream ss;
530 ss <<
"maximum number of tries exceeded for the proposed "
532 <<
" + " << theIonTable->GetIonName(nucleusZ, nucleusA, 0)
533 <<
" inelastic reaction, in " << (inverseKinematics ?
"inverse" :
"direct") <<
" kinematics.";
534 theInterfaceStore->EmitWarning(ss.str());
535 theResult.SetStatusChange(
isAlive);
544 for(std::list<G4Fragment>::iterator i = remnants.begin();
545 i != remnants.end(); ++i) {
548 for(G4ReactionProductVector::iterator fragment = deExcitationResult->begin();
549 fragment != deExcitationResult->end(); ++fragment) {
553 theResult.AddSecondary(theFragment, (*fragment)->GetCreatorModelID());
557 for(G4ReactionProductVector::iterator fragment = deExcitationResult->begin();
558 fragment != deExcitationResult->end(); ++fragment) {
561 deExcitationResult->clear();
562 delete deExcitationResult;
568 if((theTally = theInterfaceStore->GetTally()))
569 theTally->Tally(aTrack, theNucleus, theResult);