00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include "Geometry/Records/interface/CaloGeometryRecord.h"
00021 #include "TrackingTools/TrackAssociator/interface/TrackDetectorAssociator.h"
00022 #include "TrackingTools/TrajectoryState/interface/TrajectoryStateTransform.h"
00023
00024
00025 #include "FWCore/Framework/interface/Frameworkfwd.h"
00026
00027 #include "FWCore/Framework/interface/Event.h"
00028 #include "FWCore/Framework/interface/EventSetup.h"
00029 #include "FWCore/Framework/interface/MakerMacros.h"
00030 #include "DataFormats/Common/interface/Handle.h"
00031 #include "FWCore/Framework/interface/ESHandle.h"
00032 #include "DataFormats/Common/interface/OrphanHandle.h"
00033
00034 #include "DataFormats/TrackReco/interface/Track.h"
00035 #include "DataFormats/TrackReco/interface/TrackExtra.h"
00036 #include "DataFormats/CaloTowers/interface/CaloTower.h"
00037 #include "DataFormats/CaloTowers/interface/CaloTowerCollection.h"
00038 #include "DataFormats/HcalRecHit/interface/HcalRecHitCollections.h"
00039 #include "DataFormats/EgammaReco/interface/SuperCluster.h"
00040 #include "DataFormats/DTRecHit/interface/DTRecHitCollection.h"
00041 #include "DataFormats/EcalDetId/interface/EBDetId.h"
00042 #include "DataFormats/DetId/interface/DetId.h"
00043
00044
00045 #include "Geometry/CaloGeometry/interface/CaloGeometry.h"
00046 #include "Geometry/CaloGeometry/interface/CaloSubdetectorGeometry.h"
00047 #include "Geometry/CaloGeometry/interface/CaloCellGeometry.h"
00048 #include "DataFormats/EcalDetId/interface/EcalSubdetector.h"
00049 #include "DataFormats/HcalDetId/interface/HcalSubdetector.h"
00050 #include "DataFormats/EcalRecHit/interface/EcalRecHitCollections.h"
00051
00052 #include "Geometry/DTGeometry/interface/DTLayer.h"
00053 #include "Geometry/DTGeometry/interface/DTGeometry.h"
00054 #include "Geometry/Records/interface/MuonGeometryRecord.h"
00055
00056 #include "Geometry/CSCGeometry/interface/CSCGeometry.h"
00057 #include "Geometry/CSCGeometry/interface/CSCChamberSpecs.h"
00058
00059 #include "DataFormats/GeometrySurface/interface/Cylinder.h"
00060 #include "DataFormats/GeometrySurface/interface/Plane.h"
00061
00062 #include "Geometry/CommonDetUnit/interface/GeomDetUnit.h"
00063
00064
00065 #include "MagneticField/Engine/interface/MagneticField.h"
00066 #include "MagneticField/Records/interface/IdealMagneticFieldRecord.h"
00067
00068 #include "TrackPropagation/SteppingHelixPropagator/interface/SteppingHelixPropagator.h"
00069 #include "Utilities/Timing/interface/TimingReport.h"
00070 #include <stack>
00071 #include <set>
00072
00073 #include "DataFormats/Math/interface/LorentzVector.h"
00074 #include "Math/VectorUtil.h"
00075 #include <algorithm>
00076
00077 #include "TrackingTools/TrackAssociator/interface/DetIdAssociator.h"
00078 #include "TrackingTools/TrackAssociator/interface/DetIdInfo.h"
00079
00080
00081
00082
00083
00084 #include "DataFormats/DTRecHit/interface/DTRecSegment4DCollection.h"
00085 #include "DataFormats/DTRecHit/interface/DTRecSegment2D.h"
00086 #include "DataFormats/CSCRecHit/interface/CSCSegmentCollection.h"
00087 #include "DataFormats/GeometryCommonDetAlgo/interface/ErrorFrameTransformer.h"
00088
00089 #include "SimDataFormats/TrackingHit/interface/PSimHit.h"
00090 #include "SimDataFormats/TrackingHit/interface/PSimHitContainer.h"
00091 #include "SimDataFormats/Track/interface/SimTrack.h"
00092 #include "SimDataFormats/Track/interface/SimTrackContainer.h"
00093 #include "SimDataFormats/Vertex/interface/SimVertex.h"
00094 #include "SimDataFormats/Vertex/interface/SimVertexContainer.h"
00095 #include "SimDataFormats/CaloHit/interface/PCaloHit.h"
00096 #include "SimDataFormats/CaloHit/interface/PCaloHitContainer.h"
00097
00098 #include "TrackingTools/Records/interface/DetIdAssociatorRecord.h"
00099
00100 using namespace reco;
00101
00102 TrackDetectorAssociator::TrackDetectorAssociator()
00103 {
00104 ivProp_ = 0;
00105 defProp_ = 0;
00106 useDefaultPropagator_ = false;
00107 }
00108
00109 TrackDetectorAssociator::~TrackDetectorAssociator()
00110 {
00111 if (defProp_) delete defProp_;
00112 }
00113
00114 void TrackDetectorAssociator::setPropagator( const Propagator* ptr)
00115 {
00116 ivProp_ = ptr;
00117 cachedTrajectory_.setPropagator(ivProp_);
00118 }
00119
00120 void TrackDetectorAssociator::useDefaultPropagator()
00121 {
00122 useDefaultPropagator_ = true;
00123 }
00124
00125
00126 void TrackDetectorAssociator::init( const edm::EventSetup& iSetup )
00127 {
00128
00129 iSetup.get<CaloGeometryRecord>().get(theCaloGeometry_);
00130 if (!theCaloGeometry_.isValid())
00131 throw cms::Exception("FatalError") << "Unable to find CaloGeometryRecord in event!\n";
00132
00133
00134 iSetup.get<GlobalTrackingGeometryRecord>().get(theTrackingGeometry_);
00135 if (!theTrackingGeometry_.isValid())
00136 throw cms::Exception("FatalError") << "Unable to find GlobalTrackingGeometryRecord in event!\n";
00137
00138 if (useDefaultPropagator_ && (! defProp_ || theMagneticFeildWatcher_.check(iSetup) ) ) {
00139
00140 edm::ESHandle<MagneticField> bField;
00141 iSetup.get<IdealMagneticFieldRecord>().get(bField);
00142
00143 SteppingHelixPropagator* prop = new SteppingHelixPropagator(&*bField,anyDirection);
00144 prop->setMaterialMode(false);
00145 prop->applyRadX0Correction(true);
00146
00147 defProp_ = prop;
00148 setPropagator(defProp_);
00149 }
00150
00151 iSetup.get<DetIdAssociatorRecord>().get("EcalDetIdAssociator", ecalDetIdAssociator_);
00152 iSetup.get<DetIdAssociatorRecord>().get("HcalDetIdAssociator", hcalDetIdAssociator_);
00153 iSetup.get<DetIdAssociatorRecord>().get("HODetIdAssociator", hoDetIdAssociator_);
00154 iSetup.get<DetIdAssociatorRecord>().get("CaloDetIdAssociator", caloDetIdAssociator_);
00155 iSetup.get<DetIdAssociatorRecord>().get("MuonDetIdAssociator", muonDetIdAssociator_);
00156 iSetup.get<DetIdAssociatorRecord>().get("PreshowerDetIdAssociator", preshowerDetIdAssociator_);
00157 }
00158
00159 TrackDetMatchInfo TrackDetectorAssociator::associate( const edm::Event& iEvent,
00160 const edm::EventSetup& iSetup,
00161 const FreeTrajectoryState& fts,
00162 const AssociatorParameters& parameters )
00163 {
00164 return associate(iEvent,iSetup,parameters,&fts);
00165 }
00166
00167 TrackDetMatchInfo TrackDetectorAssociator::associate( const edm::Event& iEvent,
00168 const edm::EventSetup& iSetup,
00169 const AssociatorParameters& parameters,
00170 const FreeTrajectoryState* innerState,
00171 const FreeTrajectoryState* outerState)
00172 {
00173 TrackDetMatchInfo info;
00174 if (! parameters.useEcal && ! parameters.useCalo && ! parameters.useHcal &&
00175 ! parameters.useHO && ! parameters.useMuon && !parameters.usePreshower)
00176 throw cms::Exception("ConfigurationError") <<
00177 "Configuration error! No subdetector was selected for the track association.";
00178
00179
00180
00181 SteppingHelixStateInfo trackOrigin(*innerState);
00182 info.stateAtIP = *innerState;
00183 cachedTrajectory_.setStateAtIP(trackOrigin);
00184
00185 init( iSetup );
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196 info.setCaloGeometry(theCaloGeometry_);
00197
00198
00199 cachedTrajectory_.reset_trajectory();
00200
00201
00202
00203
00204 double HOmaxR = hoDetIdAssociator_->volume().maxR();
00205 double HOmaxZ = hoDetIdAssociator_->volume().maxZ();
00206 double minR = ecalDetIdAssociator_->volume().minR();
00207 double minZ = preshowerDetIdAssociator_->volume().minZ();
00208 cachedTrajectory_.setMaxHORadius(HOmaxR);
00209 cachedTrajectory_.setMaxHOLength(HOmaxZ*2.);
00210 cachedTrajectory_.setMinDetectorRadius(minR);
00211 cachedTrajectory_.setMinDetectorLength(minZ*2.);
00212
00213 double maxR(0);
00214 double maxZ(0);
00215
00216 if (parameters.useMuon) {
00217 maxR = muonDetIdAssociator_->volume().maxR();
00218 maxZ = muonDetIdAssociator_->volume().maxZ();
00219 cachedTrajectory_.setMaxDetectorRadius(maxR);
00220 cachedTrajectory_.setMaxDetectorLength(maxZ*2.);
00221 }
00222 else {
00223 maxR = HOmaxR;
00224 maxZ = HOmaxZ;
00225 cachedTrajectory_.setMaxDetectorRadius(HOmaxR);
00226 cachedTrajectory_.setMaxDetectorLength(HOmaxZ*2.);
00227 }
00228
00229
00230 if (outerState) {
00231 if (outerState->position().perp()<HOmaxR && fabs(outerState->position().z())<HOmaxZ) {
00232 LogTrace("TrackAssociator") << "Using outerState as trackOrigin at Rho=" << outerState->position().perp()
00233 << " Z=" << outerState->position().z() << "\n";
00234 trackOrigin = SteppingHelixStateInfo(*outerState);
00235 }
00236 else if(innerState) {
00237 LogTrace("TrackAssociator") << "Using innerState as trackOrigin at Rho=" << innerState->position().perp()
00238 << " Z=" << innerState->position().z() << "\n";
00239 trackOrigin = SteppingHelixStateInfo(*innerState);
00240 }
00241 }
00242
00243 if ( ! cachedTrajectory_.propagateAll(trackOrigin) ) return info;
00244
00245
00246 cachedTrajectory_.findEcalTrajectory( ecalDetIdAssociator_->volume() );
00247 cachedTrajectory_.findHcalTrajectory( hcalDetIdAssociator_->volume() );
00248 cachedTrajectory_.findHOTrajectory( hoDetIdAssociator_->volume() );
00249 cachedTrajectory_.findPreshowerTrajectory( preshowerDetIdAssociator_->volume() );
00250
00251 info.trkGlobPosAtEcal = getPoint( cachedTrajectory_.getStateAtEcal().position() );
00252 info.trkGlobPosAtHcal = getPoint( cachedTrajectory_.getStateAtHcal().position() );
00253 info.trkGlobPosAtHO = getPoint( cachedTrajectory_.getStateAtHO().position() );
00254
00255 info.trkMomAtEcal = cachedTrajectory_.getStateAtEcal().momentum();
00256 info.trkMomAtHcal = cachedTrajectory_.getStateAtHcal().momentum();
00257 info.trkMomAtHO = cachedTrajectory_.getStateAtHO().momentum();
00258
00259
00260
00261 if (parameters.useEcal) fillEcal( iEvent, info, parameters);
00262 if (parameters.useCalo) fillCaloTowers( iEvent, info, parameters);
00263 if (parameters.useHcal) fillHcal( iEvent, info, parameters);
00264 if (parameters.useHO) fillHO( iEvent, info, parameters);
00265 if (parameters.usePreshower) fillPreshower( iEvent, info, parameters);
00266 if (parameters.useMuon) fillMuon( iEvent, info, parameters);
00267 if (parameters.truthMatch) fillCaloTruth( iEvent, info, parameters);
00268
00269 return info;
00270 }
00271
00272 void TrackDetectorAssociator::fillEcal( const edm::Event& iEvent,
00273 TrackDetMatchInfo& info,
00274 const AssociatorParameters& parameters)
00275 {
00276
00277
00278
00279 const std::vector<SteppingHelixStateInfo>& trajectoryStates = cachedTrajectory_.getEcalTrajectory();
00280
00281 for(std::vector<SteppingHelixStateInfo>::const_iterator itr = trajectoryStates.begin();
00282 itr != trajectoryStates.end(); itr++)
00283 LogTrace("TrackAssociator") << "ECAL trajectory point (rho, z, phi): " << itr->position().perp() <<
00284 ", " << itr->position().z() << ", " << itr->position().phi();
00285
00286 std::vector<GlobalPoint> coreTrajectory;
00287 for(std::vector<SteppingHelixStateInfo>::const_iterator itr = trajectoryStates.begin();
00288 itr != trajectoryStates.end(); itr++) coreTrajectory.push_back(itr->position());
00289
00290 if(coreTrajectory.empty()) {
00291 LogTrace("TrackAssociator") << "ECAL track trajectory is empty; moving on\n";
00292 info.isGoodEcal = 0;
00293 return;
00294 }
00295 info.isGoodEcal = 1;
00296
00297
00298
00299 edm::Handle<EBRecHitCollection> EBRecHits;
00300 iEvent.getByLabel( parameters.theEBRecHitCollectionLabel, EBRecHits );
00301 if (!EBRecHits.isValid()) throw cms::Exception("FatalError") << "Unable to find EBRecHitCollection in the event!\n";
00302
00303
00304 edm::Handle<EERecHitCollection> EERecHits;
00305 iEvent.getByLabel( parameters.theEERecHitCollectionLabel, EERecHits );
00306 if (!EERecHits.isValid()) throw cms::Exception("FatalError") << "Unable to find EERecHitCollection in event!\n";
00307
00308
00309
00310 std::set<DetId> ecalIdsInRegion;
00311 if (parameters.accountForTrajectoryChangeCalo){
00312
00313 DetIdAssociator::MapRange mapRange = getMapRange(cachedTrajectory_.trajectoryDelta(CachedTrajectory::IpToEcal),
00314 parameters.dREcalPreselection);
00315 ecalIdsInRegion = ecalDetIdAssociator_->getDetIdsCloseToAPoint(coreTrajectory[0],mapRange);
00316 } else ecalIdsInRegion = ecalDetIdAssociator_->getDetIdsCloseToAPoint(coreTrajectory[0], parameters.dREcalPreselection);
00317
00318 LogTrace("TrackAssociator") << "ECAL hits in the region: " << ecalIdsInRegion.size();
00319 if (parameters.dREcalPreselection > parameters.dREcal)
00320 ecalIdsInRegion = ecalDetIdAssociator_->getDetIdsInACone(ecalIdsInRegion, coreTrajectory, parameters.dREcal);
00321 LogTrace("TrackAssociator") << "ECAL hits in the cone: " << ecalIdsInRegion.size();
00322 std::vector<DetId> crossedEcalIds =
00323 ecalDetIdAssociator_->getCrossedDetIds(ecalIdsInRegion, coreTrajectory);
00324 LogTrace("TrackAssociator") << "ECAL crossed hits " << crossedEcalIds.size();
00325
00326 info.crossedEcalIds = crossedEcalIds;
00327
00328
00329
00330 for(std::vector<DetId>::const_iterator itr=crossedEcalIds.begin(); itr!=crossedEcalIds.end();itr++)
00331 {
00332 std::vector<EcalRecHit>::const_iterator ebHit = (*EBRecHits).find(*itr);
00333 std::vector<EcalRecHit>::const_iterator eeHit = (*EERecHits).find(*itr);
00334 if(ebHit != (*EBRecHits).end())
00335 info.crossedEcalRecHits.push_back(&*ebHit);
00336 else if(eeHit != (*EERecHits).end())
00337 info.crossedEcalRecHits.push_back(&*eeHit);
00338 else
00339 LogTrace("TrackAssociator") << "Crossed EcalRecHit is not found for DetId: " << itr->rawId();
00340 }
00341
00342 for(std::set<DetId>::const_iterator itr=ecalIdsInRegion.begin(); itr!=ecalIdsInRegion.end();itr++)
00343 {
00344 std::vector<EcalRecHit>::const_iterator ebHit = (*EBRecHits).find(*itr);
00345 std::vector<EcalRecHit>::const_iterator eeHit = (*EERecHits).find(*itr);
00346 if(ebHit != (*EBRecHits).end())
00347 info.ecalRecHits.push_back(&*ebHit);
00348 else if(eeHit != (*EERecHits).end())
00349 info.ecalRecHits.push_back(&*eeHit);
00350 else
00351 LogTrace("TrackAssociator") << "EcalRecHit from the cone is not found for DetId: " << itr->rawId();
00352 }
00353 }
00354
00355 void TrackDetectorAssociator::fillCaloTowers( const edm::Event& iEvent,
00356 TrackDetMatchInfo& info,
00357 const AssociatorParameters& parameters)
00358 {
00359
00360
00361
00362
00363 std::vector<GlobalPoint> trajectory;
00364 const std::vector<SteppingHelixStateInfo>& ecalTrajectoryStates = cachedTrajectory_.getEcalTrajectory();
00365 const std::vector<SteppingHelixStateInfo>& hcalTrajectoryStates = cachedTrajectory_.getHcalTrajectory();
00366 for(std::vector<SteppingHelixStateInfo>::const_iterator itr = ecalTrajectoryStates.begin();
00367 itr != ecalTrajectoryStates.end(); itr++) trajectory.push_back(itr->position());
00368 for(std::vector<SteppingHelixStateInfo>::const_iterator itr = hcalTrajectoryStates.begin();
00369 itr != hcalTrajectoryStates.end(); itr++) trajectory.push_back(itr->position());
00370
00371 if(trajectory.empty()) {
00372 LogTrace("TrackAssociator") << "HCAL trajectory is empty; moving on\n";
00373 info.isGoodCalo = 0;
00374 return;
00375 }
00376 info.isGoodCalo = 1;
00377
00378
00379
00380 edm::Handle<CaloTowerCollection> caloTowers;
00381
00382 iEvent.getByLabel( parameters.theCaloTowerCollectionLabel, caloTowers );
00383 if (!caloTowers.isValid()) throw cms::Exception("FatalError") << "Unable to find CaloTowers in event!\n";
00384
00385
00386 std::set<DetId> caloTowerIdsInRegion;
00387 if (parameters.accountForTrajectoryChangeCalo){
00388
00389 DetIdAssociator::MapRange mapRange = getMapRange(cachedTrajectory_.trajectoryDelta(CachedTrajectory::IpToHcal),
00390 parameters.dRHcalPreselection);
00391 caloTowerIdsInRegion = caloDetIdAssociator_->getDetIdsCloseToAPoint(trajectory[0],mapRange);
00392 } else caloTowerIdsInRegion = caloDetIdAssociator_->getDetIdsCloseToAPoint(trajectory[0], parameters.dRHcalPreselection);
00393
00394 LogTrace("TrackAssociator") << "Towers in the region: " << caloTowerIdsInRegion.size();
00395 std::set<DetId> caloTowerIdsInACone = caloDetIdAssociator_->getDetIdsInACone(caloTowerIdsInRegion, trajectory, parameters.dRHcal);
00396 LogTrace("TrackAssociator") << "Towers in the cone: " << caloTowerIdsInACone.size();
00397 std::vector<DetId> crossedCaloTowerIds = caloDetIdAssociator_->getCrossedDetIds(caloTowerIdsInRegion, trajectory);
00398 LogTrace("TrackAssociator") << "Towers crossed: " << crossedCaloTowerIds.size();
00399
00400 info.crossedTowerIds = crossedCaloTowerIds;
00401
00402
00403
00404 for(std::vector<DetId>::const_iterator itr=crossedCaloTowerIds.begin(); itr!=crossedCaloTowerIds.end();itr++)
00405 {
00406 CaloTowerCollection::const_iterator tower = (*caloTowers).find(*itr);
00407 if(tower != (*caloTowers).end())
00408 info.crossedTowers.push_back(&*tower);
00409 else
00410 LogTrace("TrackAssociator") << "Crossed CaloTower is not found for DetId: " << (*itr).rawId();
00411 }
00412
00413
00414 for(std::set<DetId>::const_iterator itr=caloTowerIdsInACone.begin(); itr!=caloTowerIdsInACone.end();itr++)
00415 {
00416 CaloTowerCollection::const_iterator tower = (*caloTowers).find(*itr);
00417 if(tower != (*caloTowers).end())
00418 info.towers.push_back(&*tower);
00419 else
00420 LogTrace("TrackAssociator") << "CaloTower from the cone is not found for DetId: " << (*itr).rawId();
00421 }
00422
00423 }
00424
00425 void TrackDetectorAssociator::fillPreshower( const edm::Event& iEvent,
00426 TrackDetMatchInfo& info,
00427 const AssociatorParameters& parameters)
00428 {
00429 std::vector<GlobalPoint> trajectory;
00430 const std::vector<SteppingHelixStateInfo>& trajectoryStates = cachedTrajectory_.getPreshowerTrajectory();
00431 for(std::vector<SteppingHelixStateInfo>::const_iterator itr = trajectoryStates.begin();
00432 itr != trajectoryStates.end(); itr++) trajectory.push_back(itr->position());
00433
00434 if(trajectory.empty()) {
00435 LogTrace("TrackAssociator") << "Preshower trajectory is empty; moving on\n";
00436 return;
00437 }
00438
00439 std::set<DetId> idsInRegion =
00440 preshowerDetIdAssociator_->getDetIdsCloseToAPoint(trajectory[0],
00441 parameters.dRPreshowerPreselection);
00442
00443 LogTrace("TrackAssociator") << "Number of Preshower Ids in the region: " << idsInRegion.size();
00444 std::vector<DetId> crossedIds = preshowerDetIdAssociator_->getCrossedDetIds(idsInRegion, trajectory);
00445 LogTrace("TrackAssociator") << "Number of Preshower Ids in crossed: " << crossedIds.size();
00446 info.crossedPreshowerIds = crossedIds;
00447 }
00448
00449
00450 void TrackDetectorAssociator::fillHcal( const edm::Event& iEvent,
00451 TrackDetMatchInfo& info,
00452 const AssociatorParameters& parameters)
00453 {
00454
00455
00456
00457 const std::vector<SteppingHelixStateInfo>& trajectoryStates = cachedTrajectory_.getHcalTrajectory();
00458
00459 std::vector<GlobalPoint> coreTrajectory;
00460 for(std::vector<SteppingHelixStateInfo>::const_iterator itr = trajectoryStates.begin();
00461 itr != trajectoryStates.end(); itr++) coreTrajectory.push_back(itr->position());
00462
00463 if(coreTrajectory.empty()) {
00464 LogTrace("TrackAssociator") << "HCAL trajectory is empty; moving on\n";
00465 info.isGoodHcal = 0;
00466 return;
00467 }
00468 info.isGoodHcal = 1;
00469
00470
00471
00472 edm::Handle<HBHERecHitCollection> collection;
00473
00474 iEvent.getByLabel( parameters.theHBHERecHitCollectionLabel, collection );
00475 if ( ! collection.isValid() ) throw cms::Exception("FatalError") << "Unable to find HBHERecHits in event!\n";
00476
00477
00478 std::set<DetId> idsInRegion;
00479 if (parameters.accountForTrajectoryChangeCalo){
00480
00481 DetIdAssociator::MapRange mapRange = getMapRange(cachedTrajectory_.trajectoryDelta(CachedTrajectory::IpToHcal),
00482 parameters.dRHcalPreselection);
00483 idsInRegion = hcalDetIdAssociator_->getDetIdsCloseToAPoint(coreTrajectory[0], mapRange);
00484 } else idsInRegion = hcalDetIdAssociator_->getDetIdsCloseToAPoint(coreTrajectory[0], parameters.dRHcalPreselection);
00485
00486 LogTrace("TrackAssociator") << "HCAL hits in the region: " << idsInRegion.size() << "\n" << DetIdInfo::info(idsInRegion);
00487 std::set<DetId> idsInACone = hcalDetIdAssociator_->getDetIdsInACone(idsInRegion, coreTrajectory, parameters.dRHcal);
00488 LogTrace("TrackAssociator") << "HCAL hits in the cone: " << idsInACone.size() << "\n" << DetIdInfo::info(idsInACone);
00489 std::vector<DetId> crossedIds =
00490 hcalDetIdAssociator_->getCrossedDetIds(idsInRegion, coreTrajectory);
00491 LogTrace("TrackAssociator") << "HCAL hits crossed: " << crossedIds.size() << "\n" << DetIdInfo::info(crossedIds);
00492
00493 info.crossedHcalIds = crossedIds;
00494
00495
00496
00497 for(std::vector<DetId>::const_iterator itr=crossedIds.begin(); itr!=crossedIds.end();itr++)
00498 {
00499 HBHERecHitCollection::const_iterator hit = (*collection).find(*itr);
00500 if( hit != (*collection).end() )
00501 info.crossedHcalRecHits.push_back(&*hit);
00502 else
00503 LogTrace("TrackAssociator") << "Crossed HBHERecHit is not found for DetId: " << itr->rawId();
00504 }
00505
00506 for(std::set<DetId>::const_iterator itr=idsInACone.begin(); itr!=idsInACone.end();itr++)
00507 {
00508 HBHERecHitCollection::const_iterator hit = (*collection).find(*itr);
00509 if( hit != (*collection).end() )
00510 info.hcalRecHits.push_back(&*hit);
00511 else
00512 LogTrace("TrackAssociator") << "HBHERecHit from the cone is not found for DetId: " << itr->rawId();
00513 }
00514 }
00515
00516 void TrackDetectorAssociator::fillHO( const edm::Event& iEvent,
00517 TrackDetMatchInfo& info,
00518 const AssociatorParameters& parameters)
00519 {
00520
00521
00522
00523 const std::vector<SteppingHelixStateInfo>& trajectoryStates = cachedTrajectory_.getHOTrajectory();
00524
00525 std::vector<GlobalPoint> coreTrajectory;
00526 for(std::vector<SteppingHelixStateInfo>::const_iterator itr = trajectoryStates.begin();
00527 itr != trajectoryStates.end(); itr++) coreTrajectory.push_back(itr->position());
00528
00529 if(coreTrajectory.empty()) {
00530 LogTrace("TrackAssociator") << "HO trajectory is empty; moving on\n";
00531 info.isGoodHO = 0;
00532 return;
00533 }
00534 info.isGoodHO = 1;
00535
00536
00537
00538 edm::Handle<HORecHitCollection> collection;
00539
00540 iEvent.getByLabel( parameters.theHORecHitCollectionLabel, collection );
00541 if ( ! collection.isValid() ) throw cms::Exception("FatalError") << "Unable to find HORecHits in event!\n";
00542
00543
00544 std::set<DetId> idsInRegion;
00545 if (parameters.accountForTrajectoryChangeCalo){
00546
00547 DetIdAssociator::MapRange mapRange = getMapRange(cachedTrajectory_.trajectoryDelta(CachedTrajectory::IpToHO),
00548 parameters.dRHcalPreselection);
00549 idsInRegion = hoDetIdAssociator_->getDetIdsCloseToAPoint(coreTrajectory[0], mapRange);
00550 } else idsInRegion = hoDetIdAssociator_->getDetIdsCloseToAPoint(coreTrajectory[0], parameters.dRHcalPreselection);
00551
00552 LogTrace("TrackAssociator") << "idsInRegion.size(): " << idsInRegion.size();
00553 std::set<DetId> idsInACone = hoDetIdAssociator_->getDetIdsInACone(idsInRegion, coreTrajectory, parameters.dRHcal);
00554 LogTrace("TrackAssociator") << "idsInACone.size(): " << idsInACone.size();
00555 std::vector<DetId> crossedIds =
00556 hoDetIdAssociator_->getCrossedDetIds(idsInRegion, coreTrajectory);
00557
00558 info.crossedHOIds = crossedIds;
00559
00560
00561
00562 for(std::vector<DetId>::const_iterator itr=crossedIds.begin(); itr!=crossedIds.end();itr++)
00563 {
00564 HORecHitCollection::const_iterator hit = (*collection).find(*itr);
00565 if( hit != (*collection).end() )
00566 info.crossedHORecHits.push_back(&*hit);
00567 else
00568 LogTrace("TrackAssociator") << "Crossed HORecHit is not found for DetId: " << itr->rawId();
00569 }
00570
00571
00572 for(std::set<DetId>::const_iterator itr=idsInACone.begin(); itr!=idsInACone.end();itr++)
00573 {
00574 HORecHitCollection::const_iterator hit = (*collection).find(*itr);
00575 if( hit != (*collection).end() )
00576 info.hoRecHits.push_back(&*hit);
00577 else
00578 LogTrace("TrackAssociator") << "HORecHit from the cone is not found for DetId: " << itr->rawId();
00579 }
00580 }
00581
00582 FreeTrajectoryState TrackDetectorAssociator::getFreeTrajectoryState( const edm::EventSetup& iSetup,
00583 const SimTrack& track,
00584 const SimVertex& vertex )
00585 {
00586 GlobalVector vector( track.momentum().x(), track.momentum().y(), track.momentum().z() );
00587 GlobalPoint point( vertex.position().x(), vertex.position().y(), vertex.position().z() );
00588
00589 int charge = track.type( )> 0 ? -1 : 1;
00590 if ( abs(track.type( )) == 211 ||
00591 abs(track.type( )) == 321 ||
00592 abs(track.type( )) == 2212 )
00593 charge = track.type( )< 0 ? -1 : 1;
00594 return getFreeTrajectoryState(iSetup, vector, point, charge);
00595 }
00596
00597 FreeTrajectoryState TrackDetectorAssociator::getFreeTrajectoryState( const edm::EventSetup& iSetup,
00598 const GlobalVector& momentum,
00599 const GlobalPoint& vertex,
00600 const int charge)
00601 {
00602 edm::ESHandle<MagneticField> bField;
00603 iSetup.get<IdealMagneticFieldRecord>().get(bField);
00604
00605 GlobalTrajectoryParameters tPars(vertex, momentum, charge, &*bField);
00606
00607 ROOT::Math::SMatrixIdentity id;
00608 AlgebraicSymMatrix66 covT(id); covT *= 1e-6;
00609 CartesianTrajectoryError tCov(covT);
00610
00611 return FreeTrajectoryState(tPars, tCov);
00612 }
00613
00614
00615 FreeTrajectoryState TrackDetectorAssociator::getFreeTrajectoryState( const edm::EventSetup& iSetup,
00616 const reco::Track& track )
00617 {
00618 edm::ESHandle<MagneticField> bField;
00619 iSetup.get<IdealMagneticFieldRecord>().get(bField);
00620
00621 GlobalVector vector( track.momentum().x(), track.momentum().y(), track.momentum().z() );
00622
00623 GlobalPoint point( track.vertex().x(), track.vertex().y(), track.vertex().z() );
00624
00625 GlobalTrajectoryParameters tPars(point, vector, track.charge(), &*bField);
00626
00627
00628
00629
00630 ROOT::Math::SMatrixIdentity id;
00631 AlgebraicSymMatrix66 covT(id); covT *= 1e-6;
00632 CartesianTrajectoryError tCov(covT);
00633
00634 return FreeTrajectoryState(tPars, tCov);
00635 }
00636
00637 DetIdAssociator::MapRange TrackDetectorAssociator::getMapRange( const std::pair<float,float>& delta,
00638 const float dR )
00639 {
00640 DetIdAssociator::MapRange mapRange;
00641 mapRange.dThetaPlus = dR;
00642 mapRange.dThetaMinus = dR;
00643 mapRange.dPhiPlus = dR;
00644 mapRange.dPhiMinus = dR;
00645 if ( delta.first > 0 )
00646 mapRange.dThetaPlus += delta.first;
00647 else
00648 mapRange.dThetaMinus += fabs(delta.first);
00649 if ( delta.second > 0 )
00650 mapRange.dPhiPlus += delta.second;
00651 else
00652 mapRange.dPhiMinus += fabs(delta.second);
00653 LogTrace("TrackAssociator") << "Selection range: (dThetaPlus, dThetaMinus, dPhiPlus, dPhiMinus, dRPreselection): " <<
00654 mapRange.dThetaPlus << ", " << mapRange.dThetaMinus << ", " <<
00655 mapRange.dPhiPlus << ", " << mapRange.dPhiMinus << ", " << dR;
00656 return mapRange;
00657 }
00658
00659 void TrackDetectorAssociator::getTAMuonChamberMatches(std::vector<TAMuonChamberMatch>& matches,
00660 const AssociatorParameters& parameters)
00661 {
00662
00663
00664
00665
00666
00667
00668
00669
00670
00671
00672
00673 SteppingHelixStateInfo trajectoryPoint = cachedTrajectory_.getStateAtHcal();
00674
00675
00676 if(! trajectoryPoint.isValid() ) trajectoryPoint = cachedTrajectory_.getOuterState();
00677 if(! trajectoryPoint.isValid() ) {
00678 LogTrace("TrackAssociator") <<
00679 "trajectory position at HCAL is not valid. Assume the track cannot reach muon detectors and skip it";
00680 return;
00681 }
00682
00683 GlobalVector direction = trajectoryPoint.momentum().unit();
00684 LogTrace("TrackAssociator") << "muon direction: " << direction << "\n\t and corresponding point: " <<
00685 trajectoryPoint.position() <<"\n";
00686
00687 DetIdAssociator::MapRange mapRange = getMapRange(cachedTrajectory_.trajectoryDelta(CachedTrajectory::FullTrajectory),
00688 parameters.dRMuonPreselection);
00689
00690
00691
00692
00693 std::set<DetId> muonIdsInRegion =
00694 muonDetIdAssociator_->getDetIdsCloseToAPoint(trajectoryPoint.position(), mapRange);
00695
00696 LogTrace("TrackAssociator") << "Number of chambers to check: " << muonIdsInRegion.size();
00697 for(std::set<DetId>::const_iterator detId = muonIdsInRegion.begin(); detId != muonIdsInRegion.end(); detId++)
00698 {
00699 const GeomDet* geomDet = muonDetIdAssociator_->getGeomDet(*detId);
00700
00701 TrajectoryStateOnSurface stateOnSurface = cachedTrajectory_.propagate( &geomDet->surface() );
00702 if (! stateOnSurface.isValid()) {
00703 LogTrace("TrackAssociator") << "Failed to propagate the track; moving on\n\t"<<
00704 "Element is not crosssed: " << DetIdInfo::info(*detId) << "\n";
00705 continue;
00706 }
00707
00708 LocalPoint localPoint = geomDet->surface().toLocal(stateOnSurface.freeState()->position());
00709 LocalError localError = stateOnSurface.localError().positionError();
00710 float distanceX = 0;
00711 float distanceY = 0;
00712 float sigmaX = 0.0;
00713 float sigmaY = 0.0;
00714 if(const CSCChamber* cscChamber = dynamic_cast<const CSCChamber*>(geomDet) ) {
00715 const CSCChamberSpecs* chamberSpecs = cscChamber->specs();
00716 if(! chamberSpecs) {
00717 LogTrace("TrackAssociator") << "Failed to get CSCChamberSpecs from CSCChamber; moving on\n";
00718 continue;
00719 }
00720 const CSCLayerGeometry* layerGeometry = chamberSpecs->oddLayerGeometry(1);
00721 if(! layerGeometry) {
00722 LogTrace("TrackAssociator") << "Failed to get CSCLayerGeometry from CSCChamberSpecs; moving on\n";
00723 continue;
00724 }
00725 const CSCWireTopology* wireTopology = layerGeometry->wireTopology();
00726 if(! wireTopology) {
00727 LogTrace("TrackAssociator") << "Failed to get CSCWireTopology from CSCLayerGeometry; moving on\n";
00728 continue;
00729 }
00730
00731 float wideWidth = wireTopology->wideWidthOfPlane();
00732 float narrowWidth = wireTopology->narrowWidthOfPlane();
00733 float length = wireTopology->lengthOfPlane();
00734
00735 float yOfFirstWire = fabs(wireTopology->wireAngle())>1.E-06 ? -0.5*length : wireTopology->yOfWire(1);
00736
00737 float yCOWPOffset = yOfFirstWire+0.5*length;
00738
00739
00740 float tangent = (wideWidth-narrowWidth)/(2.*length);
00741
00742 float yPrime = localPoint.y()+fabs(yOfFirstWire);
00743
00744 float halfWidthAtYPrime = 0.5*narrowWidth+yPrime*tangent;
00745 distanceX = fabs(localPoint.x()) - halfWidthAtYPrime;
00746 distanceY = fabs(localPoint.y()-yCOWPOffset) - 0.5*length;
00747 sigmaX = distanceX/sqrt(localError.xx());
00748 sigmaY = distanceY/sqrt(localError.yy());
00749 } else {
00750 distanceX = fabs(localPoint.x()) - geomDet->surface().bounds().width()/2.;
00751 distanceY = fabs(localPoint.y()) - geomDet->surface().bounds().length()/2.;
00752 sigmaX = distanceX/sqrt(localError.xx());
00753 sigmaY = distanceY/sqrt(localError.yy());
00754 }
00755
00756 if ( (distanceX < parameters.muonMaxDistanceX && distanceY < parameters.muonMaxDistanceY) ||
00757 (sigmaX < parameters.muonMaxDistanceSigmaX && sigmaY < parameters.muonMaxDistanceSigmaY) ) {
00758 LogTrace("TrackAssociator") << "found a match: " << DetIdInfo::info(*detId) << "\n";
00759 TAMuonChamberMatch match;
00760 match.tState = stateOnSurface;
00761 match.localDistanceX = distanceX;
00762 match.localDistanceY = distanceY;
00763 match.id = *detId;
00764 matches.push_back(match);
00765 } else {
00766 LogTrace("TrackAssociator") << "chamber is too far: " <<
00767 DetIdInfo::info(*detId) << "\n\tdistanceX: " << distanceX << "\t distanceY: " << distanceY <<
00768 "\t sigmaX: " << sigmaX << "\t sigmaY: " << sigmaY << "\n";
00769 }
00770
00771 }
00772
00773
00774 }
00775
00776 void TrackDetectorAssociator::fillMuon( const edm::Event& iEvent,
00777 TrackDetMatchInfo& info,
00778 const AssociatorParameters& parameters)
00779 {
00780
00781
00782
00783
00784
00785 edm::Handle<DTRecSegment4DCollection> dtSegments;
00786 iEvent.getByLabel( parameters.theDTRecSegment4DCollectionLabel, dtSegments );
00787 if (! dtSegments.isValid())
00788 throw cms::Exception("FatalError") << "Unable to find DTRecSegment4DCollection in event!\n";
00789
00790 edm::Handle<CSCSegmentCollection> cscSegments;
00791 iEvent.getByLabel( parameters.theCSCSegmentCollectionLabel, cscSegments );
00792 if (! cscSegments.isValid())
00793 throw cms::Exception("FatalError") << "Unable to find CSCSegmentCollection in event!\n";
00794
00796
00797
00798
00799
00800
00801
00802
00803
00804
00805
00806
00807
00808 std::vector<TAMuonChamberMatch> matchedChambers;
00809 LogTrace("TrackAssociator") << "Trying to Get ChamberMatches" << std::endl;
00810 getTAMuonChamberMatches(matchedChambers, parameters);
00811 LogTrace("TrackAssociator") << "Chambers matched: " << matchedChambers.size() << "\n";
00812
00813
00814
00815
00816 for(std::vector<TAMuonChamberMatch>::iterator matchedChamber = matchedChambers.begin();
00817 matchedChamber != matchedChambers.end(); matchedChamber++)
00818 {
00819 const GeomDet* geomDet = muonDetIdAssociator_->getGeomDet((*matchedChamber).id);
00820
00821 if(const DTChamber* chamber = dynamic_cast<const DTChamber*>(geomDet) ) {
00822
00823 DTRecSegment4DCollection::range range = dtSegments->get(chamber->id());
00824
00825 for (DTRecSegment4DCollection::const_iterator segment = range.first; segment!=range.second; segment++) {
00826 if (addTAMuonSegmentMatch(*matchedChamber, &(*segment), parameters)) {
00827 matchedChamber->segments.back().dtSegmentRef = DTRecSegment4DRef(dtSegments, segment - dtSegments->begin());
00828 }
00829 }
00830 }else{
00831
00832 if(const CSCChamber* chamber = dynamic_cast<const CSCChamber*>(geomDet) ) {
00833
00834 CSCSegmentCollection::range range = cscSegments->get(chamber->id());
00835
00836 for (CSCSegmentCollection::const_iterator segment = range.first; segment!=range.second; segment++) {
00837 if (addTAMuonSegmentMatch(*matchedChamber, &(*segment), parameters)) {
00838 matchedChamber->segments.back().cscSegmentRef = CSCSegmentRef(cscSegments, segment - cscSegments->begin());
00839 }
00840 }
00841 }else{
00842
00843 }
00844 }
00845 info.chambers.push_back(*matchedChamber);
00846 }
00847 }
00848
00849
00850 bool TrackDetectorAssociator::addTAMuonSegmentMatch(TAMuonChamberMatch& matchedChamber,
00851 const RecSegment* segment,
00852 const AssociatorParameters& parameters)
00853 {
00854 LogTrace("TrackAssociator")
00855 << "Segment local position: " << segment->localPosition() << "\n"
00856 << std::hex << segment->geographicalId().rawId() << "\n";
00857
00858 const GeomDet* chamber = muonDetIdAssociator_->getGeomDet(matchedChamber.id);
00859 TrajectoryStateOnSurface trajectoryStateOnSurface = matchedChamber.tState;
00860 GlobalPoint segmentGlobalPosition = chamber->toGlobal(segment->localPosition());
00861
00862 LogTrace("TrackAssociator")
00863 << "Segment global position: " << segmentGlobalPosition << " \t (R_xy,eta,phi): "
00864 << segmentGlobalPosition.perp() << "," << segmentGlobalPosition.eta() << "," << segmentGlobalPosition.phi() << "\n";
00865
00866 LogTrace("TrackAssociator")
00867 << "\teta hit: " << segmentGlobalPosition.eta() << " \tpropagator: " << trajectoryStateOnSurface.freeState()->position().eta() << "\n"
00868 << "\tphi hit: " << segmentGlobalPosition.phi() << " \tpropagator: " << trajectoryStateOnSurface.freeState()->position().phi() << std::endl;
00869
00870 bool isGood = false;
00871 bool isDTWithoutY = false;
00872 const DTRecSegment4D* dtseg = dynamic_cast<const DTRecSegment4D*>(segment);
00873 if ( dtseg && (! dtseg->hasZed()) )
00874 isDTWithoutY = true;
00875
00876 double deltaPhi(fabs(segmentGlobalPosition.phi()-trajectoryStateOnSurface.freeState()->position().phi()));
00877 if(deltaPhi>M_PI) deltaPhi = fabs(deltaPhi-M_PI*2.);
00878
00879 if( isDTWithoutY )
00880 {
00881 isGood = deltaPhi < parameters.dRMuon;
00882
00883 isGood &= fabs(segmentGlobalPosition.eta()-trajectoryStateOnSurface.freeState()->position().eta()) < .3;
00884 } else isGood = sqrt( pow(segmentGlobalPosition.eta()-trajectoryStateOnSurface.freeState()->position().eta(),2) +
00885 deltaPhi*deltaPhi) < parameters.dRMuon;
00886
00887 if(isGood) {
00888 TAMuonSegmentMatch muonSegment;
00889 muonSegment.segmentGlobalPosition = getPoint(segmentGlobalPosition);
00890 muonSegment.segmentLocalPosition = getPoint( segment->localPosition() );
00891 muonSegment.segmentLocalDirection = getVector( segment->localDirection() );
00892 muonSegment.segmentLocalErrorXX = segment->localPositionError().xx();
00893 muonSegment.segmentLocalErrorYY = segment->localPositionError().yy();
00894 muonSegment.segmentLocalErrorXY = segment->localPositionError().xy();
00895 muonSegment.segmentLocalErrorDxDz = segment->localDirectionError().xx();
00896 muonSegment.segmentLocalErrorDyDz = segment->localDirectionError().yy();
00897
00898
00899
00900
00901
00902 muonSegment.segmentLocalErrorXDxDz = -999;
00903 muonSegment.segmentLocalErrorYDyDz = -999;
00904 muonSegment.hasZed = true;
00905 muonSegment.hasPhi = true;
00906
00907
00908 muonSegment.t0 = 0;
00909 if ( dtseg ) {
00910 if ( (dtseg->hasPhi()) && (! isDTWithoutY) ) {
00911 int phiHits = dtseg->phiSegment()->specificRecHits().size();
00912
00913 int hits=0;
00914 double t0=0.;
00915
00916 if (phiHits>5 && dtseg->phiSegment()->ist0Valid()) {
00917 t0+=dtseg->phiSegment()->t0()*phiHits;
00918 hits+=phiHits;
00919 LogTrace("TrackAssociator") << " Phi t0: " << dtseg->phiSegment()->t0() << " hits: " << phiHits;
00920 }
00921
00922
00923
00924
00925
00926
00927 if (hits) muonSegment.t0 = t0/hits;
00928
00929 } else {
00930
00931 if (isDTWithoutY) muonSegment.hasZed = false;
00932 if (! dtseg->hasPhi()) muonSegment.hasPhi = false;
00933 }
00934 }
00935 matchedChamber.segments.push_back(muonSegment);
00936 }
00937
00938 return isGood;
00939 }
00940
00941
00942
00943 void TrackDetectorAssociator::fillCaloTruth( const edm::Event& iEvent,
00944 TrackDetMatchInfo& info,
00945 const AssociatorParameters& parameters)
00946 {
00947
00948 using namespace edm;
00949 Handle<SimTrackContainer> simTracks;
00950 iEvent.getByType<SimTrackContainer>(simTracks);
00951 if (! simTracks.isValid() ) throw cms::Exception("FatalError") << "No simulated tracks found\n";
00952
00953 Handle<SimVertexContainer> simVertices;
00954 iEvent.getByType<SimVertexContainer>(simVertices);
00955 if (! simVertices.isValid() ) throw cms::Exception("FatalError") << "No simulated vertices found\n";
00956
00957
00958 Handle<PCaloHitContainer> simEcalHitsEB;
00959 iEvent.getByLabel("g4SimHits","EcalHitsEB",simEcalHitsEB);
00960 if (! simEcalHitsEB.isValid() ) throw cms::Exception("FatalError") << "No simulated ECAL EB hits found\n";
00961
00962 Handle<PCaloHitContainer> simEcalHitsEE;
00963 iEvent.getByLabel("g4SimHits","EcalHitsEE",simEcalHitsEE);
00964 if (! simEcalHitsEE.isValid() ) throw cms::Exception("FatalError") << "No simulated ECAL EE hits found\n";
00965
00966 Handle<PCaloHitContainer> simHcalHits;
00967 iEvent.getByLabel("g4SimHits","HcalHits",simHcalHits);
00968 if (! simHcalHits.isValid() ) throw cms::Exception("FatalError") << "No simulated HCAL hits found\n";
00969
00970
00971 SimTrackContainer::const_iterator simTrack = simTracks->begin();
00972 for( ; simTrack != simTracks->end(); ++simTrack){
00973 math::XYZVector simP3( simTrack->momentum().x(), simTrack->momentum().y(), simTrack->momentum().z() );
00974 math::XYZVector recoP3( info.stateAtIP.momentum().x(), info.stateAtIP.momentum().y(), info.stateAtIP.momentum().z() );
00975 if ( ROOT::Math::VectorUtil::DeltaR(recoP3, simP3) < 0.1 ) break;
00976 }
00977 if ( simTrack != simTracks->end() ) {
00978 info.simTrack = &(*simTrack);
00979 double ecalTrueEnergy(0);
00980 double hcalTrueEnergy(0);
00981
00982
00983 for( PCaloHitContainer::const_iterator hit = simEcalHitsEB->begin(); hit != simEcalHitsEB->end(); ++hit )
00984 if ( hit->geantTrackId() == info.simTrack->genpartIndex() ) ecalTrueEnergy += hit->energy();
00985
00986 for( PCaloHitContainer::const_iterator hit = simEcalHitsEE->begin(); hit != simEcalHitsEE->end(); ++hit )
00987 if ( hit->geantTrackId() == info.simTrack->genpartIndex() ) ecalTrueEnergy += hit->energy();
00988
00989 for( PCaloHitContainer::const_iterator hit = simHcalHits->begin(); hit != simHcalHits->end(); ++hit )
00990 if ( hit->geantTrackId() == info.simTrack->genpartIndex() ) hcalTrueEnergy += hit->energy();
00991
00992 info.ecalTrueEnergy = ecalTrueEnergy;
00993 info.hcalTrueEnergy = hcalTrueEnergy;
00994 info.hcalTrueEnergyCorrected = hcalTrueEnergy;
00995 if ( fabs(info.trkGlobPosAtHcal.eta()) < 1.3 )
00996 info.hcalTrueEnergyCorrected = hcalTrueEnergy*113.2;
00997 else
00998 if ( fabs(info.trkGlobPosAtHcal.eta()) < 3.0 )
00999 info.hcalTrueEnergyCorrected = hcalTrueEnergy*167.2;
01000 }
01001 }
01002
01003 TrackDetMatchInfo TrackDetectorAssociator::associate( const edm::Event& iEvent,
01004 const edm::EventSetup& iSetup,
01005 const reco::Track& track,
01006 const AssociatorParameters& parameters,
01007 Direction direction )
01008 {
01009 double currentStepSize = cachedTrajectory_.getPropagationStep();
01010
01011 edm::ESHandle<MagneticField> bField;
01012 iSetup.get<IdealMagneticFieldRecord>().get(bField);
01013
01014 if(track.extra().isNull()) {
01015 if ( direction != InsideOut )
01016 throw cms::Exception("FatalError") <<
01017 "No TrackExtra information is available and association is done with something else than InsideOut track.\n" <<
01018 "Either change the parameter or provide needed data!\n";
01019 LogTrace("TrackAssociator") << "Track Extras not found\n";
01020 FreeTrajectoryState initialState = trajectoryStateTransform::initialFreeState(track,&*bField);
01021 return associate(iEvent, iSetup, parameters, &initialState);
01022 }
01023
01024 LogTrace("TrackAssociator") << "Track Extras found\n";
01025 FreeTrajectoryState innerState = trajectoryStateTransform::innerFreeState(track,&*bField);
01026 FreeTrajectoryState outerState = trajectoryStateTransform::outerFreeState(track,&*bField);
01027 FreeTrajectoryState referenceState = trajectoryStateTransform::initialFreeState(track,&*bField);
01028
01029 LogTrace("TrackAssociator") << "inner track state (rho, z, phi):" <<
01030 track.innerPosition().Rho() << ", " << track.innerPosition().z() <<
01031 ", " << track.innerPosition().phi() << "\n";
01032 LogTrace("TrackAssociator") << "innerFreeState (rho, z, phi):" <<
01033 innerState.position().perp() << ", " << innerState.position().z() <<
01034 ", " << innerState.position().phi() << "\n";
01035
01036 LogTrace("TrackAssociator") << "outer track state (rho, z, phi):" <<
01037 track.outerPosition().Rho() << ", " << track.outerPosition().z() <<
01038 ", " << track.outerPosition().phi() << "\n";
01039 LogTrace("TrackAssociator") << "outerFreeState (rho, z, phi):" <<
01040 outerState.position().perp() << ", " << outerState.position().z() <<
01041 ", " << outerState.position().phi() << "\n";
01042
01043
01044 if ( crossedIP( track ) ) {
01045 switch ( direction ) {
01046 case InsideOut:
01047 case Any:
01048 return associate(iEvent, iSetup, parameters, &referenceState, &outerState);
01049 break;
01050 case OutsideIn:
01051 {
01052 cachedTrajectory_.setPropagationStep( -fabs(currentStepSize) );
01053 TrackDetMatchInfo result = associate(iEvent, iSetup, parameters, &innerState, &referenceState);
01054 cachedTrajectory_.setPropagationStep( currentStepSize );
01055 return result;
01056 break;
01057 }
01058 }
01059 } else {
01060 switch ( direction ) {
01061 case InsideOut:
01062 return associate(iEvent, iSetup, parameters, &innerState, &outerState);
01063 break;
01064 case OutsideIn:
01065 {
01066 cachedTrajectory_.setPropagationStep( -fabs(currentStepSize) );
01067 TrackDetMatchInfo result = associate(iEvent, iSetup, parameters, &outerState, &innerState);
01068 cachedTrajectory_.setPropagationStep( currentStepSize );
01069 return result;
01070 break;
01071 }
01072 case Any:
01073 {
01074
01075 if ( track.innerPosition().Dot( track.innerMomentum() ) < 0 &&
01076 track.outerPosition().Dot( track.outerMomentum() ) < 0 )
01077 {
01078 cachedTrajectory_.setPropagationStep( -fabs(currentStepSize) );
01079 TrackDetMatchInfo result;
01080 if ( track.innerPosition().R() < track.outerPosition().R() )
01081 result = associate(iEvent, iSetup, parameters, &innerState, &outerState);
01082 else
01083 result = associate(iEvent, iSetup, parameters, &outerState, &innerState);
01084 cachedTrajectory_.setPropagationStep( currentStepSize );
01085 return result;
01086 }
01087 }
01088 }
01089 }
01090
01091
01092 return associate(iEvent, iSetup, parameters, &innerState, &outerState);
01093 }
01094
01095 TrackDetMatchInfo TrackDetectorAssociator::associate( const edm::Event& iEvent,
01096 const edm::EventSetup& iSetup,
01097 const SimTrack& track,
01098 const SimVertex& vertex,
01099 const AssociatorParameters& parameters)
01100 {
01101 return associate(iEvent, iSetup, getFreeTrajectoryState(iSetup, track, vertex), parameters);
01102 }
01103
01104 TrackDetMatchInfo TrackDetectorAssociator::associate( const edm::Event& iEvent,
01105 const edm::EventSetup& iSetup,
01106 const GlobalVector& momentum,
01107 const GlobalPoint& vertex,
01108 const int charge,
01109 const AssociatorParameters& parameters)
01110 {
01111 return associate(iEvent, iSetup, getFreeTrajectoryState(iSetup, momentum, vertex, charge), parameters);
01112 }
01113
01114 bool TrackDetectorAssociator::crossedIP( const reco::Track& track )
01115 {
01116 bool crossed = true;
01117 crossed &= (track.innerPosition().rho() > 3 );
01118 crossed &= (track.outerPosition().rho() > 3 );
01119 crossed &= ( ( track.innerPosition().x()*track.innerMomentum().x() +
01120 track.innerPosition().y()*track.innerMomentum().y() < 0 ) !=
01121 ( track.outerPosition().x()*track.outerMomentum().x() +
01122 track.outerPosition().y()*track.outerMomentum().y() < 0 ) );
01123 return crossed;
01124 }