00001 #include "SimMuon/MCTruth/interface/DTHitAssociator.h"
00002 #include "SimDataFormats/CrossingFrame/interface/CrossingFrame.h"
00003 #include "SimDataFormats/CrossingFrame/interface/MixCollection.h"
00004 #include "DataFormats/DetId/interface/DetId.h"
00005 #include "DataFormats/MuonDetId/interface/MuonSubdetId.h"
00006 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00007 #include "Geometry/Records/interface/MuonGeometryRecord.h"
00008 #include "Geometry/DTGeometry/interface/DTLayer.h"
00009 #include "Geometry/DTGeometry/interface/DTTopology.h"
00010 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00011 #include <string>
00012 #include <sstream>
00013
00014 using namespace std;
00015
00016
00017 DTHitAssociator::DTHitAssociator(const edm::Event& iEvent, const edm::EventSetup& iSetup, const edm::ParameterSet& conf, bool printRtS):
00018
00019
00020 DTsimhitsTag(conf.getParameter<edm::InputTag>("DTsimhitsTag")),
00021 DTsimhitsXFTag(conf.getParameter<edm::InputTag>("DTsimhitsXFTag")),
00022 DTdigiTag(conf.getParameter<edm::InputTag>("DTdigiTag")),
00023 DTdigisimlinkTag(conf.getParameter<edm::InputTag>("DTdigisimlinkTag")),
00024 DTrechitTag(conf.getParameter<edm::InputTag>("DTrechitTag")),
00025
00026
00027 dumpDT(conf.getParameter<bool>("dumpDT")),
00028
00029 crossingframe(conf.getParameter<bool>("crossingframe")),
00030
00031 links_exist(conf.getParameter<bool>("links_exist")),
00032
00033 associatorByWire(conf.getParameter<bool>("associatorByWire")),
00034
00035 printRtS(true)
00036
00037 {
00038 LogTrace("DTHitAssociator") <<"DTHitAssociator constructor: dumpDT = "<<dumpDT
00039 <<", crossingframe = "<<crossingframe<<", links_exist = "<<links_exist
00040 <<", associatorByWire = "<<associatorByWire;
00041
00042 if (!links_exist && !associatorByWire) {
00043 edm::LogWarning("DTHitAssociator")<<"*** WARNING in DTHitAssociator::DTHitAssociator: associatorByWire reset to TRUE !"
00044 <<" \t (missing DTDigiSimLinkCollection ?)";
00045 associatorByWire = true;
00046 }
00047
00048
00049 edm::ESHandle<DTGeometry> muonGeom;
00050 iSetup.get<MuonGeometryRecord>().get(muonGeom);
00051
00052
00053 mapOfSimHit.clear();
00054 bool takeHit(true);
00055
00056 if (crossingframe) {
00057 edm::Handle<CrossingFrame<PSimHit> > xFrame;
00058 LogTrace("DTHitAssociator") <<"getting CrossingFrame<PSimHit> collection - "<<DTsimhitsXFTag;
00059 iEvent.getByLabel(DTsimhitsXFTag,xFrame);
00060 auto_ptr<MixCollection<PSimHit> >
00061 DTsimhits( new MixCollection<PSimHit>(xFrame.product()) );
00062 LogTrace("DTHitAssociator") <<"... size = "<<DTsimhits->size();
00063 MixCollection<PSimHit>::MixItr isimhit;
00064 for (isimhit=DTsimhits->begin(); isimhit!= DTsimhits->end(); isimhit++) {
00065 DTWireId wireid((*isimhit).detUnitId());
00066 takeHit = SimHitOK(muonGeom, *isimhit);
00067 mapOfSimHit[wireid].push_back(make_pair(*isimhit,takeHit));
00068 }
00069 }
00070 else if (!DTsimhitsTag.label().empty()) {
00071 edm::Handle<edm::PSimHitContainer> DTsimhits;
00072 LogTrace("DTHitAssociator") <<"getting PSimHit collection - "<<DTsimhitsTag;
00073 iEvent.getByLabel(DTsimhitsTag,DTsimhits);
00074 LogTrace("DTHitAssociator") <<"... size = "<<DTsimhits->size();
00075 edm::PSimHitContainer::const_iterator isimhit;
00076 for (isimhit=DTsimhits->begin(); isimhit!= DTsimhits->end(); isimhit++) {
00077 DTWireId wireid((*isimhit).detUnitId());
00078 takeHit = SimHitOK(muonGeom, *isimhit);
00079 mapOfSimHit[wireid].push_back(make_pair(*isimhit,takeHit));
00080 }
00081 }
00082
00083
00084 mapOfDigi.clear();
00085 edm::Handle<DTDigiCollection> digis;
00086 LogTrace("DTHitAssociator") <<"getting DTDigi collection - "<<DTdigiTag;
00087 iEvent.getByLabel(DTdigiTag,digis);
00088
00089 if (digis.isValid()) {
00090
00091 for (DTDigiCollection::DigiRangeIterator detUnit=digis->begin(); detUnit !=digis->end(); ++detUnit) {
00092 const DTLayerId& layerid = (*detUnit).first;
00093 const DTDigiCollection::Range& range = (*detUnit).second;
00094
00095 DTDigiCollection::const_iterator digi;
00096 for (digi = range.first; digi != range.second; ++digi){
00097 DTWireId wireid(layerid,(*digi).wire());
00098 mapOfDigi[wireid].push_back(*digi);
00099 }
00100 }
00101 } else {
00102 LogTrace("DTHitAssociator") <<"... NO DTDigi collection found !";
00103 }
00104
00105 mapOfLinks.clear();
00106 if (links_exist) {
00107
00108 edm::Handle<DTDigiSimLinkCollection> digisimlinks;
00109 LogTrace("DTHitAssociator") <<"getting DTDigiSimLink collection - "<<DTdigisimlinkTag;
00110 iEvent.getByLabel(DTdigisimlinkTag,digisimlinks);
00111
00112 for (DTDigiSimLinkCollection::DigiRangeIterator detUnit=digisimlinks->begin();
00113 detUnit !=digisimlinks->end();
00114 ++detUnit) {
00115 const DTLayerId& layerid = (*detUnit).first;
00116 const DTDigiSimLinkCollection::Range& range = (*detUnit).second;
00117
00118 DTDigiSimLinkCollection::const_iterator link;
00119 for (link=range.first; link!=range.second; ++link){
00120 DTWireId wireid(layerid,(*link).wire());
00121 mapOfLinks[wireid].push_back(*link);
00122 }
00123 }
00124 }
00125
00126 if(dumpDT && printRtS) {
00127
00128
00129 edm::Handle<DTRecHitCollection> DTrechits;
00130 LogTrace("DTHitAssociator") <<"getting DTRecHit1DPair collection - "<<DTrechitTag;
00131 iEvent.getByLabel(DTrechitTag,DTrechits);
00132 LogTrace("DTHitAssociator") <<"... size = "<<DTrechits->size();
00133
00134
00135 mapOfRecHit.clear();
00136 DTRecHitCollection::const_iterator rechit;
00137 for(rechit=DTrechits->begin(); rechit!=DTrechits->end(); ++rechit) {
00138 DTWireId wireid = (*rechit).wireId();
00139 mapOfRecHit[wireid].push_back(*rechit);
00140 }
00141
00142 if (mapOfSimHit.end() != mapOfSimHit.begin()) {
00143 edm::LogVerbatim("DTHitAssociator")<<"\n *** Dump DT PSimHit's ***";
00144
00145 int jwire = 0;
00146 int ihit = 0;
00147
00148 for(SimHitMap::const_iterator mapIT=mapOfSimHit.begin();
00149 mapIT!=mapOfSimHit.end();
00150 ++mapIT , jwire++) {
00151
00152 DTWireId wireid = (*mapIT).first;
00153 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00154 hitIT != mapOfSimHit[wireid].end();
00155 hitIT++ , ihit++) {
00156 PSimHit hit = hitIT->first;
00157 edm::LogVerbatim("DTHitAssociator")
00158 <<"PSimHit "<<ihit <<", wire "<<wireid
00159 <<", SimTrack Id:"<<hit.trackId()<<"/Evt:(" <<hit.eventId().event()<<","<<hit.eventId().bunchCrossing()<<") "
00160 <<", pdg = "<<hit.particleType()<<", procs = "<<hit.processType();
00161 }
00162 }
00163 } else {
00164 edm::LogVerbatim("DTHitAssociator")<<"\n *** There are NO DT PSimHit's ***";
00165 }
00166
00167 if(mapOfDigi.end() != mapOfDigi.begin()) {
00168
00169 int jwire = 0;
00170 int ihit = 0;
00171
00172 for(DigiMap::const_iterator mapIT=mapOfDigi.begin(); mapIT!=mapOfDigi.end(); ++mapIT , jwire++) {
00173 edm::LogVerbatim("DTHitAssociator")<<"\n *** Dump DT digis ***";
00174
00175 DTWireId wireid = (*mapIT).first;
00176 for (vector<DTDigi>::const_iterator hitIT = mapOfDigi[wireid].begin();
00177 hitIT != mapOfDigi[wireid].end();
00178 hitIT++ , ihit++) {
00179 edm::LogVerbatim("DTHitAssociator")
00180 <<"DTDigi "<<ihit<<", wire "<<wireid<<", number = "<<hitIT->number()<<", TDC counts = "<<hitIT->countsTDC();
00181 }
00182 }
00183 } else {
00184 LogTrace("DTHitAssociator")<<"\n *** There are NO DTDigi's ***";
00185 }
00186
00187 if (mapOfRecHit.end() != mapOfRecHit.begin())
00188 edm::LogVerbatim("DTHitAssociator")<<"\n *** Analyze DTRecHitCollection by DTWireId ***";
00189
00190 int iwire = 0;
00191 for(RecHitMap::const_iterator mapIT=mapOfRecHit.begin();
00192 mapIT!=mapOfRecHit.end();
00193 ++mapIT , iwire++) {
00194
00195 DTWireId wireid = (*mapIT).first;
00196 edm::LogVerbatim("DTHitAssociator")<<"\n===================================================================";
00197 edm::LogVerbatim("DTHitAssociator")<<"wire index = "<<iwire<<" *** DTWireId = "<<" ("<<wireid<<")";
00198
00199 if(mapOfSimHit.find(wireid) != mapOfSimHit.end()) {
00200 edm::LogVerbatim("DTHitAssociator")<<"\n"<<mapOfSimHit[wireid].size()<<" SimHits (PSimHit):";
00201
00202 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00203 hitIT != mapOfSimHit[wireid].end();
00204 ++hitIT) {
00205 stringstream tId;
00206 tId << (hitIT->first).trackId();
00207 string simhitlog = "\t SimTrack Id = "+tId.str();
00208 if (hitIT->second) simhitlog = simhitlog + "\t -VALID HIT-";
00209 else simhitlog = simhitlog + "\t -not valid hit-";
00210 edm::LogVerbatim("DTHitAssociator")<<simhitlog;
00211 }
00212 }
00213
00214 if(mapOfLinks.find(wireid) != mapOfLinks.end()) {
00215 edm::LogVerbatim("DTHitAssociator")<<"\n"<<mapOfLinks[wireid].size()<<" Links (DTDigiSimLink):";
00216
00217 for (vector<DTDigiSimLink>::const_iterator hitIT = mapOfLinks[wireid].begin();
00218 hitIT != mapOfLinks[wireid].end();
00219 ++hitIT) {
00220 edm::LogVerbatim("DTHitAssociator")
00221 <<"\t digi number = "<<hitIT->number()<<", time = "<<hitIT->time()<<", SimTrackId = "<<hitIT->SimTrackId();
00222 }
00223 }
00224
00225 if(mapOfDigi.find(wireid) != mapOfDigi.end()) {
00226 edm::LogVerbatim("DTHitAssociator")<<"\n"<<mapOfDigi[wireid].size()<<" Digis (DTDigi):";
00227 for (vector<DTDigi>::const_iterator hitIT = mapOfDigi[wireid].begin();
00228 hitIT != mapOfDigi[wireid].end();
00229 ++hitIT) {
00230 edm::LogVerbatim("DTHitAssociator")<<"\t digi number = "<<hitIT->number()<<", time = "<<hitIT->time();
00231 }
00232 }
00233
00234 edm::LogVerbatim("DTHitAssociator")<<"\n"<<(*mapIT).second.size()<<" RecHits (DTRecHit1DPair):";
00235 for(vector<DTRecHit1DPair>::const_iterator vIT =(*mapIT).second.begin();
00236 vIT !=(*mapIT).second.end();
00237 ++vIT) {
00238 edm::LogVerbatim("DTHitAssociator")<<"\t digi time = "<<vIT->digiTime();
00239 }
00240 }
00241 }
00242 }
00243
00244
00245 std::vector<DTHitAssociator::SimHitIdpr> DTHitAssociator::associateHitId(const TrackingRecHit & hit) {
00246
00247 std::vector<SimHitIdpr> simtrackids;
00248 const TrackingRecHit * hitp = &hit;
00249 const DTRecHit1D * dtrechit = dynamic_cast<const DTRecHit1D *>(hitp);
00250
00251 if (dtrechit) {
00252 simtrackids = associateDTHitId(dtrechit);
00253 } else {
00254 edm::LogWarning("DTHitAssociator")<<"*** WARNING in DTHitAssociator::associateHitId, null dynamic_cast !";
00255 }
00256 return simtrackids;
00257 }
00258
00259 std::vector<DTHitAssociator::SimHitIdpr> DTHitAssociator::associateDTHitId(const DTRecHit1D * dtrechit) {
00260
00261 std::vector<SimHitIdpr> matched;
00262
00263 DTWireId wireid = dtrechit->wireId();
00264
00265 if(associatorByWire) {
00266
00267
00268 if(mapOfSimHit.find(wireid) != mapOfSimHit.end()) {
00269 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00270 hitIT != mapOfSimHit[wireid].end();
00271 ++hitIT) {
00272
00273 bool valid_hit = hitIT->second;
00274 PSimHit this_hit = hitIT->first;
00275
00276 if (valid_hit) {
00277 SimHitIdpr currentId(this_hit.trackId(), this_hit.eventId());
00278 matched.push_back(currentId);
00279 }
00280 }
00281 }
00282 }
00283
00284 else {
00285
00286
00287 float theTime = dtrechit->digiTime();
00288 int theNumber(-1);
00289
00290 if (mapOfLinks.find(wireid) != mapOfLinks.end()) {
00291
00292
00293
00294
00295 for (vector<DTDigiSimLink>::const_iterator linkIT = mapOfLinks[wireid].begin();
00296 linkIT != mapOfLinks[wireid].end();
00297 ++linkIT ) {
00298 float digitime = linkIT->time();
00299 if (fabs(digitime-theTime)<0.1) {
00300 theNumber = linkIT->number();
00301 }
00302 }
00303
00304
00305
00306 for (vector<DTDigiSimLink>::const_iterator linkIT = mapOfLinks[wireid].begin();
00307 linkIT != mapOfLinks[wireid].end();
00308 ++linkIT ) {
00309
00310 int digiNr = linkIT->number();
00311 if (digiNr == theNumber) {
00312 SimHitIdpr currentId(linkIT->SimTrackId(), linkIT->eventId());
00313 matched.push_back(currentId);
00314 }
00315 }
00316
00317 } else {
00318 edm::LogError("DTHitAssociator")<<"*** ERROR in DTHitAssociator::associateDTHitId - DTRecHit1D: "
00319 <<*dtrechit<<" has no associated DTDigiSimLink !"<<endl;
00320 return matched;
00321 }
00322 }
00323
00324 return matched;
00325 }
00326
00327 std::vector<PSimHit> DTHitAssociator::associateHit(const TrackingRecHit & hit) {
00328
00329 std::vector<PSimHit> simhits;
00330 std::vector<SimHitIdpr> simtrackids;
00331
00332 const TrackingRecHit * hitp = &hit;
00333 const DTRecHit1D * dtrechit = dynamic_cast<const DTRecHit1D *>(hitp);
00334
00335 if (dtrechit) {
00336 DTWireId wireid = dtrechit->wireId();
00337
00338 if (associatorByWire) {
00339
00340
00341 if(mapOfSimHit.find(wireid) != mapOfSimHit.end()) {
00342 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00343 hitIT != mapOfSimHit[wireid].end();
00344 ++hitIT) {
00345
00346 bool valid_hit = hitIT->second;
00347 if (valid_hit) simhits.push_back(hitIT->first);
00348 }
00349 }
00350 }
00351 else {
00352
00353
00354 simtrackids = associateDTHitId(dtrechit);
00355
00356 for (vector<SimHitIdpr>::const_iterator idIT = simtrackids.begin(); idIT != simtrackids.end(); ++idIT) {
00357 uint32_t trId = idIT->first;
00358 EncodedEventId evId = idIT->second;
00359
00360 if(mapOfSimHit.find(wireid) != mapOfSimHit.end()) {
00361 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00362 hitIT != mapOfSimHit[wireid].end();
00363 ++hitIT) {
00364
00365 if (hitIT->first.trackId() == trId &&
00366 hitIT->first.eventId() == evId)
00367 simhits.push_back(hitIT->first);
00368 }
00369 }
00370 }
00371 }
00372
00373 } else {
00374 edm::LogWarning("DTHitAssociator")<<"*** WARNING in DTHitAssociator::associateHit, null dynamic_cast !";
00375 }
00376 return simhits;
00377 }
00378
00379 bool DTHitAssociator::SimHitOK(const edm::ESHandle<DTGeometry> & muongeom,
00380 const PSimHit & simhit) {
00381 bool result = true;
00382
00383 DTWireId wireid(simhit.detUnitId());
00384 const DTLayer* dtlayer = muongeom->layer(wireid.layerId());
00385 LocalPoint entryP = simhit.entryPoint();
00386 LocalPoint exitP = simhit.exitPoint();
00387 const DTTopology &topo = dtlayer->specificTopology();
00388 float xwire = topo.wirePosition(wireid.wire());
00389 float xEntry = entryP.x() - xwire;
00390 float xExit = exitP.x() - xwire;
00391 DTTopology::Side entrySide = topo.onWhichBorder(xEntry,entryP.y(),entryP.z());
00392 DTTopology::Side exitSide = topo.onWhichBorder(xExit,exitP.y(),exitP.z());
00393
00394 bool noParametrisation =
00395 (( entrySide == DTTopology::none || exitSide == DTTopology::none ) ||
00396 (entrySide == exitSide) ||
00397 ((entrySide == DTTopology::xMin && exitSide == DTTopology::xMax) ||
00398 (entrySide == DTTopology::xMax && exitSide == DTTopology::xMin)) );
00399
00400
00401 if (noParametrisation)
00402 {
00403 result = false;
00404 return result;
00405 }
00406
00407 float x;
00408 LocalPoint hitPos = simhit.localPosition();
00409
00410 if(fabs(hitPos.z()) < 0.002) {
00411
00412 x = hitPos.x() - xwire;
00413 } else {
00414 x = xEntry - (entryP.z()*(xExit-xEntry))/(exitP.z()-entryP.z());
00415 }
00416
00417
00418 x *= 10.;
00419 if (fabs(x) > 21.)
00420 result = false;
00421
00422 return result;
00423 }