80 const EventContext& ctx,
86 CLHEP::HepRandomEngine* randomEngine = m_randomEngine->getEngine(ctx);
87 Generator generator(CLHEP::RandFlat::shoot(randomEngine->flat()));
88 ATH_MSG_VERBOSE(name() <<
" RNG seed " << CLHEP::RandFlat::shoot(randomEngine->flat()));
90 << particles.size() <<
" particles for simulation.");
94 auto bField = std::make_shared<ATLASMagneticFieldWrapper>();
113 simulator.charged.interactions = ActsFatras::makeStandardChargedElectroMagneticInteractions(
m_interact_minPt * Acts::UnitConstants::MeV);
120 ATH_MSG_VERBOSE(name() <<
" Processing particles in ISFParticleVector.");
121 for (
const auto isfp : particles) {
128 ATH_MSG_DEBUG(name() <<
" Convert ISF::Particle(mass) " << isfp->id()<<
"|" << isfp<<
"(" << isfp->mass() <<
")");
129 std::vector<ActsFatras::Particle> input = std::vector<ActsFatras::Particle>{
130 ActsFatras::Particle(ActsFatras::Barcode().withVertexPrimary(0).withParticle(isfp->id()),
static_cast<Acts::PdgParticle
>(isfp->pdgCode()),
131 isfp->charge(),isfp->mass() * Acts::UnitConstants::MeV)
132 .setDirection(Acts::makeDirectionFromPhiEta(isfp->momentum().phi(), isfp->momentum().eta()))
133 .setAbsoluteMomentum(isfp->momentum().mag() * Acts::UnitConstants::MeV)
135 ATH_MSG_DEBUG(name() <<
" Propagating ActsFatras::Particle vertex|particle|generation|subparticle, " << input[0]);
136 std::vector<ActsFatras::Particle> simulatedInitial;
137 std::vector<ActsFatras::Particle> simulatedFinal;
138 std::vector<ActsFatras::Hit> hits;
140 auto result=simulator.simulate(anygctx, mctx, generator, input, simulatedInitial, simulatedFinal, hits);
141 auto simulatedFailure=
result.value();
142 if (simulatedFailure.size()>0){
143 for (
const auto& simfail : simulatedFailure){
144 auto errCode = Acts::make_error_code(Acts::PropagatorError(simfail.error.value()));
145 ATH_MSG_WARNING(name() <<
" Particle id " <<simfail.particle.particleId()<<
": fail to be simulated during Propagation: " << errCode.message());
146 ATH_MSG_WARNING(name() <<
" Particle vertex|particle|generation|subparticle"<<simfail.particle <<
" starts from position" << Acts::toString(simfail.particle.position()) <<
" and direction " << Acts::toString(simfail.particle.direction()));
147 return StatusCode::SUCCESS;
151 ATH_MSG_DEBUG(name() <<
" initial particle " << simulatedInitial[0]);
152 ATH_MSG_DEBUG(name() <<
" ActsFatras simulator hits: " << hits.size());
154 for (
const auto& hit : hits) {
159 ATH_MSG_DEBUG(name() <<
" No. of particles after ActsFatras simulator: " << simulatedFinal.size());
160 if (!simulatedFinal.empty()){
162 auto itr = simulatedFinal.begin();
164 std::vector<ActsFatras::Hit> particle_hits;
165 if (itr->numberOfHits() > 0) {
166 std::copy(hits.begin(), hits.begin()+itr->numberOfHits(), std::back_inserter(particle_hits));
170 auto isKilled = !itr->isAlive();
171 int maxGeneration = simulatedFinal.back().particleId().generation();
173 for (
int gen = 0; gen <= maxGeneration; ++gen){
174 ATH_MSG_DEBUG(name() <<
" start with generation "<< gen <<
"|" << maxGeneration <<
": "<< *itr);
175 auto vecsecisfp = std::make_unique<ISF::ISFParticleVector>();
176 while (itr != simulatedFinal.end() &&
static_cast<int>(itr->particleId().generation()) == gen) {
177 ATH_MSG_DEBUG(name() <<
" genration "<< gen <<
"|" << maxGeneration <<
": "<< *itr);
178 if(itr->isSecondary()){
182 double mass = itr->mass() / Acts::UnitConstants::MeV;
183 double charge = itr->charge();
184 int pdgid = itr->pdg();
189 ATH_MSG_DEBUG(name() <<
" secondaries particle (ACTS): "<<*itr<<
"("<<itr->momentum()<<
")|time "<<itr->time()<<
"|process "<<
getATLASProcessCode(itr->process()));
190 ATH_MSG_DEBUG(name() <<
" secondaries particle (ISF): " << *secisfp <<
" time "<<secisfp->timeStamp());
191 vecsecisfp->push_back(secisfp);
194 ATH_MSG_DEBUG(name() <<
" primary particle found with generation "<< gen);
198 if (!vecsecisfp->empty()) {
210 for (
auto *secisfp : *vecsecisfp){
211 if (secisfp->getTruthBinding()) {
212 secondaries.push_back(secisfp);
215 ATH_MSG_WARNING(
"Secondary particle not written out to truth.\n Parent (" << isfp <<
")\n Secondary (" << *secisfp <<
")");
221 ATH_MSG_VERBOSE(name() <<
" No. of secondaries: " << secondaries.size());
224 std::vector<ActsFatras::Particle>().swap(input);
225 std::vector<ActsFatras::Particle>().swap(simulatedInitial);
226 std::vector<ActsFatras::Particle>().swap(simulatedFinal);
227 std::vector<ActsFatras::Hit>().swap(hits);
229 return StatusCode::SUCCESS;
The generic ISF particle definition,.