File indexing completed on 2024-04-06 12:30:45
0001 #ifndef SimMuon_GEMDigitizer_ME0DigiProducer_h
0002 #define SimMuon_GEMDigitizer_ME0DigiProducer_h
0003
0004 #include "FWCore/Framework/interface/stream/EDProducer.h"
0005 #include "FWCore/Framework/interface/MakerMacros.h"
0006 #include "FWCore/Framework/interface/ESHandle.h"
0007 #include "FWCore/Utilities/interface/ESGetToken.h"
0008 #include "FWCore/Framework/interface/Event.h"
0009 #include "FWCore/Framework/interface/EventSetup.h"
0010 #include "FWCore/Framework/interface/ConsumesCollector.h"
0011 #include "FWCore/ServiceRegistry/interface/Service.h"
0012 #include "FWCore/MessageLogger/interface/MessageLogger.h"
0013 #include "FWCore/ParameterSet/interface/ParameterSet.h"
0014 #include "FWCore/Utilities/interface/RandomNumberGenerator.h"
0015 #include "FWCore/Utilities/interface/Exception.h"
0016
0017 #include "DataFormats/Common/interface/Handle.h"
0018 #include "DataFormats/Common/interface/DetSetVector.h"
0019 #include "SimDataFormats/CrossingFrame/interface/CrossingFrame.h"
0020 #include "SimDataFormats/CrossingFrame/interface/MixCollection.h"
0021 #include "SimDataFormats/TrackingHit/interface/PSimHitContainer.h"
0022 #include "SimDataFormats/GEMDigiSimLink/interface/ME0DigiSimLink.h"
0023
0024 #include "SimMuon/GEMDigitizer/interface/ME0DigiModelFactory.h"
0025 #include "SimMuon/GEMDigitizer/interface/ME0DigiModel.h"
0026
0027 #include "Geometry/Records/interface/MuonGeometryRecord.h"
0028 #include "Geometry/GEMGeometry/interface/ME0Geometry.h"
0029
0030 #include <sstream>
0031 #include <string>
0032 #include <map>
0033 #include <vector>
0034
0035 namespace CLHEP {
0036 class HepRandomEngine;
0037 }
0038
0039 class ME0DigiProducer : public edm::stream::EDProducer<> {
0040 public:
0041 typedef edm::DetSetVector<ME0DigiSimLink> ME0DigiSimLinks;
0042
0043 explicit ME0DigiProducer(const edm::ParameterSet& ps);
0044
0045 ~ME0DigiProducer() override;
0046
0047 void beginRun(const edm::Run&, const edm::EventSetup&) override;
0048
0049 void produce(edm::Event&, const edm::EventSetup&) override;
0050
0051 private:
0052
0053 edm::EDGetTokenT<CrossingFrame<PSimHit> > cf_token;
0054 edm::ESGetToken<ME0Geometry, MuonGeometryRecord> geom_token_;
0055
0056 std::unique_ptr<ME0DigiModel> ME0DigiModel_;
0057 };
0058
0059 ME0DigiProducer::ME0DigiProducer(const edm::ParameterSet& ps)
0060 : ME0DigiModel_{
0061 ME0DigiModelFactory::get()->create("ME0" + ps.getParameter<std::string>("digiModelString") + "Model", ps)} {
0062 produces<ME0DigiCollection>();
0063 produces<ME0DigiSimLinks>("ME0");
0064
0065 edm::Service<edm::RandomNumberGenerator> rng;
0066 if (!rng.isAvailable()) {
0067 throw cms::Exception("Configuration")
0068 << "ME0DigiProducer::ME0DigiProducer() - RandomNumberGeneratorService is not present in configuration file.\n"
0069 << "Add the service in the configuration file or remove the modules that require it.";
0070 }
0071
0072 LogDebug("ME0DigiProducer") << "Using ME0" + ps.getParameter<std::string>("digiModelString") + "Model";
0073
0074 std::string mix_(ps.getParameter<std::string>("mixLabel"));
0075 std::string collection_(ps.getParameter<std::string>("inputCollection"));
0076
0077 cf_token = consumes<CrossingFrame<PSimHit> >(edm::InputTag(mix_, collection_));
0078 geom_token_ = esConsumes<ME0Geometry, MuonGeometryRecord, edm::Transition::BeginRun>();
0079 }
0080
0081 ME0DigiProducer::~ME0DigiProducer() = default;
0082
0083 void ME0DigiProducer::beginRun(const edm::Run&, const edm::EventSetup& eventSetup) {
0084 edm::ESHandle<ME0Geometry> hGeom = eventSetup.getHandle(geom_token_);
0085 ME0DigiModel_->setGeometry(&*hGeom);
0086 ME0DigiModel_->setup();
0087 }
0088
0089 void ME0DigiProducer::produce(edm::Event& e, const edm::EventSetup& eventSetup) {
0090 edm::Service<edm::RandomNumberGenerator> rng;
0091 CLHEP::HepRandomEngine* engine = &rng->getEngine(e.streamID());
0092
0093 edm::Handle<CrossingFrame<PSimHit> > cf;
0094 e.getByToken(cf_token, cf);
0095
0096 MixCollection<PSimHit> hits{cf.product()};
0097
0098
0099 auto digis = std::make_unique<ME0DigiCollection>();
0100 auto me0DigiSimLinks = std::make_unique<ME0DigiSimLinks>();
0101
0102
0103 std::map<uint32_t, edm::PSimHitContainer> hitMap;
0104 for (const auto& hit : hits) {
0105 hitMap[hit.detUnitId()].emplace_back(hit);
0106 }
0107
0108
0109 const auto& etaPartitions(ME0DigiModel_->getGeometry()->etaPartitions());
0110
0111 for (const auto& roll : etaPartitions) {
0112 const ME0DetId detId(roll->id());
0113 const uint32_t rawId(detId.rawId());
0114 const auto& simHits(hitMap[rawId]);
0115
0116 LogDebug("ME0DigiProducer") << "ME0DigiProducer: found " << simHits.size() << " hit(s) in eta partition" << rawId;
0117
0118 ME0DigiModel_->simulateSignal(roll, simHits, engine);
0119 ME0DigiModel_->simulateNoise(roll, engine);
0120 ME0DigiModel_->fillDigis(rawId, *digis);
0121 (*me0DigiSimLinks).insert(ME0DigiModel_->me0DigiSimLinks());
0122 }
0123
0124
0125 e.put(std::move(digis));
0126 e.put(std::move(me0DigiSimLinks), "ME0");
0127 }
0128
0129 DEFINE_FWK_MODULE(ME0DigiProducer);
0130 #endif