15 #include <CLHEP/Random/RandGaussQ.h>
16 #include <CLHEP/Random/RandFlat.h>
61 if (
debug)
cout<<
"Creating a DTDigitizer"<<endl;
65 produces<DTDigiCollection>();
67 produces<DTDigiSimLinkCollection>();
99 theConstVDrift = conf_.
getParameter<
double>(
"IdealModelConstantDriftVelocity");
100 else theConstVDrift = 55.;
106 <<
"RandomNumberGeneratorService for DTDigitizer missing in cfg file";
110 MultipleLinks = conf_.
getParameter<
bool>(
"MultipleLinks");
113 LinksTimeWindow = conf_.
getParameter<
double>(
"LinksTimeWindow");
118 cf_token = consumes<CrossingFrame<PSimHit> >(
edm::InputTag(mix_, collection_for_XF) );
137 <<
" Event: " << iEvent.
id().
event() << endl;
148 auto_ptr<MixCollection<PSimHit> >
171 simHit != simHits->end(); simHit++){
175 DTWireId wireId( (*simHit).detUnitId() );
177 wireMap[wireId].push_back(&(*simHit));
180 pair<float,bool>
time(0.,
false);
186 const vector<const PSimHit*> & vhit = (*wire).second;
197 for (vector<const PSimHit*>::const_iterator
hit=vhit.begin();
198 hit != vhit.end();
hit++){
204 time = computeTime(layer, wireId, *
hit, BLoc, engine);
208 tdCont.push_back(make_pair((*
hit),time.first));
210 if (
debug)
cout <<
"hit discarded" << endl;
219 storeDigis(wireId,tdCont,*output,*outputLinks);
228 iEvent.
put(outputLinks);
234 CLHEP::HepRandomEngine* engine){
244 if(
debug)
cout<<
"Hit local entry point: "<<entryP<<endl
245 <<
"Hit local exit point: "<<exitP<<endl;
248 float xEntry = entryP.
x() - xwire;
249 float xExit = exitP.
x() - xwire;
252 <<
" x entry in cell rf: "<<xEntry
253 <<
" x exit in cell rf: "<<xExit<<endl;
258 if (
debug) dumpHit(hit, xEntry, xExit,topo);
261 pair<float,bool> driftTime(0.,
false);
268 if (
debug)
cout <<
" e- hit in gas; discarding " << endl;
281 float cosAlpha = hHat.
dot(pHat);
282 float sinAlpha =
sqrt(1.-cosAlpha*cosAlpha);
283 float radius_P = (d.
mag())/(2.*cosAlpha);
284 float sagitta_P = radius_P*(1.-sinAlpha);
288 float halfd = d.
mag()/2.;
289 float BMag = BLoc.
mag();
291 float radius_B = (pT.
mag()/(0.3*BMag))*100.;
293 if (radius_B > halfd) {
294 sagitta_B = radius_B -
sqrt(radius_B*radius_B - halfd*halfd);
296 sagitta_B = radius_B;
302 if (
debug)
cout <<
" delta = " << delta << endl
303 <<
" cosAlpha = " << cosAlpha << endl
304 <<
" sinAlpha = " << sinAlpha << endl
305 <<
" pMag = " << pT.
mag() << endl
306 <<
" bMag = " << BMag << endl
307 <<
" pT = " << pT << endl
308 <<
" halfd = " << halfd << endl
309 <<
" radius_P (cm) = " << radius_P << endl
310 <<
" sagitta_P (um) = " << sagitta_P*10000. << endl
311 <<
" radius_B (cm) = " << radius_B << endl
312 <<
" sagitta_B (um) = " << sagitta_B*10000. << endl;
315 bool noParametrisation =
317 || (entrySide == exitSide)
325 && (noParametrisation ==
false)) {
326 if (
debug)
cout <<
"*** WARNING: hit is not straight, type = " << partType << endl;
331 if (!noParametrisation) {
344 if(fabs(pt.
z()) < 0.002) {
348 x = xEntry - (entryP.
z()*(xExit-xEntry))/(exitP.
z()-entryP.
z());
351 if(IdealModel)
return make_pair(fabs(x)/theConstVDrift,
true);
352 else driftTime = driftTimeFromParametrization(x, theta, By, Bz, engine);
357 if ((driftTime.second)==
false) {
359 driftTime = driftTimeFromTimeMap();
365 if (driftTime.second) {
366 driftTime.first += externalDelays(layer,wireId,hit);
374 CLHEP::HepRandomEngine* engine)
const {
382 if (
debug)
cout <<
"*** WARNING: parametrisation: x out of range = "
383 << x <<
", skipping" << endl;
384 return pair<float,bool>(0.f,
false);
392 float theta_par =
theta;
396 if (fabs(theta_par)>45.) {
397 if (
debug)
cout <<
"*** WARNING: extrapolating theta > 45: "
401 if (fabs(By_par)>0.75) {
402 if (
debug)
cout <<
"*** WARNING: extrapolating Bnorm > 0.75: "
406 if (fabs(Bz_par)>0.4) {
407 if (
debug)
cout <<
"*** WARNING: extrapolating Bwire >0.4: "
417 cout <<
" Parametrisation: x, theta, Bnorm, Bwire = "
418 << x <<
" " << theta_par <<
" " << By_par <<
" " << Bz_par << endl
423 cout <<
"*** WARNING: call to parametrisation failed" << endl;
424 return pair<float,bool>(0.f,
false);
432 time =
max(time,0.
f);
437 double u = CLHEP::RandGaussQ::shoot(engine, 0., smearing);
440 if (
debug)
cout <<
" drift time = " << time << endl;
442 return pair<float,bool>(
time,
true);
446 CLHEP::HepRandomEngine* engine)
const {
448 double f = sigmaLeft/(sigmaLeft+sigmaRight);
451 if (CLHEP::RandFlat::shoot(engine) <=
f) {
452 t = CLHEP::RandGaussQ::shoot(engine, mean, sigmaLeft);
453 t = mean - fabs(t - mean);
455 t = CLHEP::RandGaussQ::shoot(engine, mean, sigmaRight);
456 t = mean + fabs(t - mean);
458 return static_cast<float>(
t);
464 return pair<float,bool>(0.,
false);
477 float propgL = halfL - wireCoord;
479 float propDelay = propgL/vPropWire;
482 float tof = hit->
tof();
486 double sync= theSync->digitizerOffset(&wireId,layer);
490 cout <<
" propDelay =" << propDelay
492 <<
"; sync= " << sync
496 return propDelay + tof + sync;
513 float wakeTime = -999999.0;
514 float resolTime = -999999.0;
519 for ( TDContainer::const_iterator
hit = hits.begin() ;
hit != hits.end() ;
522 if (onlyMuHits &&
abs((*hit).first->particleType())!=13)
continue;
526 float time = (*hit).second;
527 if ( time > wakeTime ) {
529 int wireN = wireId.
wire();
531 digi =
DTDigi(wireN, time, digiN);
534 unsigned int SimTrackId = (*hit).first->trackId();
536 DTDigiSimLink digisimLink(wireN, digiN, time, SimTrackId, evId);
539 cout<<endl<<
"---- DTDigitizer ----"<<endl;
540 cout<<
"wireId: "<<wireId<<endl;
541 cout<<
"sim. time = "<<time<<endl;
542 cout<<
"digi number = "<< digi.
number()<<
", digi time = "<<digi.
time()
543 <<
", linked to SimTrack Id = "<<SimTrackId<<endl;
549 output.insertDigi(layerID, digi);
551 wakeTime = time + deadTime;
552 resolTime = time + LinksTimeWindow;
558 else if (MultipleLinks && time < resolTime){
559 int wireN = wireId.
wire();
560 unsigned int SimTrackId = (*hit).first->trackId();
562 DTDigiSimLink digisimLink(wireN, digiN, time, SimTrackId, evId);
567 cout<<
"\nAdded multiple link: \n"
568 <<
"digi number = "<<digi.
number()<<
", digi time = "<<digi.
time()<<
" (sim. time = "<<time<<
")"
569 <<
", linked to SimTrack Id = "<<SimTrackId<<endl;
577 float xEntry,
float xExit,
588 <<
"------- SimHit: " << endl
590 <<
" process type = " << hit->
processType() << endl
591 <<
" process type = " << hit->
processType() << endl
593 <<
" trackId = " << hit->
trackId() << endl
595 <<
" |p| = " << hit->
pabs() << endl
596 <<
" Energy loss = " << hit->
energyLoss() << endl
601 <<
" Entry point = " << entryP <<
" cell x = " << xEntry << endl
602 <<
" Exit point = " << exitP <<
" cell x = " << xExit << endl
603 <<
" DR = = " << (exitP-entryP).
mag() << endl
604 <<
" Dx = = " << (exitP-entryP).
x() << endl
607 <<
" , " << topo.
cellLenght() <<
") cm" << endl
608 <<
" DY entry from edge = " << topo.
cellLenght()/2.-fabs(entryP.
y())
609 <<
" DY exit from edge = " << topo.
cellLenght()/2.-fabs(exitP.
y())
610 <<
" entrySide = " << (
int)entrySide
611 <<
" ; exitSide = " << (int)exitSide << endl;
std::pair< float, bool > computeTime(const DTLayer *layer, const DTWireId &wireId, const PSimHit *hit, const LocalVector &BLoc, CLHEP::HepRandomEngine *)
GlobalPoint toGlobal(const Point2DBase< Scalar, LocalTag > lp) const
T getParameter(std::string const &) const
EventNumber_t event() const
T getUntrackedParameter(std::string const &, T const &) const
void dumpHit(const PSimHit *hit, float xEntry, float xExit, const DTTopology &topo)
float wirePosition(int wireNumber) const
Returns the x position in the layer of a given wire number.
float tof() const
deprecated name for timeOfFlight()
Side onWhichBorder(float x, float y, float z) const
LocalVector momentumAtEntry() const
The momentum of the track that produced the hit, at entry point.
bool getByToken(EDGetToken token, Handle< PROD > &result) const
T mag() const
The vector magnitude. Equivalent to sqrt(vec.mag2())
Geom::Theta< T > theta() const
float cellWidth() const
Returns the cell width.
PreciseFloatType< T, U >::Type dot(const Vector3DBase< U, FrameTag > &v) const
void insertDigi(const IndexType &index, const DigiType &digi)
insert a digi for a given DetUnit
const Plane & surface() const
The nominal surface of the GeomDet.
const DTTopology & specificTopology() const
double time() const
Get time in ns.
Local3DPoint exitPoint() const
Exit point in the local Det frame.
void storeDigis(DTWireId &wireId, TDContainer &hits, DTDigiCollection &output, DTDigiSimLinkCollection &outputLinks)
Local3DPoint localPosition() const
OrphanHandle< PROD > put(std::auto_ptr< PROD > product)
Put a new product.
LocalPoint toLocal(const GlobalPoint &gp) const
Vector3DBase< typename PreciseFloatType< T, U >::Type, FrameTag > cross(const Vector3DBase< U, FrameTag > &v) const
Abs< T >::type abs(const T &t)
DTDigitizer(const edm::ParameterSet &)
float cellHeight() const
Returns the cell height.
float pabs() const
fast and more accurate access to momentumAtEntry().mag()
DTWireIdMap::const_iterator DTWireIdMapConstIter
uint32_t countsTDC() const
Get raw TDC count.
LocalVector localDirection() const
Obsolete. Same as momentumAtEntry().unit(), for backward compatibility.
int wire() const
Return the wire number.
Vector3DBase unit() const
unsigned short MB_DT_drift_time(double x, double alpha, double by, double bz, short ifl, drift_time *DT, short interpolate) const
Calculate drift time and spread.
std::pair< float, bool > driftTimeFromParametrization(float x, float alpha, float By, float Bz, CLHEP::HepRandomEngine *) const
T const * product() const
virtual CLHEP::HepRandomEngine & getEngine(StreamID const &) const =0
Use this engine in event methods.
unsigned short processType() const
std::vector< hitAndT > TDContainer
Structure used to return output values.
DTLayerId layerId() const
Return the corresponding LayerId.
float energyLoss() const
The energy deposit in the PSimHit, in ???.
MuonDigiCollection< DTLayerId, DTDigi > DTDigiCollection
int number() const
Identifies different digis within the same.
StreamID streamID() const
unsigned int trackId() const
float externalDelays(const DTLayer *layer, const DTWireId &wireId, const PSimHit *hit) const
virtual void produce(edm::Event &, const edm::EventSetup &)
MuonDigiCollection< DTLayerId, DTDigiSimLink > DTDigiSimLinkCollection
std::pair< float, bool > driftTimeFromTimeMap() const
Local3DPoint entryPoint() const
Entry point in the local Det frame.
std::map< DTWireId, std::vector< const PSimHit * > > DTWireIdMap
Power< A, B >::type pow(const A &a, const B &b)
float asymGausSmear(double mean, double sigmaLeft, double sigmaRight, CLHEP::HepRandomEngine *) const
T get(const Candidate &c)
EventID const & max(EventID const &lh, EventID const &rh)