00001
00012 #include "RecoMuon/TrackingTools/interface/MuonTrackLoader.h"
00013
00014 #include "RecoMuon/TrackingTools/interface/MuonPatternRecoDumper.h"
00015 #include "RecoMuon/TrackingTools/interface/MuonServiceProxy.h"
00016 #include "RecoMuon/TrackingTools/interface/MuonUpdatorAtVertex.h"
00017
00018 #include "TrackingTools/PatternTools/interface/Trajectory.h"
00019 #include "TrackingTools/TrackFitters/interface/TrajectoryFitter.h"
00020 #include "TrackingTools/PatternTools/interface/TrajTrackAssociation.h"
00021 #include "TrackingTools/TransientTrack/interface/TransientTrack.h"
00022 #include "TrackingTools/GeomPropagators/interface/TrackerBounds.h"
00023 #include "TrackingTools/PatternTools/interface/TrajectorySmoother.h"
00024 #include "TrackingTools/Records/interface/TrackingComponentsRecord.h"
00025 #include "TrackingTools/DetLayers/interface/BarrelDetLayer.h"
00026 #include "TrackingTools/DetLayers/interface/ForwardDetLayer.h"
00027
00028 #include "Geometry/CommonDetUnit/interface/GeomDet.h"
00029
00030 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00031 #include "FWCore/Framework/interface/Event.h"
00032 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00033
00034 #include "DataFormats/Math/interface/LorentzVector.h"
00035 #include "DataFormats/TrackReco/interface/Track.h"
00036 #include "DataFormats/TrackReco/interface/TrackExtra.h"
00037 #include "DataFormats/TrackReco/interface/TrackToTrackMap.h"
00038
00039 #include "DataFormats/MuonReco/interface/MuonTrackLinks.h"
00040 #include "DataFormats/MuonReco/interface/MuonFwd.h"
00041
00042 using namespace edm;
00043 using namespace std;
00044
00045
00046 MuonTrackLoader::MuonTrackLoader(ParameterSet ¶meterSet, const MuonServiceProxy *service):
00047 theService(service){
00048
00049
00050
00051 theSmoothingStep = parameterSet.getParameter<bool>("DoSmoothing");
00052 if(theSmoothingStep)
00053 theSmootherName = parameterSet.getParameter<string>("Smoother");
00054
00055
00056 theUpdatingAtVtx = parameterSet.getParameter<bool>("VertexConstraint");
00057
00058
00059 theBeamSpotInputTag = parameterSet.getParameter<edm::InputTag>("beamSpot");
00060
00061
00062 theTrajectoryFlag = parameterSet.getUntrackedParameter<bool>("PutTrajectoryIntoEvent",true);
00063
00064 theL2SeededTkLabel = parameterSet.getUntrackedParameter<string>("MuonSeededTracksInstance",string());
00065
00066 ParameterSet updatorPar = parameterSet.getParameter<ParameterSet>("MuonUpdatorAtVertexParameters");
00067 theUpdatorAtVtx = new MuonUpdatorAtVertex(updatorPar,service);
00068
00069 thePutTkTrackFlag = parameterSet.getUntrackedParameter<bool>("PutTkTrackIntoEvent",false);
00070 theSmoothTkTrackFlag = parameterSet.getUntrackedParameter<bool>("SmoothTkTrack",false);
00071 theAllowNoVtxFlag = parameterSet.getUntrackedParameter<bool>("AllowNoVertex",false);
00072 }
00073
00074 MuonTrackLoader::~MuonTrackLoader(){
00075 if(theUpdatorAtVtx) delete theUpdatorAtVtx;
00076 }
00077
00078 OrphanHandle<reco::TrackCollection>
00079 MuonTrackLoader::loadTracks(const TrajectoryContainer& trajectories,
00080 Event& event, const string& instance, bool reallyDoSmoothing) {
00081 std::vector<bool> dummyVecBool;
00082 return loadTracks(trajectories, event, dummyVecBool, instance, reallyDoSmoothing);
00083 }
00084
00085 OrphanHandle<reco::TrackCollection>
00086 MuonTrackLoader::loadTracks(const TrajectoryContainer& trajectories,
00087 Event& event, std::vector<bool>& tkBoolVec,
00088 const string& instance, bool reallyDoSmoothing) {
00089
00090 const bool doSmoothing = theSmoothingStep && reallyDoSmoothing;
00091
00092 const string metname = "Muon|RecoMuon|MuonTrackLoader";
00093
00094
00095 auto_ptr<reco::TrackCollection> trackCollection(new reco::TrackCollection());
00096
00097 reco::TrackRefProd trackCollectionRefProd = event.getRefBeforePut<reco::TrackCollection>(instance);
00098
00099
00100 auto_ptr<reco::TrackCollection> updatedAtVtxTrackCollection(new reco::TrackCollection());
00101
00102 reco::TrackRefProd trackUpdatedCollectionRefProd;
00103 if(theUpdatingAtVtx) trackUpdatedCollectionRefProd = event.getRefBeforePut<reco::TrackCollection>(instance+"UpdatedAtVtx");
00104
00105
00106 auto_ptr<reco:: TrackToTrackMap> trackToTrackmap(new reco::TrackToTrackMap);
00107
00108
00109 auto_ptr<reco::TrackExtraCollection> trackExtraCollection(new reco::TrackExtraCollection() );
00110
00111 reco::TrackExtraRefProd trackExtraCollectionRefProd = event.getRefBeforePut<reco::TrackExtraCollection>(instance);
00112
00113
00114 auto_ptr<TrackingRecHitCollection> recHitCollection(new TrackingRecHitCollection() );
00115
00116 TrackingRecHitRefProd recHitCollectionRefProd = event.getRefBeforePut<TrackingRecHitCollection>(instance);
00117
00118
00119 auto_ptr<vector<Trajectory> > trajectoryCollection(new vector<Trajectory>);
00120
00121
00122 std::auto_ptr<TrajTrackAssociationCollection> trajTrackMap( new TrajTrackAssociationCollection() );
00123
00124
00125 if ( trajectories.empty() ) {
00126 event.put(recHitCollection,instance);
00127 event.put(trackExtraCollection,instance);
00128 if(theTrajectoryFlag) {
00129 event.put(trajectoryCollection,instance);
00130 event.put( trajTrackMap, instance );
00131 }
00132 if(theUpdatingAtVtx){
00133 event.put(trackToTrackmap);
00134 event.put(updatedAtVtxTrackCollection,instance+"UpdatedAtVtx");
00135 }
00136 return event.put(trackCollection,instance);
00137 }
00138
00139 edm::Handle<reco::BeamSpot> beamSpot;
00140 event.getByLabel(theBeamSpotInputTag, beamSpot);
00141
00142 LogTrace(metname) << "Create the collection of Tracks";
00143
00144 reco::TrackRef::key_type trackIndex = 0;
00145 reco::TrackRef::key_type trackUpdatedIndex = 0;
00146
00147 reco::TrackExtraRef::key_type trackExtraIndex = 0;
00148 TrackingRecHitRef::key_type recHitsIndex = 0;
00149
00150 edm::Ref<reco::TrackCollection>::key_type iTkRef = 0;
00151 edm::Ref< std::vector<Trajectory> >::key_type iTjRef = 0;
00152 std::map<unsigned int, unsigned int> tjTkMap;
00153
00154 if(doSmoothing)
00155 theService->eventSetup().get<TrajectoryFitter::Record>().get(theSmootherName,theSmoother);
00156
00157 unsigned int tjCnt = 0;
00158 for(TrajectoryContainer::const_iterator rawTrajectory = trajectories.begin();
00159 rawTrajectory != trajectories.end(); ++rawTrajectory, ++tjCnt){
00160
00161 Trajectory &trajectory = **rawTrajectory;
00162
00163 if(doSmoothing){
00164 vector<Trajectory> trajectoriesSM = theSmoother->trajectories(**rawTrajectory);
00165
00166 if(!trajectoriesSM.empty()) {
00167 const edm::RefToBase<TrajectorySeed> tmpSeedRef = (**rawTrajectory).seedRef();
00168 trajectory = trajectoriesSM.front();
00169 trajectory.setSeedRef(tmpSeedRef);
00170 LogDebug(metname) << "theSeedRef.isNonnull " << trajectory.seedRef().isNonnull();
00171 } else
00172 LogInfo(metname)<<"The trajectory has not been smoothed!"<<endl;
00173 }
00174
00175 if(theTrajectoryFlag) {
00176 trajectoryCollection->push_back(trajectory);
00177 iTjRef++;
00178 }
00179
00180
00181 Trajectory::RecHitContainer transHits = trajectory.recHits();
00182
00183 if ( trajectory.direction() == oppositeToMomentum)
00184 reverse(transHits.begin(),transHits.end());
00185
00186
00187
00188 pair<bool,reco::Track> resultOfTrackExtrapAtPCA = buildTrackAtPCA(trajectory, *beamSpot);
00189
00190
00191 if(!resultOfTrackExtrapAtPCA.first) {
00192 delete *rawTrajectory;
00193 continue;
00194 }
00195
00196
00197 reco::Track &track = resultOfTrackExtrapAtPCA.second;
00198
00199
00200 reco::TrackExtra trackExtra = buildTrackExtra( trajectory );
00201
00202
00203 reco::TrackExtraRef trackExtraRef(trackExtraCollectionRefProd, trackExtraIndex++ );
00204
00205
00206 track.setExtra(trackExtraRef);
00207
00208
00209 pair<bool,reco::Track> updateResult(false,reco::Track());
00210
00211 if(theUpdatingAtVtx){
00212
00213 updateResult = buildTrackUpdatedAtPCA(track, *beamSpot);
00214
00215 if(!updateResult.first) ++trackIndex;
00216 else{
00217
00218
00219 updateResult.second.setExtra(trackExtraRef);
00220
00221
00222 trackToTrackmap->insert(reco::TrackRef(trackCollectionRefProd,trackIndex++),
00223 reco::TrackRef(trackUpdatedCollectionRefProd,trackUpdatedIndex++));
00224 }
00225 }
00226
00227
00228 for (Trajectory::RecHitContainer::const_iterator recHit = transHits.begin();
00229 recHit != transHits.end(); ++recHit) {
00230 TrackingRecHit *singleHit = (**recHit).hit()->clone();
00231 track.appendHitPattern( *singleHit);
00232 if(theUpdatingAtVtx && updateResult.first) updateResult.second.appendHitPattern(*singleHit);
00233 recHitCollection->push_back( singleHit );
00234
00235 trackExtra.add(TrackingRecHitRef(recHitCollectionRefProd, recHitsIndex++ ));
00236 }
00237
00238
00239 trackExtraCollection->push_back(trackExtra);
00240
00241
00242 trackCollection->push_back(track);
00243 iTkRef++;
00244 LogTrace(metname) << "Debug Track being loaded pt "<< track.pt();
00245
00246 if(theUpdatingAtVtx && updateResult.first)
00247 updatedAtVtxTrackCollection->push_back(updateResult.second);
00248
00249
00250
00251
00252 delete *rawTrajectory;
00253
00254 if(tkBoolVec.size()>tjCnt) tkBoolVec[tjCnt] = true;
00255 if(theTrajectoryFlag) tjTkMap[iTjRef-1] = iTkRef-1;
00256 }
00257
00258
00259
00260
00261 LogTrace(metname) << "put the Collections in the event";
00262 event.put(recHitCollection,instance);
00263 event.put(trackExtraCollection,instance);
00264
00265 OrphanHandle<reco::TrackCollection> returnTrackHandle;
00266 OrphanHandle<reco::TrackCollection> nonUpdatedHandle;
00267 if(theUpdatingAtVtx){
00268 nonUpdatedHandle = event.put(trackCollection,instance);
00269 event.put(trackToTrackmap);
00270 returnTrackHandle = event.put(updatedAtVtxTrackCollection,instance+"UpdatedAtVtx");
00271 }
00272 else {
00273 returnTrackHandle = event.put(trackCollection,instance);
00274 nonUpdatedHandle = returnTrackHandle;
00275 }
00276
00277 if ( theTrajectoryFlag ) {
00278 OrphanHandle<std::vector<Trajectory> > rTrajs = event.put(trajectoryCollection,instance);
00279
00280 for ( std::map<unsigned int, unsigned int>::iterator i = tjTkMap.begin();
00281 i != tjTkMap.end(); i++ ) {
00282 trajTrackMap->insert( edm::Ref<std::vector<Trajectory> >( rTrajs, (*i).first ),
00283 edm::Ref<reco::TrackCollection>( nonUpdatedHandle, (*i).second ) );
00284 }
00285 event.put( trajTrackMap, instance );
00286 }
00287
00288 return returnTrackHandle;
00289 }
00290
00291 OrphanHandle<reco::MuonTrackLinksCollection>
00292 MuonTrackLoader::loadTracks(const CandidateContainer& muonCands,
00293 Event& event) {
00294
00295 const string metname = "Muon|RecoMuon|MuonTrackLoader";
00296
00297
00298 auto_ptr<reco::MuonTrackLinksCollection> trackLinksCollection(new reco::MuonTrackLinksCollection());
00299
00300
00301 if ( muonCands.empty() ) {
00302 auto_ptr<reco::TrackExtraCollection> trackExtraCollection(new reco::TrackExtraCollection() );
00303 auto_ptr<TrackingRecHitCollection> recHitCollection(new TrackingRecHitCollection() );
00304 auto_ptr<reco::TrackCollection> trackCollection( new reco::TrackCollection() );
00305
00306 event.put(recHitCollection);
00307 event.put(trackExtraCollection);
00308 event.put(trackCollection);
00309
00310
00311 if(thePutTkTrackFlag){
00312
00313 TrajectoryContainer trackerTrajs;
00314 loadTracks(trackerTrajs, event, theL2SeededTkLabel, theSmoothTkTrackFlag);
00315 }
00316
00317 return event.put(trackLinksCollection);
00318 }
00319
00320
00321 TrajectoryContainer combinedTrajs;
00322 TrajectoryContainer trackerTrajs;
00323 for (CandidateContainer::const_iterator it = muonCands.begin(); it != muonCands.end(); ++it) {
00324 LogDebug(metname) << "Loader glbSeedRef " << (*it)->trajectory()->seedRef().isNonnull();
00325 if ((*it)->trackerTrajectory() ) LogDebug(metname) << " " << "tkSeedRef " << (*it)->trackerTrajectory()->seedRef().isNonnull();
00326
00327 combinedTrajs.push_back((*it)->trajectory());
00328 if ( thePutTkTrackFlag ) trackerTrajs.push_back((*it)->trackerTrajectory());
00329
00330 else {
00331 if ((*it)->trackerTrajectory()) delete ((*it)->trackerTrajectory());
00332 }
00333
00334
00335
00336
00337
00338
00339
00340 }
00341
00342
00343
00344 LogTrace(metname) << "Build combinedTracks";
00345 std::vector<bool> combTksVec(combinedTrajs.size(), false);
00346 OrphanHandle<reco::TrackCollection> combinedTracks = loadTracks(combinedTrajs, event, combTksVec);
00347
00348 OrphanHandle<reco::TrackCollection> trackerTracks;
00349 std::vector<bool> trackerTksVec(trackerTrajs.size(), false);
00350 if(thePutTkTrackFlag) {
00351 LogTrace(metname) << "Build trackerTracks: "
00352 << trackerTrajs.size();
00353 trackerTracks = loadTracks(trackerTrajs, event, trackerTksVec, theL2SeededTkLabel, theSmoothTkTrackFlag);
00354 } else {
00355 for (TrajectoryContainer::iterator it = trackerTrajs.begin(); it != trackerTrajs.end(); ++it) {
00356 if(*it) delete *it;
00357 }
00358 }
00359
00360 LogTrace(metname) << "Set the final links in the MuonTrackLinks collection";
00361
00362 unsigned int candposition(0), position(0), tkposition(0);
00363
00364
00365
00366 for (CandidateContainer::const_iterator it = muonCands.begin(); it != muonCands.end(); ++it, ++candposition) {
00367
00368
00369
00370
00371
00372
00373 if(combTksVec[candposition]) {
00374 reco::TrackRef combinedTR(combinedTracks, position++);
00375
00376
00377
00378 reco::MuonTrackLinks links;
00379 links.setStandAloneTrack((*it)->muonTrack());
00380 links.setTrackerTrack((*it)->trackerTrack());
00381 links.setGlobalTrack(combinedTR);
00382
00383 if(thePutTkTrackFlag && trackerTksVec[candposition]) {
00384 reco::TrackRef trackerTR(trackerTracks, tkposition++);
00385 links.setTrackerTrack(trackerTR);
00386 }
00387
00388 trackLinksCollection->push_back(links);
00389 }
00390
00391 else {
00392 if(thePutTkTrackFlag && trackerTksVec[candposition]) tkposition++;
00393 }
00394
00395 delete *it;
00396 }
00397
00398 if( thePutTkTrackFlag && trackerTracks.isValid() && !(combinedTracks->size() > 0 && trackerTracks->size() > 0 ) )
00399 LogWarning(metname)<<"The MuonTrackLinkCollection is incomplete";
00400
00401
00402 LogTrace(metname) << "put the MuonCollection in the event" << "\n";
00403
00404 return event.put(trackLinksCollection);
00405 }
00406
00407 OrphanHandle<reco::TrackCollection>
00408 MuonTrackLoader::loadTracks(const TrajectoryContainer& trajectories,
00409 Event& event, std::vector<std::pair<Trajectory*,reco::TrackRef> > miniMap, const string& instance, bool reallyDoSmoothing) {
00410
00411 const bool doSmoothing = theSmoothingStep && reallyDoSmoothing;
00412
00413 const string metname = "Muon|RecoMuon|MuonTrackLoader|TevMuonTrackLoader";
00414
00415 LogDebug(metname)<<"TeV LoadTracks instance: " << instance;
00416
00417
00418 auto_ptr<reco::TrackCollection> trackCollection(new reco::TrackCollection());
00419
00420 reco::TrackRefProd trackCollectionRefProd = event.getRefBeforePut<reco::TrackCollection>(instance);
00421
00422
00423 auto_ptr<reco:: TrackToTrackMap> trackToTrackmap(new reco::TrackToTrackMap);
00424
00425
00426 auto_ptr<reco::TrackExtraCollection> trackExtraCollection(new reco::TrackExtraCollection() );
00427
00428 reco::TrackExtraRefProd trackExtraCollectionRefProd = event.getRefBeforePut<reco::TrackExtraCollection>(instance);
00429
00430
00431 auto_ptr<TrackingRecHitCollection> recHitCollection(new TrackingRecHitCollection() );
00432
00433 TrackingRecHitRefProd recHitCollectionRefProd = event.getRefBeforePut<TrackingRecHitCollection>(instance);
00434
00435
00436 auto_ptr<vector<Trajectory> > trajectoryCollection(new vector<Trajectory>);
00437
00438
00439 std::auto_ptr<TrajTrackAssociationCollection> trajTrackMap( new TrajTrackAssociationCollection() );
00440
00441
00442 if ( trajectories.empty() ) {
00443 event.put(recHitCollection,instance);
00444 event.put(trackExtraCollection,instance);
00445 if(theTrajectoryFlag) {
00446 event.put(trajectoryCollection,instance);
00447 event.put( trajTrackMap, instance );
00448 }
00449 event.put(trackToTrackmap, instance);
00450 return event.put(trackCollection,instance);
00451 }
00452
00453 LogTrace(metname) << "Create the collection of Tracks";
00454
00455 edm::Handle<reco::BeamSpot> beamSpot;
00456 event.getByLabel(theBeamSpotInputTag,beamSpot);
00457
00458 reco::TrackRef::key_type trackIndex = 0;
00459
00460
00461 reco::TrackExtraRef::key_type trackExtraIndex = 0;
00462 TrackingRecHitRef::key_type recHitsIndex = 0;
00463
00464 edm::Ref<reco::TrackCollection>::key_type iTkRef = 0;
00465 edm::Ref< std::vector<Trajectory> >::key_type iTjRef = 0;
00466 std::map<unsigned int, unsigned int> tjTkMap;
00467
00468 if(doSmoothing)
00469 theService->eventSetup().get<TrajectoryFitter::Record>().get(theSmootherName,theSmoother);
00470
00471
00472 for(TrajectoryContainer::const_iterator rawTrajectory = trajectories.begin();
00473 rawTrajectory != trajectories.end(); ++rawTrajectory){
00474
00475 reco::TrackRef glbRef;
00476 std::vector<std::pair<Trajectory*,reco::TrackRef> >::const_iterator mmit;
00477 for(mmit = miniMap.begin();mmit!=miniMap.end();++mmit){
00478 if(mmit->first == *rawTrajectory) glbRef = mmit->second;
00479 }
00480
00481 Trajectory &trajectory = **rawTrajectory;
00482
00483 if(doSmoothing){
00484 vector<Trajectory> trajectoriesSM = theSmoother->trajectories(**rawTrajectory);
00485
00486 if(!trajectoriesSM.empty()) {
00487 const edm::RefToBase<TrajectorySeed> tmpSeedRef = (**rawTrajectory).seedRef();
00488 trajectory = trajectoriesSM.front();
00489 trajectory.setSeedRef(tmpSeedRef);
00490 } else
00491 LogInfo(metname)<<"The trajectory has not been smoothed!"<<endl;
00492 }
00493
00494 if(theTrajectoryFlag) {
00495 trajectoryCollection->push_back(trajectory);
00496 iTjRef++;
00497 }
00498
00499
00500 Trajectory::RecHitContainer transHits = trajectory.recHits();
00501
00502 if ( trajectory.direction() == oppositeToMomentum)
00503 reverse(transHits.begin(),transHits.end());
00504
00505
00506
00507 pair<bool,reco::Track> resultOfTrackExtrapAtPCA = buildTrackAtPCA(trajectory, *beamSpot);
00508
00509
00510 if(!resultOfTrackExtrapAtPCA.first) {
00511
00512 delete *rawTrajectory;
00513 continue;
00514 }
00515
00516
00517 reco::Track &track = resultOfTrackExtrapAtPCA.second;
00518
00519
00520 reco::TrackExtra trackExtra = buildTrackExtra( trajectory );
00521
00522
00523 reco::TrackExtraRef trackExtraRef(trackExtraCollectionRefProd, trackExtraIndex++ );
00524
00525
00526 track.setExtra(trackExtraRef);
00527
00528
00529 trackToTrackmap->insert(glbRef,
00530 reco::TrackRef(trackCollectionRefProd,trackIndex++));
00531
00532
00533 pair<bool,reco::Track> updateResult(false,reco::Track());
00534
00535
00536 for (Trajectory::RecHitContainer::const_iterator recHit = transHits.begin();
00537 recHit != transHits.end(); ++recHit) {
00538 TrackingRecHit *singleHit = (**recHit).hit()->clone();
00539 track.appendHitPattern( *singleHit);
00540 if(theUpdatingAtVtx && updateResult.first) updateResult.second.appendHitPattern( *singleHit);
00541 recHitCollection->push_back( singleHit );
00542
00543 trackExtra.add(TrackingRecHitRef(recHitCollectionRefProd, recHitsIndex++ ));
00544 }
00545
00546
00547 trackExtraCollection->push_back(trackExtra);
00548
00549
00550 trackCollection->push_back(track);
00551 iTkRef++;
00552 LogTrace(metname) << "Debug Track being loaded pt "<< track.pt();
00553
00554
00555
00556
00557 delete *rawTrajectory;
00558
00559 if(theTrajectoryFlag) tjTkMap[iTjRef-1] = iTkRef-1;
00560 }
00561
00562
00563
00564
00565 LogTrace(metname) << "put the Collections in the event";
00566 event.put(recHitCollection,instance);
00567 event.put(trackExtraCollection,instance);
00568
00569 OrphanHandle<reco::TrackCollection> returnTrackHandle;
00570 OrphanHandle<reco::TrackCollection> nonUpdatedHandle;
00571 if(theUpdatingAtVtx){
00572 }
00573 else {
00574 event.put(trackToTrackmap,instance);
00575 returnTrackHandle = event.put(trackCollection,instance);
00576 nonUpdatedHandle = returnTrackHandle;
00577 }
00578
00579 if ( theTrajectoryFlag ) {
00580 OrphanHandle<std::vector<Trajectory> > rTrajs = event.put(trajectoryCollection,instance);
00581
00582 for ( std::map<unsigned int, unsigned int>::iterator i = tjTkMap.begin();
00583 i != tjTkMap.end(); i++ ) {
00584 trajTrackMap->insert( edm::Ref<std::vector<Trajectory> >( rTrajs, (*i).first ),
00585 edm::Ref<reco::TrackCollection>( nonUpdatedHandle, (*i).second ) );
00586 }
00587 event.put( trajTrackMap, instance );
00588 }
00589
00590 return returnTrackHandle;
00591 }
00592
00593
00594 pair<bool,reco::Track> MuonTrackLoader::buildTrackAtPCA(const Trajectory& trajectory, const reco::BeamSpot &beamSpot) const {
00595
00596 const string metname = "Muon|RecoMuon|MuonTrackLoader";
00597
00598 MuonPatternRecoDumper debug;
00599
00600
00601 TrajectoryStateOnSurface innerTSOS = trajectory.geometricalInnermostState();
00602
00603
00604 LogTrace(metname) << "Propagate to PCA...";
00605 pair<bool,FreeTrajectoryState>
00606 extrapolationResult = theUpdatorAtVtx->propagate(innerTSOS, beamSpot);
00607 FreeTrajectoryState ftsAtVtx;
00608
00609 if(extrapolationResult.first)
00610 ftsAtVtx = extrapolationResult.second;
00611 else{
00612 if(TrackerBounds::isInside(innerTSOS.globalPosition())){
00613 LogInfo(metname) << "Track in the Tracker: taking the innermost state instead of the state at PCA";
00614 ftsAtVtx = *innerTSOS.freeState();
00615 }
00616 else{
00617 if ( theAllowNoVtxFlag ) {
00618 LogInfo(metname) << "Propagation to PCA failed, taking the innermost state instead of the state at PCA";
00619 ftsAtVtx = *innerTSOS.freeState();
00620 } else {
00621 LogInfo(metname) << "Stand Alone track: this track will be rejected";
00622 return pair<bool,reco::Track>(false,reco::Track());
00623 }
00624 }
00625 }
00626
00627 LogTrace(metname) << "TSOS after the extrapolation at vtx";
00628 LogTrace(metname) << debug.dumpFTS(ftsAtVtx);
00629
00630 GlobalPoint pca = ftsAtVtx.position();
00631 math::XYZPoint persistentPCA(pca.x(),pca.y(),pca.z());
00632 GlobalVector p = ftsAtVtx.momentum();
00633 math::XYZVector persistentMomentum(p.x(),p.y(),p.z());
00634
00635 bool bon = true;
00636 if(fabs(theService->magneticField()->inTesla(GlobalPoint(0,0,0)).z()) < 0.01) bon=false;
00637 double ndof = trajectory.ndof(bon);
00638
00639 reco::Track track(trajectory.chiSquared(),
00640 ndof,
00641 persistentPCA,
00642 persistentMomentum,
00643 ftsAtVtx.charge(),
00644 ftsAtVtx.curvilinearError());
00645
00646 return pair<bool,reco::Track>(true,track);
00647 }
00648
00649
00650 pair<bool,reco::Track> MuonTrackLoader::buildTrackUpdatedAtPCA(const reco::Track &track, const reco::BeamSpot &beamSpot) const {
00651
00652 const string metname = "Muon|RecoMuon|MuonTrackLoader";
00653 MuonPatternRecoDumper debug;
00654
00655
00656 reco::TransientTrack transientTrack(track,
00657 &*theService->magneticField(),
00658 theService->trackingGeometry());
00659
00660 LogTrace(metname) << "Apply the vertex constraint";
00661 pair<bool,FreeTrajectoryState> updateResult = theUpdatorAtVtx->update(transientTrack,beamSpot);
00662
00663 if(!updateResult.first){
00664 return pair<bool,reco::Track>(false,reco::Track());
00665 }
00666
00667 LogTrace(metname) << "FTS after the vertex constraint";
00668 FreeTrajectoryState &ftsAtVtx = updateResult.second;
00669
00670 LogTrace(metname) << debug.dumpFTS(ftsAtVtx);
00671
00672 GlobalPoint pca = ftsAtVtx.position();
00673 math::XYZPoint persistentPCA(pca.x(),pca.y(),pca.z());
00674 GlobalVector p = ftsAtVtx.momentum();
00675 math::XYZVector persistentMomentum(p.x(),p.y(),p.z());
00676
00677 reco::Track updatedTrack(track.chi2(),
00678 track.ndof(),
00679 persistentPCA,
00680 persistentMomentum,
00681 ftsAtVtx.charge(),
00682 ftsAtVtx.curvilinearError());
00683
00684 return pair<bool,reco::Track>(true,updatedTrack);
00685 }
00686
00687
00688 reco::TrackExtra MuonTrackLoader::buildTrackExtra(const Trajectory& trajectory) const {
00689
00690 const string metname = "Muon|RecoMuon|MuonTrackLoader";
00691
00692 const Trajectory::RecHitContainer transRecHits = trajectory.recHits();
00693
00694
00695
00696
00697
00698 TrajectoryStateOnSurface outerTSOS;
00699 TrajectoryStateOnSurface innerTSOS;
00700 unsigned int innerId=0, outerId=0;
00701 TrajectoryMeasurement::ConstRecHitPointer outerRecHit;
00702 DetId outerDetId;
00703
00704 if (trajectory.direction() == alongMomentum) {
00705 LogTrace(metname)<<"alongMomentum";
00706 outerTSOS = trajectory.lastMeasurement().updatedState();
00707 innerTSOS = trajectory.firstMeasurement().updatedState();
00708 outerId = trajectory.lastMeasurement().recHit()->geographicalId().rawId();
00709 innerId = trajectory.firstMeasurement().recHit()->geographicalId().rawId();
00710 outerRecHit = trajectory.lastMeasurement().recHit();
00711 outerDetId = trajectory.lastMeasurement().recHit()->geographicalId();
00712 }
00713 else if (trajectory.direction() == oppositeToMomentum) {
00714 LogTrace(metname)<<"oppositeToMomentum";
00715 outerTSOS = trajectory.firstMeasurement().updatedState();
00716 innerTSOS = trajectory.lastMeasurement().updatedState();
00717 outerId = trajectory.firstMeasurement().recHit()->geographicalId().rawId();
00718 innerId = trajectory.lastMeasurement().recHit()->geographicalId().rawId();
00719 outerRecHit = trajectory.firstMeasurement().recHit();
00720 outerDetId = trajectory.firstMeasurement().recHit()->geographicalId();
00721 }
00722 else LogError(metname)<<"Wrong propagation direction!";
00723
00724 const GeomDet *outerDet = theService->trackingGeometry()->idToDet(outerDetId);
00725 GlobalPoint outerTSOSPos = outerTSOS.globalParameters().position();
00726 bool inside = outerDet->surface().bounds().inside(outerDet->toLocal(outerTSOSPos));
00727
00728
00729 GlobalPoint hitPos = (outerRecHit->isValid()) ? outerRecHit->globalPosition() : outerTSOS.globalParameters().position() ;
00730
00731 if(!inside) {
00732 LogTrace(metname)<<"The Global Muon outerMostMeasurementState is not compatible with the recHit detector! Setting outerMost postition to recHit position if recHit isValid: " << outerRecHit->isValid();
00733 LogTrace(metname)<<"From " << outerTSOSPos << " to " << hitPos;
00734 }
00735
00736
00737
00738 GlobalPoint v = (inside) ? outerTSOSPos : hitPos ;
00739 GlobalVector p = outerTSOS.globalParameters().momentum();
00740 math::XYZPoint outpos( v.x(), v.y(), v.z() );
00741 math::XYZVector outmom( p.x(), p.y(), p.z() );
00742
00743 v = innerTSOS.globalParameters().position();
00744 p = innerTSOS.globalParameters().momentum();
00745 math::XYZPoint inpos( v.x(), v.y(), v.z() );
00746 math::XYZVector inmom( p.x(), p.y(), p.z() );
00747
00748 reco::TrackExtra trackExtra(outpos, outmom, true, inpos, inmom, true,
00749 outerTSOS.curvilinearError(), outerId,
00750 innerTSOS.curvilinearError(), innerId,
00751 trajectory.direction(),trajectory.seedRef());
00752
00753 return trackExtra;
00754
00755 }