CMS 3D CMS Logo

/afs/cern.ch/work/a/aaltunda/public/www/CMSSW_6_2_5/src/RecoEgamma/EgammaPhotonAlgos/src/InOutConversionSeedFinder.cc

Go to the documentation of this file.
00001 #include "RecoEgamma/EgammaPhotonAlgos/interface/InOutConversionSeedFinder.h"
00002 #include "RecoEgamma/EgammaPhotonAlgos/interface/ConversionBarrelEstimator.h"
00003 #include "RecoEgamma/EgammaPhotonAlgos/interface/ConversionForwardEstimator.h"
00004 
00005 #include "RecoEgamma/EgammaPhotonAlgos/interface/ConversionFastHelix.h"
00006 
00007 // Field
00008 //
00009 #include "DataFormats/CLHEP/interface/AlgebraicObjects.h"
00010 // Geometry
00011 //
00012 #include "TrackingTools/TrajectoryParametrization/interface/GlobalTrajectoryParameters.h"
00013 #include "TrackingTools/TransientTrackingRecHit/interface/TransientTrackingRecHit.h"
00014 #include "TrackingTools/TrajectoryState/interface/TrajectoryStateTransform.h"
00015 //
00016 //
00017 //
00018 
00019 InOutConversionSeedFinder::InOutConversionSeedFinder( const edm::ParameterSet& conf ):
00020   ConversionSeedFinder( conf ), conf_(conf)  
00021 {
00022   
00023   
00024   // std::cout << " InOutConversionSeedFinder CTOR " << "\n";      
00025     
00026   maxNumberOfInOutSeedsPerInputTrack_ =  conf_.getParameter<int>("maxNumOfSeedsInOut");
00027   //the2ndHitdphi_ = 0.008; 
00028   the2ndHitdphi_ = 0.01; 
00029   the2ndHitdzConst_ = 5.;
00030   the2ndHitdznSigma_ = 2.;
00031  
00032   
00033 }
00034 
00035 
00036 
00037 InOutConversionSeedFinder::~InOutConversionSeedFinder() {
00038  //std::cout << " InOutConversionSeedFinder DTOR " << "\n";
00039 }
00040 
00041 
00042 
00043 void InOutConversionSeedFinder::makeSeeds( const edm::Handle<edm::View<reco::CaloCluster> > &  allBC )  const  {
00044   
00045 
00046   //std::cout << "  InOutConversionSeedFinder::makeSeeds() " << "\n";
00047   theSeeds_.clear();
00048   //std::cout << " Check Calo cluster collection size " << allBC->size() << "\n";  
00049   bcCollection_= allBC;
00050   
00051   
00052   findLayers();
00053   
00054   
00055   fillClusterSeeds();
00056   //std::cout << "Built vector of seeds of size  " << theSeeds_.size() <<  "\n" ;
00057   
00058   
00059   theOutInTracks_.clear();
00060   inputTracks_.clear();
00061   theFirstMeasurements_.clear();
00062   
00063 }
00064 
00065 
00066 void InOutConversionSeedFinder::fillClusterSeeds() const {
00067   
00068   std::vector<Trajectory>::const_iterator outInTrackItr;
00069   
00070  //std::cout << "  InOutConversionSeedFinder::fillClusterSeeds outInTracks_.size " << theOutInTracks_.size() << "\n";
00071   //Start looking for seeds for both of the 2 best tracks from the inward tracking
00072   
00074   /*
00075   for(outInTrackItr = theOutInTracks_.begin(); outInTrackItr != theOutInTracks_.end();  ++outInTrackItr) {
00076 
00077 
00078    //std::cout << " InOutConversionSeedFinder::fillClusterSeeds out in input track hits " << (*outInTrackItr).foundHits() << "\n";
00079     DetId tmpId = DetId( (*outInTrackItr).seed().startingState().detId());
00080     const GeomDet* tmpDet  = this->getMeasurementTracker()->geomTracker()->idToDet( tmpId );
00081     GlobalVector gv = tmpDet->surface().toGlobal( (*outInTrackItr).seed().startingState().parameters().momentum() );
00082 
00083 
00084    //std::cout << " InOutConversionSeedFinder::fillClusterSeed was built from seed position " <<gv   <<  " charge " << (*outInTrackItr).seed().startingState().parameters().charge() << "\n";
00085 
00086     Trajectory::DataContainer m=  outInTrackItr->measurements();
00087     int nHit=0;
00088     for (Trajectory::DataContainer::iterator itm = m.begin(); itm != m.end(); ++itm) {
00089       if ( itm->recHit()->isValid()  ) {
00090         nHit++;
00091         //std::cout << nHit << ")  Valid RecHit global position " << itm->recHit()->globalPosition() << " R " <<  itm->recHit()->globalPosition().perp() << " phi " << itm->recHit()->globalPosition().phi() << " eta " << itm->recHit()->globalPosition().eta() << "\n";
00092       } 
00093 
00094     }
00095 
00096   }
00097 
00098   */
00099 
00100 
00101   //Start looking for seeds for both of the 2 best tracks from the inward tracking
00102   for(outInTrackItr = theOutInTracks_.begin(); outInTrackItr != theOutInTracks_.end();  ++outInTrackItr) {
00103    //std::cout << " InOutConversionSeedFinder::fillClusterSeeds out in input track hits " << (*outInTrackItr).foundHits() << "\n";
00104     nSeedsPerInputTrack_=0;    
00105     
00106     //Find the first valid hit of the track
00107     // Measurements are ordered according to the direction in which the trajectories were built
00108     std::vector<TrajectoryMeasurement> measurements = (*outInTrackItr).measurements();
00109     
00110     std::vector<const DetLayer*> allLayers=layerList();
00111     
00112     //std::cout << "  InOutConversionSeedFinder::fill clusterSeed allLayers.size " <<  allLayers.size() << "\n";
00113     for(unsigned int i = 0; i < allLayers.size(); ++i) {
00114       //std::cout <<  " allLayers " << allLayers[i] << "\n"; 
00115       printLayer(i);
00116      }
00117     
00118     
00119     
00120     std::vector<const DetLayer*> myLayers;
00121     myLayers.clear();    
00122     std::vector<TrajectoryMeasurement>::reverse_iterator measurementItr;    
00123     std::vector<TrajectoryMeasurement*> myItr;
00124     // TrajectoryMeasurement* myPointer=0;
00125     myPointer=0;
00126     //std::cout << "  InOutConversionSeedFinder::fillClusterSeeds measurements.size " << measurements.size() <<"\n";
00127     
00128     for(measurementItr = measurements.rbegin() ; measurementItr != measurements.rend();  ++measurementItr) {
00129     
00130 
00131       if( (*measurementItr).recHit()->isValid()) {
00132         
00133         //std::cout << "  InOutConversionSeedFinder::fillClusterSeeds measurement on  layer  " << measurementItr->layer() <<   " " <<&(*measurementItr) <<  " position " << measurementItr->recHit()->globalPosition() <<   " R " << sqrt( measurementItr->recHit()->globalPosition().x()*measurementItr->recHit()->globalPosition().x() + measurementItr->recHit()->globalPosition().y()*measurementItr->recHit()->globalPosition().y() ) << " Z " << measurementItr->recHit()->globalPosition().z() << " phi " <<  measurementItr->recHit()->globalPosition().phi() << "\n";
00134         
00135         
00136         myLayers.push_back( measurementItr->layer() ) ; 
00137         myItr.push_back( &(*measurementItr) );
00138         
00139         
00140       }
00141     }
00142     
00143     
00144     
00145    //std::cout << " InOutConversionSeedFinder::fillClusterSeed myLayers.size " <<  myLayers.size() << "\n";
00146     //    for( unsigned int i = 0; i < myLayers.size(); ++i) {
00148     // }
00149     
00150     
00151     if ( myItr.size()==0 ) {
00152       //std::cout << "HORRENDOUS ERROR!  No meas on track!" << "\n";
00153     }      
00154     unsigned int ilayer;
00155     for(ilayer = 0; ilayer < allLayers.size(); ++ilayer) {
00156       //std::cout <<  " allLayers in the search loop  " << allLayers[ilayer] <<  " " << myLayers[0] <<  "\n"; 
00157       if ( allLayers[ilayer] == myLayers[0]) {
00158         
00159         myPointer=myItr[0];
00160         
00161         //std::cout <<  " allLayers in the search loop   allLayers[ilayer] == myLayers[0])  " << allLayers[ilayer] <<  " " << myLayers[0] <<  " myPointer " << myPointer << "\n"; 
00162         
00163         //std::cout  << "Layer " << ilayer << "  contains the first valid measurement " << "\n";        
00164         printLayer(ilayer);     
00165         
00166         if ( (myLayers[0])->location() == GeomDetEnumerators::barrel ) {
00167           //      const BarrelDetLayer * barrelLayer = dynamic_cast<const BarrelDetLayer*>(myLayers[0]);
00168          //std::cout << " InOutConversionSeedFinder::fillClusterSeeds  **** firstHit found in Barrel on layer " << ilayer  << " R= " << barrelLayer->specificSurface().radius() <<   "\n";
00169         } else {
00170           //const ForwardDetLayer * forwardLayer = dynamic_cast<const ForwardDetLayer*>(myLayers[0]);
00171          //std::cout << " InOutwardConversionSeedFinder::fillClusterSeeds  **** firstHit found in Forw on layer " << ilayer  << " Z= " << forwardLayer->specificSurface().position().z() <<  "\n";
00172         }
00173         
00174         
00175         break;
00176         
00177       } else if ( allLayers[ilayer] == myLayers[1] )  {
00178         myPointer=myItr[1];
00179         
00180         //std::cout <<  " allLayers in the search loop   allLayers[ilayer] == myLayers[1])  " << allLayers[ilayer] <<  " " << myLayers[1] <<  " myPointer " << myPointer << "\n"; 
00181         
00182         //std::cout << "Layer " << ilayer << "  contains the first innermost  valid measurement " << "\n";      
00183         if ( (myLayers[1])->location() == GeomDetEnumerators::barrel ) {
00184           //      const BarrelDetLayer * barrelLayer = dynamic_cast<const BarrelDetLayer*>(myLayers[1]);
00185          //std::cout << " InOutConversionSeedFinder::fillClusterSeeds  **** 2ndHit found in Barrel on layer " << ilayer  << " R= " << barrelLayer->specificSurface().radius() <<   "\n"; 
00186         } else {
00187           //const ForwardDetLayer * forwardLayer = dynamic_cast<const ForwardDetLayer*>(myLayers[1]);
00188          //std::cout << " InOutwardConversionSeedFinder::fillClusterSeeds  ****  2ndHitfound on forw layer " << ilayer  << " Z= " << forwardLayer->specificSurface().position().z() <<  "\n";
00189         }
00190         
00191         
00192         
00193         break;
00194         
00195       }
00196     }
00197     
00198     
00199     
00200     if(ilayer == allLayers.size()) {
00201      //std::cout << "InOutConversionSeedFinder::fillClusterSeeds ERROR could not find layer on list" <<  "\n"; 
00202       return;
00203     }
00204     
00205     //PropagatorWithMaterial reversePropagator(oppositeToMomentum, 0.000511, &(*theMF_) );
00206     FreeTrajectoryState * fts = myPointer->updatedState().freeTrajectoryState();
00207     
00208    //std::cout << " InOutConversionSeedFinder::fillClusterSeeds First FTS charge " << fts->charge() << " Position " << fts->position() << " momentum " << fts->momentum() << " R " << sqrt(fts->position().x()*fts->position().x() + fts->position().y()* fts->position().y() ) << " Z " << fts->position().z() << " phi " << fts->position().phi() << " fts parameters " << fts->parameters() << "\n";
00209     
00210     
00211     while (ilayer > 0) {
00212       
00213       //std::cout << " InOutConversionSeedFinder::fillClusterSeeds looking for 2nd seed from layer " << ilayer << "\n";
00214       
00215       //   if ( (allLayers[ilayer])->location() == GeomDetEnumerators::barrel ) {const BarrelDetLayer * barrelLayer = dynamic_cast<const BarrelDetLayer*>(allLayers[ilayer]);
00216       //std::cout <<  " InOutConversionSeedFinder::fillClusterSeeds  ****  Barrel on layer " << ilayer  << " R= " << barrelLayer->specificSurface().radius() <<  "\n";     
00217       // } else {
00218         //const ForwardDetLayer * forwardLayer = dynamic_cast<const ForwardDetLayer*>(allLayers[ilayer]);
00219         //std::cout <<  " InOutConversionSeedFinder::fillClusterSeeds  ****  Forw on layer " << ilayer  << " Z= " << forwardLayer->specificSurface().position().z() << "\n";
00220       //      }
00221       
00222      
00223      const DetLayer * previousLayer = allLayers[ilayer];
00224      TrajectoryStateOnSurface  stateAtPreviousLayer;
00225      //std::cout << " InOutConversionSeedFinder::fillClusterSeeds previousLayer->surface() position before  " <<allLayers[ilayer] << " " <<  previousLayer->surface().position() << " layer location " << previousLayer->location() << "\n";   
00226      // Propagate to the previous layer
00227      // The present layer is actually included in the loop so that a partner can be searched for
00228      // Applying the propagator to the same layer does not do any harm. It simply does nothing
00229      
00230      //     const Propagator& newProp=thePropagatorOppositeToMomentum_;  
00231      //std::cout << " InOutConversionSeedFinder::fillClusterSeeds reversepropagator direction " << thePropagatorOppositeToMomentum_->propagationDirection()  << "\n";
00232      if (ilayer-1>0) { 
00233        
00234        if ( allLayers[ilayer] == myLayers[0] ) {
00235          //std::cout << " innermost hit R " << myPointer->recHit()->globalPosition().perp() << " Z " << myPointer->recHit()->globalPosition().z() << " phi " <<myPointer->recHit()->globalPosition().phi() << "\n";
00236          //std::cout << " surface R " << theTrackerGeom_->idToDet(  myPointer->recHit() ->geographicalId())->surface().position().perp() <<  " Z " <<  theTrackerGeom_->idToDet(  myPointer->recHit() ->geographicalId())->surface().position().z() << " phi " << theTrackerGeom_->idToDet(  myPointer->recHit() ->geographicalId())->surface().position().phi() << "\n";
00237          
00238          stateAtPreviousLayer= thePropagatorOppositeToMomentum_->propagate(*fts,   theTrackerGeom_->idToDet(  myPointer->recHit() ->geographicalId())->surface()   );
00239          
00240        } else {
00241          
00242          stateAtPreviousLayer= thePropagatorOppositeToMomentum_->propagate(*fts, previousLayer->surface() );
00243          //std::cout << " InOutConversionSeedFinder::fillClusterSeeds previousLayer->surface() position after " << previousLayer->surface().position() << " layer location " << previousLayer->location() <<   "\n";
00244          
00245        }
00246        
00247      } else if ( ilayer-1==0) {
00248        
00249        
00252        
00253        //stateAtPreviousLayer= thePropagatorOppositeToMomentum_->propagate(*fts,   theTrackerGeom_->idToDet(  myPointer->recHit() ->geographicalId())->surface()   );
00254        stateAtPreviousLayer= thePropagatorOppositeToMomentum_->propagate(*fts, previousLayer->surface() );      
00255        
00256      }
00257      
00258      if(!stateAtPreviousLayer.isValid()) {
00259        //std::cout << "InOutConversionSeedFinder::fillClusterSeeds ERROR:could not propagate back to layer "  << ilayer << "\n";
00261      } else {
00262        //std::cout << "InOutConversionSeedFinder::fillClusterSeeds  stateAtPreviousLayer is valid.  Propagating back to layer "  << ilayer << "\n";
00263        //std::cout << "InOutConversionSeedFinder::fillClusterSeeds stateAtPreviousLayer R  " << stateAtPreviousLayer.globalPosition().perp()  << " Z " << stateAtPreviousLayer.globalPosition().z() << " phi " <<  stateAtPreviousLayer.globalPosition().phi() << "\n";
00264        
00265        startSeed(fts,  stateAtPreviousLayer, -1, ilayer ); 
00266        
00267        
00268      }      
00269      
00270      --ilayer;
00271      
00272     }
00273     
00274     if ( ilayer == 0) {
00275       
00276 
00277       //     if ( (allLayers[ilayer])->location() == GeomDetEnumerators::barrel ) {const BarrelDetLayer * barrelLayer = dynamic_cast<const BarrelDetLayer*>(allLayers[ilayer]);
00278       // //std::cout <<  " InOutConversionSeedFinder::fillClusterSeeds  ****  Barrel on layer " << ilayer  << " R= " << barrelLayer->specificSurface().radius() <<  "\n";     
00279       // } else {
00280       //const ForwardDetLayer * forwardLayer = dynamic_cast<const ForwardDetLayer*>(allLayers[ilayer]);
00281        //std::cout <<  " InOutConversionSeedFinder::fillClusterSeeds  ****  Forw on layer " << ilayer  << " Z= " << forwardLayer->specificSurface().position().z() << "\n";
00282       // }
00283      const DetLayer * previousLayer = allLayers[ilayer];
00284      TrajectoryStateOnSurface  stateAtPreviousLayer;
00285      stateAtPreviousLayer= thePropagatorOppositeToMomentum_->propagate(*fts, previousLayer->surface() );
00286 
00287      if(!stateAtPreviousLayer.isValid()) {
00288        //std::cout << "InOutConversionSeedFinder::fillClusterSeeds ERROR:could not propagate back to layer "  << ilayer << "\n";
00290      } else {
00291        //std::cout << "InOutConversionSeedFinder::fillClusterSeeds  stateAtPreviousLayer is valid.  Propagating back to layer "  << ilayer << "\n";
00292        //std::cout << "InOutConversionSeedFinder::fillClusterSeeds stateAtPreviousLayer R  " << stateAtPreviousLayer.globalPosition().perp()  << " Z " << stateAtPreviousLayer.globalPosition().z() << " phi " <<  stateAtPreviousLayer.globalPosition().phi() << "\n";
00293        
00294        startSeed(fts,  stateAtPreviousLayer, -1, ilayer ); 
00295      }     
00296        
00297      
00298    }
00299 
00300     
00301     
00302     
00303   }  // End loop over Out In tracks
00304   
00305   
00306   
00307 }
00308 
00309 
00310 
00311 void InOutConversionSeedFinder::startSeed( FreeTrajectoryState * fts, const TrajectoryStateOnSurface & stateAtPreviousLayer, int charge, int ilayer  )  const {
00312   
00313   //std::cout << "InOutConversionSeedFinder::startSeed ilayer " << ilayer <<  "\n";
00314   // Get a list of basic clusters that are consistent with a track 
00315   // starting at the assumed conversion point with opp. charge to the 
00316   // inward track.  Loop over these basic clusters.
00317   track2Charge_ = charge*fts->charge();
00318   std::vector<const reco::CaloCluster*> bcVec;
00319  //std::cout << "InOutConversionSeedFinder::startSeed charge assumed for the in-out track  " << track2Charge_ <<  "\n";
00320   
00321   Geom::Phi<float> theConvPhi( stateAtPreviousLayer.globalPosition().phi());
00322  //std::cout << "InOutConversionSeedFinder::startSeed  stateAtPreviousLayer phi " << stateAtPreviousLayer.globalPosition().phi() << " R " <<  stateAtPreviousLayer.globalPosition().perp() << " Z " << stateAtPreviousLayer.globalPosition().z() << "\n";
00323   
00324   bcVec = getSecondCaloClusters(stateAtPreviousLayer.globalPosition(),track2Charge_);
00325   
00326   std::vector<const reco::CaloCluster*>::iterator bcItr;
00327  //std::cout << "InOutConversionSeedFinder::startSeed bcVec.size " << bcVec.size() << "\n";
00328   
00329   // debug
00330   //  for(bcItr = bcVec.begin(); bcItr != bcVec.end(); ++bcItr) {
00331   //  //std::cout << "InOutConversionSeedFinder::startSeed list of  bc eta " << (*bcItr)->position().eta() << " phi " << (*bcItr)->position().phi() << " x " << (*bcItr)->position().x() << " y " << (*bcItr)->position().y() << " z " << (*bcItr)->position().z() << "\n";
00332   // }
00333   
00334 
00335   for(bcItr = bcVec.begin(); bcItr != bcVec.end(); ++bcItr) {
00336     
00337     theSecondBC_ = **bcItr;
00338     GlobalPoint bcPos((theSecondBC_.position()).x(),
00339                       (theSecondBC_.position()).y(),
00340                       (theSecondBC_.position()).z());
00341     
00342    //std::cout << "InOutConversionSeedFinder::startSeed for  bc position x " << bcPos.x() << " y " <<  bcPos.y() << " z  " <<  bcPos.z() << " eta " <<  bcPos.eta() << " phi " <<  bcPos.phi() << "\n";
00343     GlobalVector dir = stateAtPreviousLayer.globalDirection();
00344     GlobalPoint back1mm = stateAtPreviousLayer.globalPosition();
00345    //std::cout << "InOutConversionSeedFinder::startSeed   stateAtPreviousLayer.globalPosition() " << back1mm << "\n";
00346     
00347     back1mm -= dir.unit()*0.1;
00348     //std::cout << " InOutConversionSeedFinder:::startSeed going to make the helix using back1mm " << back1mm <<"\n";
00349     ConversionFastHelix helix(bcPos, stateAtPreviousLayer.globalPosition(), back1mm, &(*theMF_));
00350     helix.stateAtVertex();    
00351     
00352     //std::cout << " InOutConversionSeedFinder:::startSeed helix status " <<helix.isValid() << std::endl; 
00353     if ( !helix.isValid()  ) continue;
00354     findSeeds(stateAtPreviousLayer, helix.stateAtVertex().transverseCurvature(), ilayer);
00355     
00356     
00357   }
00358   
00359   
00360   
00361 }
00362 
00363 
00364 
00365 std::vector<const reco::CaloCluster*> InOutConversionSeedFinder::getSecondCaloClusters(const GlobalPoint & conversionPosition, float charge) const {
00366   
00367   
00368   std::vector<const reco::CaloCluster*> result;
00369   
00370  //std::cout << "InOutConversionSeedFinder::getSecondCaloClusters" <<  "\n"; 
00371   
00372   Geom::Phi<float> theConvPhi(conversionPosition.phi() );
00373 
00374   for (unsigned i = 0; i < bcCollection_->size(); ++i ) {
00375     
00376     Geom::Phi<float> theBcPhi( bcCollection_->ptrAt(i)->position().phi()   );
00377    //std::cout<< "InOutConversionSeedFinder::getSecondCaloClusters  BC energy " <<  bcCollection_->ptrAt(i)->energy() << " Calo cluster phi " << theBcPhi << " " <<  bcCollection_->ptrAt(i)->position().phi()<<  " theConvPhi " << theConvPhi << "\n";
00378     
00379     // Require phi of cluster to be consistent with the conversion 
00380     // position and the track charge
00381     
00382     
00383     if (fabs(theBcPhi-theConvPhi ) < .5 &&
00384         ((charge<0 && theBcPhi-theConvPhi >-.5) || 
00385          (charge>0 && theBcPhi-theConvPhi <.5))){
00387       
00388       //result.push_back(&(*bcItr));
00389 
00390       result.push_back(&(*(bcCollection_->ptrAt(i))  ));
00391 
00392     }
00393     
00394     
00395     
00396     
00397   }
00398   
00399   
00400   
00401   return result;
00402   
00403   
00404 }
00405 
00406 
00407 
00408 void InOutConversionSeedFinder::findSeeds(const TrajectoryStateOnSurface & startingState,
00409                                           float transverseCurvature, 
00410                                           unsigned int startingLayer) const {
00411   
00412   
00413   std::vector<const DetLayer*> allLayers=layerList();
00414  //std::cout << "InOutConversionSeedFinder::findSeeds starting forward propagation from  startingLayer " << startingLayer <<  "\n"; 
00415   
00416   
00417   // create error matrix
00418   AlgebraicSymMatrix55 m = AlgebraicMatrixID();
00419   m(0,0) = 0.1; m(1,1) = 0.0001 ; m(2,2) = 0.0001 ;
00420   m(3,3) = 0.0001 ; m(4,4) = 0.001;
00421 
00422   // Make an FTS consistent with the start point, start direction and curvature
00423   FreeTrajectoryState fts(GlobalTrajectoryParameters(startingState.globalPosition(), 
00424                                                      startingState.globalDirection(),
00425                                                      double(transverseCurvature), 0, &(*theMF_) ),
00426                           CurvilinearTrajectoryError(m));
00427   if (fts.momentum().mag2() == 0){
00428     edm::LogWarning("FailedToInitiateSeeding")<< " initial FTS has a zero momentum, probably because of the zero field.  ";
00429     return;
00430   }
00431  //std::cout << " InOutConversionSeedFinder::findSeeds startingState R "<< startingState.globalPosition().perp() << " Z " << startingState.globalPosition().z() << " phi " <<  startingState.globalPosition().phi() <<  " position " << startingState.globalPosition() << "\n";
00432  //std::cout << " InOutConversionSeedFinder::findSeeds Initial FTS charge " << fts.charge() << " curvature " <<  transverseCurvature << "\n";  
00433  //std::cout << " InOutConversionSeedFinder::findSeeds Initial FTS parameters " << fts <<  "\n"; 
00434     
00435   
00436   //float dphi = 0.01;
00437   float dphi = 0.03;
00438   float zrange = 5.;
00439   for( unsigned int ilayer = startingLayer; ilayer <= startingLayer+1 && (ilayer < allLayers.size()-2); ++ilayer) {
00440     const DetLayer * layer = allLayers[ilayer];
00441     
00442     
00443     
00445     //    if ( layer->location() == GeomDetEnumerators::barrel ) {const BarrelDetLayer * barrelLayer = dynamic_cast<const BarrelDetLayer*>(layer);
00446     // //std::cout << "InOutConversionSeedFinder::findSeeds  ****  Barrel on layer " << ilayer  << " R= " << barrelLayer->specificSurface().radius() <<  "\n";     
00447     // } else {
00448     // const ForwardDetLayer * forwardLayer = dynamic_cast<const ForwardDetLayer*>(layer);
00450     // }
00451     // // end debug
00452     
00453     
00454 
00455     MeasurementEstimator * newEstimator=0;
00456     if (layer->location() == GeomDetEnumerators::barrel ) {
00457      //std::cout << "InOutConversionSeedFinder::findSeeds Barrel ilayer " << ilayer <<  "\n"; 
00458       newEstimator = new ConversionBarrelEstimator(-dphi, dphi, -zrange, zrange);
00459     }
00460     else {
00461      //std::cout << "InOutConversionSeedFinder::findSeeds Forward  ilayer " << ilayer <<  "\n"; 
00462       newEstimator = new ConversionForwardEstimator(-dphi, dphi, 15.);
00463     }
00464     
00465     
00466     theFirstMeasurements_.clear();
00467     // Get measurements compatible with the FTS and Estimator
00468     TSOS tsos(fts, layer->surface() );
00469     
00470    //std::cout << "InOutConversionSeedFinder::findSeed propagationDirection " << int(thePropagatorAlongMomentum_->propagationDirection() ) << "\n";               
00472     LayerMeasurements theLayerMeasurements_(this->getMeasurementTracker() );
00473 
00474     theFirstMeasurements_ = theLayerMeasurements_.measurements( *layer, tsos, *thePropagatorAlongMomentum_, *newEstimator);
00475     
00476     delete newEstimator;
00477     //std::cout <<  "InOutConversionSeedFinder::findSeeds  Found " << theFirstMeasurements_.size() << " first hits" << "\n";
00478     
00479     if ( theFirstMeasurements_.size() == 1 ) {      // only dummy hit found: start finding the seed from the innermost hit of the OutIn track
00480 
00481       
00482       GlobalPoint bcPos((theSecondBC_.position()).x(),(theSecondBC_.position()).y(),(theSecondBC_.position()).z());
00483       GlobalVector dir = startingState.globalDirection();
00484       GlobalPoint back1mm = myPointer->recHit()->globalPosition();
00485       
00486       back1mm -= dir.unit()*0.1;
00487       //std::cout << " InOutConversionSeedFinder:::findSeeds going to make the helix using back1mm " << back1mm << "\n";
00488       ConversionFastHelix helix(bcPos,  myPointer->recHit()->globalPosition(), back1mm, &(*theMF_));
00489       
00490       helix.stateAtVertex();
00491       //std::cout << " InOutConversionSeedFinder:::findSeeds helix status " <<helix.isValid() << std::endl; 
00492       if ( !helix.isValid()  ) continue;
00493       
00494       track2InitialMomentum_= helix.stateAtVertex().momentum();
00495                   
00496       // Make a new FTS
00497       FreeTrajectoryState newfts(GlobalTrajectoryParameters(
00498                                                             myPointer->recHit()->globalPosition(), startingState.globalDirection(),
00499                                                             helix.stateAtVertex().transverseCurvature(), 0, &(*theMF_)), 
00500                                  CurvilinearTrajectoryError(m));
00501       
00502       
00503       completeSeed(*myPointer, newfts,  thePropagatorAlongMomentum_, ilayer+1);
00504       completeSeed(*myPointer, newfts,  thePropagatorAlongMomentum_, ilayer+2);
00505       
00506       
00507     } else { 
00508       
00509       
00510       
00511       //Loop over compatible hits
00512       int mea=0;
00513       for(std::vector<TrajectoryMeasurement>::iterator tmItr = theFirstMeasurements_.begin(); tmItr !=theFirstMeasurements_.end();  ++tmItr) {
00514         
00515         mea++;
00516         
00517         
00518         if (tmItr->recHit()->isValid() ) {
00519           // Make a new helix as in fillClusterSeeds() but using the hit position
00520           //std::cout << "InOutConversionSeedFinder::findSeeds hit  R " << tmItr->recHit()->globalPosition().perp() << " Z " <<  tmItr->recHit()->globalPosition().z() << " " <<  tmItr->recHit()->globalPosition() << "\n";
00521           GlobalPoint bcPos((theSecondBC_.position()).x(),(theSecondBC_.position()).y(),(theSecondBC_.position()).z());
00522           GlobalVector dir = startingState.globalDirection();
00523           GlobalPoint back1mm = tmItr->recHit()->globalPosition();
00524           
00525           back1mm -= dir.unit()*0.1;
00526           //std::cout << " InOutConversionSeedFinder:::findSeeds going to make the helix using back1mm " << back1mm << "\n";
00527           ConversionFastHelix helix(bcPos,  tmItr->recHit()->globalPosition(), back1mm, &(*theMF_));
00528           
00529           helix.stateAtVertex();
00530           //std::cout << " InOutConversionSeedFinder:::findSeeds helix status " <<helix.isValid() << std::endl; 
00531           if ( !helix.isValid()  ) continue;
00532           
00533           track2InitialMomentum_= helix.stateAtVertex().momentum();
00534           
00535           //std::cout << "InOutConversionSeedFinder::findSeeds Updated estimatedPt = " << helix.stateAtVertex().momentum().perp()  << " curvature "  << helix.stateAtVertex().transverseCurvature() << "\n";
00536           //     << ", bcet = " << theBc->Et() 
00537           //     << ", estimatedPt/bcet = " << estimatedPt/theBc->Et() << endl;
00538           
00539           
00540           // Make a new FTS
00541           FreeTrajectoryState newfts(GlobalTrajectoryParameters(
00542                                                                 tmItr->recHit()->globalPosition(), startingState.globalDirection(),
00543                                                                 helix.stateAtVertex().transverseCurvature(), 0, &(*theMF_)), 
00544                                      CurvilinearTrajectoryError(m));
00545           
00546           //std::cout <<  "InOutConversionSeedFinder::findSeeds  new FTS charge " << newfts.charge() << "\n";
00547           
00548           
00549           /*
00550           // Soome diagnostic output
00551           // may be useful - comparission of the basic cluster position 
00552           // with the ecal impact position of the track
00553           TrajectoryStateOnSurface stateAtECAL
00554           = forwardPropagator.propagate(newfts, ECALSurfaces::barrel());
00555           if (!stateAtECAL.isValid() || abs(stateAtECAL.globalPosition().eta())>1.479) {
00556           if (startingState.globalDirection().eta() > 0.) {
00557           stateAtECAL = forwardPropagator.propagate(newfts, 
00558           ECALSurfaces::positiveEtaEndcap());
00559           } else {
00560           stateAtECAL = forwardPropagator.propagate(newfts, 
00561           ECALSurfaces::negativeEtaEndcap());
00562           }
00563           }
00564           GlobalPoint ecalImpactPosition = stateAtECAL.isValid() ? stateAtECAL.globalPosition() : GlobalPoint(0.,0.,0.);
00565           cout << "Projected fts positon at ECAL surface: " << 
00566           ecalImpactPosition << " bc position: " << theBc->Position() << endl;
00567           */
00568           
00569           
00570           completeSeed(*tmItr, newfts,  thePropagatorAlongMomentum_, ilayer+1);
00571           completeSeed(*tmItr, newfts,  thePropagatorAlongMomentum_, ilayer+2);
00572           
00573           
00574         }
00575         
00576       }
00577       
00578     }    
00579     
00580     
00581   }
00582   
00583   
00584   
00585 }
00586 
00587 
00588 
00589 
00590 
00591 void InOutConversionSeedFinder::completeSeed(const TrajectoryMeasurement & m1,
00592                                              FreeTrajectoryState & fts, const Propagator* propagator, int ilayer) const {
00593   
00594  //std::cout<<  "InOutConversionSeedFinder::completeSeed ilayer " << ilayer <<  "\n";
00595   // A seed is made from 2 Trajectory Measuremennts.  The 1st is the input
00596   // argument m1.  This routine looks for the 2nd measurement in layer ilayer
00597   // Begin by making a new much stricter MeasurementEstimator based on the
00598   // position errors of the 1st hit.
00599   printLayer(ilayer);
00600   
00601   MeasurementEstimator * newEstimator;
00602   std::vector<const DetLayer*> allLayers=layerList();
00603   const DetLayer * layer = allLayers[ilayer];
00604   
00606   //  if ( layer->location() == GeomDetEnumerators::barrel ) {const BarrelDetLayer * barrelLayer = dynamic_cast<const BarrelDetLayer*>(layer);
00607   // //std::cout << "InOutConversionSeedFinder::completeSeed  ****  Barrel on layer " << ilayer  << " R= " << barrelLayer->specificSurface().radius() <<  "\n";     
00608   // } else {
00609   // const ForwardDetLayer * forwardLayer = dynamic_cast<const ForwardDetLayer*>(layer);
00610   //  //std::cout << "InOutConversionSeedFinder::completeSeed ****  Forw on layer " << ilayer  << " Z= " << forwardLayer->specificSurface().position().z() <<  "\n"; 
00613   
00614   
00615 
00616 
00617   if (layer->location() == GeomDetEnumerators::barrel ) {
00618     
00619     float dz = sqrt(the2ndHitdznSigma_*the2ndHitdznSigma_*m1.recHit()->globalPositionError().czz()
00620                     + the2ndHitdzConst_*the2ndHitdzConst_);
00621     newEstimator = new ConversionBarrelEstimator(-the2ndHitdphi_, the2ndHitdphi_, -dz, dz);
00622     
00623   }
00624   else {
00625     float m1dr = sqrt(m1.recHit()->localPositionError().yy());
00626     float dr = sqrt(the2ndHitdznSigma_*the2ndHitdznSigma_*m1dr*m1dr
00627                     + the2ndHitdzConst_*the2ndHitdznSigma_);
00628     
00629     newEstimator =  new ConversionForwardEstimator(-the2ndHitdphi_, the2ndHitdphi_, dr);
00630   }
00631   
00632 
00633  //std::cout << "InOutConversionSeedFinder::completeSeed fts For the TSOS " << fts << "\n";   
00634   
00635   TSOS tsos(fts, layer->surface() );
00636 
00637   if ( !tsos.isValid() ) {
00638    //std::cout  << "InOutConversionSeedFinder::completeSeed TSOS is not valid " <<  "\n"; 
00639   } 
00640 
00641  //std::cout << "InOutConversionSeedFinder::completeSeed TSOS " << tsos << "\n";   
00642  //std::cout << "InOutConversionSeedFinder::completeSeed propagationDirection  " << int(propagator->propagationDirection() ) << "\n";               
00643  //std::cout << "InOutConversionSeedFinder::completeSeed pointer to estimator " << newEstimator << "\n";
00644   LayerMeasurements theLayerMeasurements_(this->getMeasurementTracker() );
00645   std::vector<TrajectoryMeasurement> measurements = theLayerMeasurements_.measurements( *layer, tsos, *propagator, *newEstimator);
00646  //std::cout << "InOutConversionSeedFinder::completeSeed Found " << measurements.size() << " second hits " <<  "\n"; 
00647   delete newEstimator;
00648   
00649   for(unsigned int i = 0; i < measurements.size(); ++i) {
00650     if( measurements[i].recHit()->isValid()  ) {
00651       createSeed(m1, measurements[i]);
00652     }
00653   }
00654   
00655   
00656   
00657   
00658   
00659   
00660 }
00661 
00662 
00663 
00664 void InOutConversionSeedFinder::createSeed(const TrajectoryMeasurement & m1,  const TrajectoryMeasurement & m2) const {
00665   
00666  //std::cout << "InOutConversionSeedFinder::createSeed " << "\n";
00667 
00668   if (  m1.predictedState().isValid() ) {  
00669   GlobalTrajectoryParameters newgtp(  m1.recHit()->globalPosition(), track2InitialMomentum_, track2Charge_, &(*theMF_) );
00670   CurvilinearTrajectoryError errors = m1.predictedState().curvilinearError();
00671   FreeTrajectoryState fts(newgtp, errors);
00672 
00673   TrajectoryStateOnSurface state1 = thePropagatorAlongMomentum_->propagate(fts,  m1.recHit()->det()->surface());
00674   
00675   /*
00676    //std::cout << "hit surface " <<  m1.recHit()->det()->surface().position() << "\n";
00677    //std::cout << "prop to " << typeid( m1.recHit()->det()->surface() ).name() <<"\n";
00678    //std::cout << "prop to first hit " << state1 << "\n"; 
00679    //std::cout << "update to " <<  m1.recHit()->globalPosition() << "\n";
00680   */
00681   
00682   
00683   
00684   
00685   if ( state1.isValid() ) {
00686     
00687     TrajectoryStateOnSurface updatedState1 = theUpdator_.update(state1,  *m1.recHit() );
00688     
00689     if ( updatedState1.isValid() ) {
00690       
00691       TrajectoryStateOnSurface state2 = thePropagatorAlongMomentum_->propagate(*updatedState1.freeTrajectoryState(),  m2.recHit()->det()->surface());
00692       
00693       if ( state2.isValid() ) {
00694         
00695         TrajectoryStateOnSurface updatedState2 = theUpdator_.update(state2, *m2.recHit() );
00696         TrajectoryMeasurement meas1(state1, updatedState1,  m1.recHit()  , m1.estimate(), m1.layer());
00697         TrajectoryMeasurement meas2(state2, updatedState2,  m2.recHit()  , m2.estimate(), m2.layer());
00698         
00699         edm::OwnVector<TrackingRecHit> myHits;
00700         myHits.push_back(meas1.recHit()->hit()->clone());
00701         myHits.push_back(meas2.recHit()->hit()->clone());
00702         
00703         //std::cout << "InOutConversionSeedFinder::createSeed new seed " << "\n";
00704         if ( nSeedsPerInputTrack_ >= maxNumberOfInOutSeedsPerInputTrack_ ) return;
00705         
00706 
00707         
00708         PTrajectoryStateOnDet const & ptsod= trajectoryStateTransform::persistentState(state2, meas2.recHit()->hit()->geographicalId().rawId()  );
00709         //std::cout << "  InOutConversionSeedFinder::createSeed New seed parameters " << state2 << "\n";
00710        
00711         
00712        
00713         theSeeds_.push_back(TrajectorySeed( ptsod, myHits, alongMomentum ));
00714         nSeedsPerInputTrack_++;
00715        
00716         //std::cout << "InOutConversionSeedFinder::createSeed New seed hit 1 R " << m1.recHit()->globalPosition().perp() << "\n";
00717         //std::cout << "InOutConversionSeedFinder::createSeed New seed hit 2 R " << m2.recHit()->globalPosition().perp() << "\n";       
00718         
00719       }
00720     }
00721   }
00722   }
00723 
00724   
00725 }