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")<<"DTHitAssociator: WARNING: 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 {
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
00127 edm::Handle<DTRecHitCollection> DTrechits;
00128 LogTrace("DTHitAssociator") <<"getting DTRecHit1DPair collection - "<<DTrechitTag;
00129 iEvent.getByLabel(DTrechitTag,DTrechits);
00130 LogTrace("DTHitAssociator") <<"... size = "<<DTrechits->size();
00131
00132
00133 mapOfRecHit.clear();
00134 DTRecHitCollection::const_iterator rechit;
00135 for(rechit=DTrechits->begin(); rechit!=DTrechits->end(); ++rechit) {
00136 DTWireId wireid = (*rechit).wireId();
00137 mapOfRecHit[wireid].push_back(*rechit);
00138 }
00139
00140 if(dumpDT && printRtS) {
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 DTDigi digi = *hitIT;
00180 edm::LogVerbatim("DTHitAssociator")
00181 <<"DTDigi "<<ihit<<", wire "<<wireid<<", number = "<<hitIT->number()<<", TDC counts = "<<hitIT->countsTDC();
00182 }
00183 }
00184 } else {
00185 LogTrace("DTHitAssociator")<<"\n *** There are NO DTDigi's ***";
00186 }
00187
00188 if (mapOfRecHit.end() != mapOfRecHit.begin())
00189 edm::LogVerbatim("DTHitAssociator")<<"\n *** Analyze DTRecHitCollection by DTWireId ***";
00190
00191 int iwire = 0;
00192 for(RecHitMap::const_iterator mapIT=mapOfRecHit.begin();
00193 mapIT!=mapOfRecHit.end();
00194 ++mapIT , iwire++) {
00195
00196 DTWireId wireid = (*mapIT).first;
00197 edm::LogVerbatim("DTHitAssociator")<<"\n===================================================================";
00198 edm::LogVerbatim("DTHitAssociator")<<"wire index = "<<iwire<<" *** DTWireId = "<<" ("<<wireid<<")";
00199
00200 if(mapOfSimHit.find(wireid) != mapOfSimHit.end()) {
00201 edm::LogVerbatim("DTHitAssociator")<<"\n"<<mapOfSimHit[wireid].size()<<" SimHits (PSimHit):";
00202
00203 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00204 hitIT != mapOfSimHit[wireid].end();
00205 ++hitIT) {
00206 stringstream tId;
00207 tId << (hitIT->first).trackId();
00208 string simhitlog = "\t SimTrack Id = "+tId.str();
00209 if (hitIT->second) simhitlog = simhitlog + "\t -VALID HIT-";
00210 else simhitlog = simhitlog + "\t -not valid hit-";
00211 edm::LogVerbatim("DTHitAssociator")<<simhitlog;
00212 }
00213 }
00214
00215 if(mapOfLinks.find(wireid) != mapOfLinks.end()) {
00216 edm::LogVerbatim("DTHitAssociator")<<"\n"<<mapOfLinks[wireid].size()<<" Links (DTDigiSimLink):";
00217
00218 for (vector<DTDigiSimLink>::const_iterator hitIT = mapOfLinks[wireid].begin();
00219 hitIT != mapOfLinks[wireid].end();
00220 ++hitIT) {
00221 edm::LogVerbatim("DTHitAssociator")
00222 <<"\t digi number = "<<hitIT->number()<<", time = "<<hitIT->time()<<", SimTrackId = "<<hitIT->SimTrackId();
00223 }
00224 }
00225
00226 if(mapOfDigi.find(wireid) != mapOfDigi.end()) {
00227 edm::LogVerbatim("DTHitAssociator")<<"\n"<<mapOfDigi[wireid].size()<<" Digis (DTDigi):";
00228 for (vector<DTDigi>::const_iterator hitIT = mapOfDigi[wireid].begin();
00229 hitIT != mapOfDigi[wireid].end();
00230 ++hitIT) {
00231 edm::LogVerbatim("DTHitAssociator")<<"\t digi number = "<<hitIT->number()<<", time = "<<hitIT->time();
00232 }
00233 }
00234
00235 edm::LogVerbatim("DTHitAssociator")<<"\n"<<(*mapIT).second.size()<<" RecHits (DTRecHit1DPair):";
00236 for(vector<DTRecHit1DPair>::const_iterator vIT =(*mapIT).second.begin();
00237 vIT !=(*mapIT).second.end();
00238 ++vIT) {
00239 edm::LogVerbatim("DTHitAssociator")<<"\t digi time = "<<vIT->digiTime();
00240 }
00241 }
00242 }
00243 }
00244
00245
00246 std::vector<DTHitAssociator::SimHitIdpr> DTHitAssociator::associateHitId(const TrackingRecHit & hit) {
00247
00248 std::vector<SimHitIdpr> simtrackids;
00249 const TrackingRecHit * hitp = &hit;
00250 const DTRecHit1D * dtrechit = dynamic_cast<const DTRecHit1D *>(hitp);
00251
00252 if (dtrechit) {
00253 simtrackids = associateDTHitId(dtrechit);
00254 } else {
00255 edm::LogWarning("DTHitAssociator")<<"*** WARNING in DTHitAssociator::associateHitId, null dynamic_cast !";
00256 }
00257 return simtrackids;
00258 }
00259
00260 std::vector<DTHitAssociator::SimHitIdpr> DTHitAssociator::associateDTHitId(const DTRecHit1D * dtrechit) {
00261
00262 std::vector<SimHitIdpr> matched;
00263
00264 DTWireId wireid = dtrechit->wireId();
00265
00266 if(associatorByWire) {
00267
00268
00269 if(mapOfSimHit.find(wireid) != mapOfSimHit.end()) {
00270 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00271 hitIT != mapOfSimHit[wireid].end();
00272 ++hitIT) {
00273
00274 bool valid_hit = hitIT->second;
00275 PSimHit this_hit = hitIT->first;
00276
00277 if (valid_hit) {
00278 SimHitIdpr currentId(this_hit.trackId(), this_hit.eventId());
00279 matched.push_back(currentId);
00280 }
00281 }
00282 }
00283 }
00284
00285 else {
00286
00287
00288 float theTime = dtrechit->digiTime();
00289 int theNumber(-1);
00290
00291 if (mapOfLinks.find(wireid) != mapOfLinks.end()) {
00292
00293
00294
00295
00296 for (vector<DTDigiSimLink>::const_iterator linkIT = mapOfLinks[wireid].begin();
00297 linkIT != mapOfLinks[wireid].end();
00298 ++linkIT ) {
00299 float digitime = linkIT->time();
00300 if (fabs(digitime-theTime)<0.1) {
00301 theNumber = linkIT->number();
00302 }
00303 }
00304
00305
00306
00307 for (vector<DTDigiSimLink>::const_iterator linkIT = mapOfLinks[wireid].begin();
00308 linkIT != mapOfLinks[wireid].end();
00309 ++linkIT ) {
00310
00311 int digiNr = linkIT->number();
00312 if (digiNr == theNumber) {
00313 SimHitIdpr currentId(linkIT->SimTrackId(), linkIT->eventId());
00314 matched.push_back(currentId);
00315 }
00316 }
00317
00318 } else {
00319 edm::LogError("DTHitAssociator")<<"ERROR in DTHitAssociator::associateDTHitId - DTRecHit1D: "
00320 <<*dtrechit<<" has no associated DTDigiSimLink !"<<endl;
00321 return matched;
00322 }
00323 }
00324
00325 return matched;
00326 }
00327
00328 std::vector<PSimHit> DTHitAssociator::associateHit(const TrackingRecHit & hit) {
00329
00330 std::vector<PSimHit> simhits;
00331 std::vector<SimHitIdpr> simtrackids;
00332
00333 const TrackingRecHit * hitp = &hit;
00334 const DTRecHit1D * dtrechit = dynamic_cast<const DTRecHit1D *>(hitp);
00335
00336 if (dtrechit) {
00337 DTWireId wireid = dtrechit->wireId();
00338
00339 if (associatorByWire) {
00340
00341
00342 if(mapOfSimHit.find(wireid) != mapOfSimHit.end()) {
00343 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00344 hitIT != mapOfSimHit[wireid].end();
00345 ++hitIT) {
00346
00347 bool valid_hit = hitIT->second;
00348 if (valid_hit) simhits.push_back(hitIT->first);
00349 }
00350 }
00351 }
00352 else {
00353
00354
00355 simtrackids = associateDTHitId(dtrechit);
00356
00357 for (vector<SimHitIdpr>::const_iterator idIT = simtrackids.begin(); idIT != simtrackids.end(); ++idIT) {
00358 uint32_t trId = idIT->first;
00359 EncodedEventId evId = idIT->second;
00360
00361 if(mapOfSimHit.find(wireid) != mapOfSimHit.end()) {
00362 for (vector<PSimHit_withFlag>::const_iterator hitIT = mapOfSimHit[wireid].begin();
00363 hitIT != mapOfSimHit[wireid].end();
00364 ++hitIT) {
00365
00366 if (hitIT->first.trackId() == trId &&
00367 hitIT->first.eventId() == evId)
00368 simhits.push_back(hitIT->first);
00369 }
00370 }
00371 }
00372 }
00373
00374 } else {
00375 edm::LogWarning("DTHitAssociator")<<"*** WARNING in DTHitAssociator::associateHit, null dynamic_cast !";
00376 }
00377 return simhits;
00378 }
00379
00380 bool DTHitAssociator::SimHitOK(const edm::ESHandle<DTGeometry> & muongeom,
00381 const PSimHit & simhit) {
00382 bool result = true;
00383
00384 DTWireId wireid(simhit.detUnitId());
00385 const DTLayer* dtlayer = muongeom->layer(wireid.layerId());
00386 LocalPoint entryP = simhit.entryPoint();
00387 LocalPoint exitP = simhit.exitPoint();
00388 const DTTopology &topo = dtlayer->specificTopology();
00389 float xwire = topo.wirePosition(wireid.wire());
00390 float xEntry = entryP.x() - xwire;
00391 float xExit = exitP.x() - xwire;
00392 DTTopology::Side entrySide = topo.onWhichBorder(xEntry,entryP.y(),entryP.z());
00393 DTTopology::Side exitSide = topo.onWhichBorder(xExit,exitP.y(),exitP.z());
00394
00395 bool noParametrisation =
00396 (( entrySide == DTTopology::none || exitSide == DTTopology::none ) ||
00397 (entrySide == exitSide) ||
00398 ((entrySide == DTTopology::xMin && exitSide == DTTopology::xMax) ||
00399 (entrySide == DTTopology::xMax && exitSide == DTTopology::xMin)) );
00400
00401
00402 if (noParametrisation)
00403 {
00404 result = false;
00405 return result;
00406 }
00407
00408 float x;
00409 LocalPoint hitPos = simhit.localPosition();
00410
00411 if(fabs(hitPos.z()) < 0.002) {
00412
00413 x = hitPos.x() - xwire;
00414 } else {
00415 x = xEntry - (entryP.z()*(xExit-xEntry))/(exitP.z()-entryP.z());
00416 }
00417
00418
00419 x *= 10.;
00420 if (fabs(x) > 21.)
00421 result = false;
00422
00423 return result;
00424 }