23 #include "art_root_io/TFileService.h"
24 #include "art/Framework/Core/ModuleMacros.h"
25 #include "art/Framework/Core/EDProducer.h"
26 #include "art/Framework/Principal/Event.h"
27 #include "art/Framework/Principal/Run.h"
28 #include "art/Framework/Principal/Handle.h"
29 #include "art/Persistency/Common/PtrMaker.h"
30 #include "canvas/Persistency/Common/Assns.h"
31 #include "canvas/Persistency/Common/Ptr.h"
32 #include "canvas/Utilities/InputTag.h"
33 #include "cetlib_except/exception.h"
34 #include "messagefacility/MessageLogger/MessageLogger.h"
35 #include "fhiclcpp/types/Atom.h"
50 namespace icarus {
class PMTWaveformBaselinesFromReadoutConfiguration; }
133 :
public art::EDProducer
145 Name(
"OpticalWaveforms"),
146 Comment(
"label of input digitized optical waveform data product")
150 Name(
"PMTconfigurationTag"),
151 Comment(
"label of PMT readout configuration run-level data product")
155 Name(
"PlotBaselines"),
156 Comment(
"produce plots on the extracted baseline"),
161 Name(
"PrintBaselines"),
162 Comment(
"prints baseline values for each configured channel on each run"),
167 Name(
"OutputCategory"),
168 Comment(
"tag of the module output to console via message facility"),
169 "PMTWaveformBaselinesFromReadoutConfiguration"
188 virtual void beginRun(art::Run& run)
override;
191 virtual void produce(art::Event& event)
override;
203 = std::numeric_limits<Baseline_t>::min();
244 std::pair<unsigned int, std::vector<Baseline_t>>
264 template <
typename BIter,
typename EIter>
265 auto median(BIter
begin, EIter
end) {
267 using value_type =
typename BIter::value_type;
269 std::vector<value_type> data{
begin, end };
270 assert(!data.empty());
272 auto const middle = data.begin() + data.size() / 2;
273 std::nth_element(data.begin(), middle, data.end());
287 : art::EDProducer(config)
290 , fPMTconfigurationTag(config().PMTconfigurationTag())
291 , fPlotBaselines(config().PlotBaselines())
292 , fPrintBaselines(config().PrintBaselines())
303 <<
"Using configured baselines from '" << fPMTconfigurationTag.encode()
304 <<
"', waveform by waveform, on '" << fOpDetWaveformTag.encode() <<
"'.";
309 consumes<sbn::PMTconfiguration, art::InRun>(fPMTconfigurationTag);
310 consumes<std::vector<raw::OpDetWaveform>>(fOpDetWaveformTag);
315 produces<std::vector<icarus::WaveformBaseline>>();
316 produces<art::Assns<icarus::WaveformBaseline, raw::OpDetWaveform>>();
339 std::vector<Baseline_t> newBaselines;
340 std::tie(fConfigured, newBaselines)
341 = extractBaselinesFromConfiguration(
PMTconfig);
343 bool const changed = (fBaselines != newBaselines);
344 fBaselines = std::move(newBaselines);
349 fHBaselines->Fill(
double(channel),
double(
baseline));
353 if (fPrintBaselines && changed) printBaselines();
366 auto const& waveformHandle
367 =
event.getValidHandle<std::vector<raw::OpDetWaveform>>(fOpDetWaveformTag);
368 auto const& waveforms = *waveformHandle;
382 std::vector<icarus::WaveformBaseline> baselines;
383 baselines.reserve(waveforms.size());
385 art::Assns<icarus::WaveformBaseline, raw::OpDetWaveform> baselineToWaveforms;
387 art::PtrMaker<icarus::WaveformBaseline>
const makeBaselinePtr(event);
389 for (
auto const& [ iWaveform, waveform ]:
util::enumerate(waveforms)) {
390 assert(iWaveform == baselines.size());
393 {
static_cast<float>(getBaseline(waveform.ChannelNumber())) };
397 baselineToWaveforms.addSingle(
398 makeBaselinePtr(iWaveform),
399 art::Ptr<raw::OpDetWaveform>(waveformHandle, iWaveform)
409 std::make_unique<std::vector<icarus::WaveformBaseline>>
410 (std::move(baselines))
413 std::make_unique<art::Assns<icarus::WaveformBaseline, raw::OpDetWaveform>>
414 (std::move(baselineToWaveforms))
424 auto const&
tfs = *(art::ServiceHandle<art::TFileService>());
425 auto const& geom = *(lar::providerFrom<geo::Geometry const>());
427 unsigned int const nChannels = geom.NOpChannels();
429 fHBaselines =
tfs.make<TH2F>(
431 "PMT baseline;channel;baseline per channel [ / 8 ADC ]",
432 nChannels, 0.0, double(nChannels),
433 256, 13312.0, 15360.0
444 auto const channelSlot =
static_cast<std::size_t
>(channel);
445 if (channelSlot < fBaselines.size()) {
447 if (baseline != NoBaseline)
return baseline;
449 throw cet::exception(
"PMTWaveformBaselinesFromReadoutConfiguration")
450 <<
"No baseline configured for channel " << channel <<
".\n";
460 -> std::pair<unsigned int, std::vector<Baseline_t>>
464 unsigned int nConfigured = 0U;
465 std::vector<Baseline_t> baselines;
475 if (channelID == NoChannelID)
continue;
477 auto const channelSlot =
static_cast<std::size_t
>(channelID);
478 if (baselines.size() <= channelSlot)
479 baselines.resize(channelSlot + 1U, NoBaseline);
482 if (baseline == NoBaseline) {
486 throw art::Exception(art::errors::LogicError)
487 <<
"A configured baseline actually matches the special value "
488 <<
"`NoBaseline` (" << NoBaseline <<
")\n";
496 return { nConfigured, std::move(baselines) };
506 return fBaselines.size()
507 -
std::count(fBaselines.begin(), fBaselines.end(), NoBaseline);
516 unsigned int const nChannels = nChannelsWithBaseline();
517 assert(nChannels <= fConfigured);
518 unsigned int const nMissing = fConfigured - nChannels;
520 log <<
"Configuration has " << nChannels <<
" channels";
522 log <<
" (plus " << nMissing <<
" not associated to any channel ID)";
525 if (
baseline == NoBaseline)
continue;
526 log <<
"\n channel " << channelID <<
": " <<
baseline;
Utilities related to art service access.
Definition of util::enumerate().
auto enumerate(Iterables &&...iterables)
Range-for loop helper tracking the number of iteration.
Information from the configuration of a V1730 PMT readout board.
Access the description of detector geometry.
auto end(FixedBins< T, C > const &) noexcept
BEGIN_PROLOG vertical distance to the surface Name
Information from the configuration of PMT readout.
Information from the configuration of a V1730 PMT readout board.
auto begin(FixedBins< T, C > const &) noexcept
physics producers discrimopdaq OpticalWaveforms
short signed int baseline
Baseline (BaselineCh<N+1>).
art::ServiceHandle< art::TFileService > tfs
static constexpr auto NoChannelID
Special value for unassigned channel ID.
raw::Channel_t channelID
Offline channel ID.
std::size_t count(Cont const &cont)
std::vector< sbn::V1730channelConfiguration > channels
Configuration of each channel.
Class containing configuration for a V1730 channel.
Class containing configuration for PMT readout.
art framework interface to geometry description
std::vector< sbn::V1730Configuration > boards
Configuration of all PMT readout boards.
Class containing configuration for a V1730 board.