23#include <FairRootManager.h>
26#include <TClonesArray.h>
29#include <TStopwatch.h>
38using std::setprecision;
43 std::cout << std::endl;
44 LOG(info) <<
"==========================================================";
45 LOG(info) << GetName() <<
": Initialisation";
48 LOG(info) <<
"CbmRichDigitizer uses TimeBased mode.";
51 LOG(info) <<
"CbmRichDigitizer uses Events mode.";
54 FairRootManager* manager = FairRootManager::Instance();
61 fRichPoints =
static_cast<TClonesArray*
>(manager->GetObject(
"RichPoint"));
62 if (!
fRichPoints) LOG(fatal) <<
"CbmRichDigitizer::Init: No RichPoint array!";
64 fMcTracks =
static_cast<TClonesArray*
>(manager->GetObject(
"MCTrack"));
65 if (!
fMcTracks) LOG(fatal) <<
"CbmRichDigitizer::Init: No MCTrack array!";
74 LOG(error) << GetName() <<
": Error in reading from file! Task will be inactive.";
77 LOG(info) << GetName() <<
": " << std::get<0>(result) <<
" lines read from file, " <<
fInactiveChannels.size()
78 <<
" channels set inactive";
81 LOG(info) << GetName() <<
": Initialisation successful";
82 LOG(info) <<
"==========================================================";
83 std::cout << std::endl;
113 LOG(info) <<
"+ " << setw(15) << GetName() <<
": Event " << setw(6) << right <<
fCurrentEvent <<
" at " << fixed
114 << setprecision(3) <<
fCurrentEventTime <<
" ns, points: " << nPoints <<
", digis: " << nDigis
115 <<
". Exec time " << setprecision(6) << timer.RealTime() <<
" s.";
122 std::cout << std::endl;
123 LOG(info) << GetName() <<
": Finish run";
124 LOG(info) << GetName() <<
": Processing analogue buffers";
129 LOG(info) << GetName() <<
": " << nDigis <<
" digis created and sent to DAQ";
133 std::cout << std::endl;
134 LOG(info) <<
"=====================================";
135 LOG(info) << GetName() <<
": Run summary";
136 LOG(info) <<
"Events processed : " <<
fEventNum;
137 LOG(info) <<
"RichPoint / event : " << setprecision(6) <<
fNofPoints / Double_t(
fEventNum);
141 LOG(info) <<
"=====================================";
151 for (
Int_t iPoint = 0; iPoint < nofRichPoints; iPoint++) {
158 return nofRichPoints;
163 Int_t address = point->GetDetectorID();
165 LOG(error) <<
"CbmRichDigitizer::ProcessPoint: address == -1";
168 Int_t trackId = point->GetTrackID();
169 if (trackId < 0)
return;
171 if (!mcTrack)
return;
174 Bool_t isDetected =
false;
176 if (gcode == 50000050) {
178 point->Momentum(mom);
179 Double_t momTotal = TMath::Sqrt(mom.Px() * mom.Px() + mom.Py() * mom.Py() + mom.Pz() * mom.Pz());
190 CbmLink link(1., pointId, eventNum, inputNum);
192 if (gcode == 50000050 && address > 0)
AddCrossTalk(address, time, link);
206 std::vector<Int_t> directHorizontalPixels =
208 std::vector<Int_t> directVerticalPixels =
212 Double_t crosstalkProbability = 1 - pow(1 -
fCrossTalkProbability[0], directHorizontalPixels.size()) *
215 Int_t crosstalkAddress = -1;
216 if (gRandom->Uniform() < crosstalkProbability) {
224 Double_t rnd = gRandom->Uniform();
225 if (rnd < thHorizontal) {
226 crosstalkAddress = directHorizontalPixels[gRandom->Integer(directHorizontalPixels.size())];
228 else if (rnd < thVertical) {
229 crosstalkAddress = directVerticalPixels[gRandom->Integer(directVerticalPixels.size())];
231 crosstalkAddress = diagonalPixels[gRandom->Integer(diagonalPixels.size())];
243 for (
const Int_t& addr : neighbourAddresses) {
245 Double_t d = TMath::Sqrt((sourcePixelIdx.rem - iPixelIdx.rem) * (sourcePixelIdx.rem - iPixelIdx.rem)
246 + (sourcePixelIdx.quot - iPixelIdx.quot) * (sourcePixelIdx.quot - iPixelIdx.quot));
248 CbmLink link(1., -1, eventNum, inputNum);
257 Double_t nofRichPoints =
fRichPoints->GetEntriesFast();
260 LOG(debug) <<
"CbmRichDigitizer::AddEventNoise NofAllPixels:" << nofPixels <<
" nofNoiseDigis:" << nofNoiseDigis;
262 for (
Int_t j = 0; j < nofNoiseDigis; j++) {
264 CbmLink link(1., -1, eventNum, inputNum);
273 Double_t dT = newEventTime - oldEventTime;
276 LOG(debug) <<
"CbmRichDigitizer::AddDarkRateNoise deltaTime:" << dT <<
" nofPixels:" << nofPixels
277 <<
" nofNoisePixels:" << nofNoisePixels;
279 for (
Int_t j = 0; j < nofNoisePixels; j++) {
282 Double_t time = gRandom->Uniform(oldEventTime, newEventTime);
294 dm.second.begin(), dm.second.end(),
295 [](
const std::pair<Double_t, CbmLink*>& a,
const std::pair<Double_t, CbmLink*>& b) { return a.first < b.first; });
299 auto it = dm.second.begin();
300 for (; it != dm.second.end(); ++it) {
301 Double_t signalTime = it->first;
302 if (processTime >= 0. && signalTime > processTime)
break;
304 Bool_t createsDigi =
true;
308 Double_t lastFiredTime = itFpm->second;
309 if (signalTime - lastFiredTime <
fPixelDeadTime) createsDigi =
false;
320 if (processTime >= 0. && digiTime > maxNewDigiTime)
break;
331 if (digi && digiMatch) digiMatch->
AddLink(*link);
335 dm.second.erase(dm.second.begin(), it);
ClassImp(CbmConverterManager)
Class for producing RICH digis from from MCPoints.
virtual std::pair< size_t, bool > ReadInactiveChannels()
TString fInactiveChannelFileName
std::set< uint32_t > fInactiveChannels
Double_t fCurrentEventTime
void SendData(Double_t time, CbmRichDigi *digi, CbmMatch *match=nullptr)
double GetCharge() const
Charge of the associated particle.
int32_t GetPdgCode() const
void AddLink(const CbmLink &newLink)
void SetTime(double time)
void SetAddress(int32_t address)
Class for producing RICH digis from from MCPoints.
Int_t ProcessBuffers(Double_t processTime)
Process signals in all buffers until processTime. New Digis are only created until processTime - fPix...
virtual void Exec(Option_t *option)
std::map< Int_t, Double_t > fPixelsLastFiredTime
Double_t fDarkRatePerPixel
Int_t ProcessMcEvent()
Process current MC event.
std::map< Int_t, std::vector< std::pair< Double_t, CbmLink * > > > fSignalBuffer
TClonesArray * fRichPoints
std::array< Double_t, 3 > fCrossTalkProbability
Double_t fClusterSignalProbability
void ProcessPoint(CbmRichPoint *point, Int_t pointId, Int_t eventNum, Int_t inputNum)
CbmRichPmtTypeEnum fDetectorType
Double_t fEventNoiseInterval
virtual InitStatus Init()
void AddEventNoise(Int_t eventNum, Int_t inputNum)
Add additional noise for each event based on fEventNoiseRate and fEventNoiseInterval.
void AddCrossTalk(Int_t address, Double_t time, const CbmLink &link)
Add crosstalk assuming fCrossTalkProbability. Only add maximum one cross talk signal per MC point....
void AddSignalToBuffer(Int_t address, Double_t time, const CbmLink &link)
void AddChargedParticleCluster(Int_t address, Double_t time, Int_t eventNum, Int_t inputNum)
Add additional signals to nearby pixels if a charged particle directly passes through the PMT,...
void AddDarkRateNoise(Double_t oldEventTime, Double_t newEventTime)
std::vector< Int_t > GetDirectNeighbourPixels(Int_t address, Bool_t horizontal=true, Bool_t vertical=true)
Return the addresses of the direct neighbour pixels.
Int_t GetRandomPixelAddress()
std::vector< Int_t > GetDiagonalNeighbourPixels(Int_t address)
Return the addresses of the diagonal neighbour pixels.
std::vector< Int_t > GetNxNNeighbourPixels(Int_t address, Int_t n)
Return the addresses of pixels in a (2n+1)*(2n+1) grid, with the address pixel in the center of the g...
std::vector< Int_t > GetPixelAddresses()
static CbmRichGeoHandler & GetInstance()
static CbmRichGeoManager & GetInstance()