LArSoft  v09_90_00
Liquid Argon Software toolkit - https://larsoft.org/
SpectrumVolumeGen_module.cc
Go to the documentation of this file.
1 
8 #include <TDatabasePDG.h>
9 #include <TF1.h>
10 #include <TParticlePDG.h>
11 
12 namespace evgen {
15 
17  public:
18  explicit SpectrumVolumeGen(fhicl::ParameterSet const& pset);
19 
20  private:
21  // This is called for each event.
23  int m_pdg;
24  double m_mass;
25  TH1D* m_spectrum;
26  };
27 
28 }
29 
30 namespace evgen {
31 
33  {
34  std::string isotope = "";
35  isotope = pset.get<std::string>("isotope");
36  m_pdg = pset.get<int>("isotope");
37 
38  bool mass_specified = pset.get_if_present<double>("mass", m_mass);
39  if (not mass_specified) {
40  const TDatabasePDG* databasePDG = TDatabasePDG::Instance();
41  const TParticlePDG* definition = databasePDG->GetParticle(m_pdg);
42  // Check that the particle is known to ROOT. If not, this is
43  // not a major error; Geant4 has an internal particle coding
44  // scheme for nuclei that ROOT doesn't recognize.
45  if (definition != 0) { m_mass = definition->Mass(); }
46  else {
47  throw cet::exception("SpectrumVolumeGen") << "Cannot find the particle pdg " << m_pdg;
48  }
49  }
50 
51  m_isotope.push_back(isotope);
52 
53  double min_p = 0, max_p = 0;
54  std::vector<double> bins;
55  bool minmax_mode = pset.get_if_present<double>("spectrum_p_min", min_p);
56  if (minmax_mode) { max_p = pset.get<double>("spectrum_p_max"); }
57  else {
58  bins = pset.get<std::vector<double>>("bins");
59  }
60 
61  std::string function;
62  std::vector<double> parameters;
63  bool have_params;
64  std::vector<double> spectrum;
65  bool func_mode = pset.get_if_present<std::string>("function", function);
66 
67  if (func_mode) {
68  have_params = pset.get_if_present<std::vector<double>>("parameters", parameters);
69  }
70  else {
71  spectrum = pset.get<std::vector<double>>("spectrum");
72  }
73 
74  if (func_mode and minmax_mode) {
75  int nbins = pset.get<int>("nbins");
76  TF1 the_func("spect_func", function.c_str(), min_p, max_p);
77  if (have_params) the_func.SetParameters(parameters.data());
78 
79  m_spectrum = new TH1D("spectrum", ";p [GeV];PDF", nbins, min_p, max_p);
80 
81  for (int ibin = 1; ibin < nbins + 1; ++ibin) {
82  double x = m_spectrum->GetBinCenter(ibin);
83  double y = the_func.Eval(x);
84  if (y < 0) y = 0;
85  m_spectrum->SetBinContent(ibin, y);
86  }
87  }
88  else if (func_mode and not minmax_mode) {
89  if (bins.size() <= 1) {
90  throw cet::exception("SpectrumVolumeGen")
91  << "You need to specify more than 1 bin edge to use the \"bins\" option.";
92  }
93  MF_LOG_WARNING("SpectrumVolumeGen")
94  << "\033[31mYou are using a function and non constant binning...\n"
95  << "Please please please check spectrum and momentum distribution are what you actually "
96  "want!\033[0m\n";
97  int nbins = bins.size() - 1;
98 
99  TF1 the_func("spect_func", function.c_str(), *bins.begin(), *bins.rbegin());
100  if (have_params) the_func.SetParameters(parameters.data());
101 
102  m_spectrum = new TH1D("spectrum", ";p [GeV];PDF", nbins, bins.data());
103 
104  for (int ibin = 1; ibin < nbins + 1; ++ibin) {
105  double x = m_spectrum->GetBinCenter(ibin);
106  double y = the_func.Eval(x);
107  if (y < 0) y = 0;
108  m_spectrum->SetBinContent(ibin, y);
109  }
110  }
111  else if (not func_mode and minmax_mode) {
112  int nbins = spectrum.size();
113 
114  m_spectrum = new TH1D("spectrum", ";p [GeV];PDF", nbins, min_p, max_p);
115  for (int ibin = 1; ibin < nbins + 1; ++ibin) {
116  m_spectrum->SetBinContent(ibin, spectrum.at(ibin - 1));
117  }
118  }
119  else {
120  int nbins = spectrum.size();
121  if ((unsigned)nbins != spectrum.size())
122  throw cet::exception("SpectrumVolumeGen") << "spectrum and bins don't have coherent size!";
123 
124  m_spectrum = new TH1D("spectrum", ";p [GeV];PDF", nbins, bins.data());
125 
126  for (int ibin = 1; ibin < nbins + 1; ++ibin) {
127  m_spectrum->SetBinContent(ibin, spectrum.at(ibin - 1));
128  }
129  }
130 
131  m_spectrum->Scale(1. / m_spectrum->Integral());
132 
134  TH1D* sp = tfs->make<TH1D>(*m_spectrum);
135  (void)sp;
136  }
137 
138  //____________________________________________________________________________
140  {
141 
142  //unique_ptr allows ownership to be transferred to the art::Event after the put statement
143  std::unique_ptr<std::vector<simb::MCTruth>> truthcol(new std::vector<simb::MCTruth>);
144 
145  simb::MCTruth truth;
147  int track_id = -1;
148  const std::string primary_str("primary");
149 
150  int n_decay = GetNDecays();
151 
152  for (int iDecay = 0; iDecay < n_decay; ++iDecay) {
153  TLorentzVector position;
154 
155  if (GetGoodPositionTime(position)) {
156  simb::MCParticle part(track_id, m_pdg, primary_str);
157 
158  TLorentzVector momentum = dirCalc(m_spectrum->GetRandom(), m_mass);
159  part.AddTrajectoryPoint(position, momentum);
160 
161  truth.Add(part);
162  FillHistos(part);
163 
164  track_id--;
165  } // GetGoodPosition
166  } // idecay
167 
168  MF_LOG_DEBUG("SpectrumVolumeGen") << truth;
169  truthcol->push_back(truth);
170  evt.put(std::move(truthcol));
171  }
172 
173  //Calculate an arbitrary direction with a given magnitude p
174 
175 } //end namespace evgen
176 
Float_t x
Definition: compare.C:6
SpectrumVolumeGen(fhicl::ParameterSet const &pset)
void AddTrajectoryPoint(TLorentzVector const &position, TLorentzVector const &momentum)
Definition: MCParticle.h:258
void produce_radio(art::Event &evt)
void SetOrigin(simb::Origin_t origin)
Definition: MCTruth.h:82
Float_t y
Definition: compare.C:6
TLorentzVector dirCalc(double p, double m)
Definition: BaseRadioGen.h:810
void FillHistos(simb::MCParticle &part)
Definition: BaseRadioGen.h:788
PutHandle< PROD > put(std::unique_ptr< PROD > &&edp, std::string const &instance={})
Definition: Event.h:77
TString part[npart]
Definition: Style.C:32
#define DEFINE_ART_MODULE(klass)
Definition: ModuleMacros.h:65
single particles thrown at the detector
Definition: MCTruth.h:26
T get(std::string const &key) const
Definition: ParameterSet.h:314
std::vector< std::string > m_isotope
isotope to simulate. Example: "Ar39"
Definition: BaseRadioGen.h:90
bool GetGoodPositionTime(TLorentzVector &position)
Definition: BaseRadioGen.h:521
void Add(simb::MCParticle const &part)
Definition: MCTruth.h:80
std::optional< T > get_if_present(std::string const &key) const
Definition: ParameterSet.h:267
#define MF_LOG_DEBUG(id)
TCEvent evt
Definition: DataStructs.cxx:8
Event generator information.
Definition: MCTruth.h:32
#define MF_LOG_WARNING(category)
Event Generation using GENIE, cosmics or single particles.
cet::coded_exception< error, detail::translate > exception
Definition: exception.h:33