Go to the documentation of this file.00001 #include "RecoPixelVertexing/PixelLowPtUtilities/interface/LowPtClusterShapeSeedComparitor.h"
00002
00003 #include "RecoPixelVertexing/PixelTrackFitting/src/CircleFromThreePoints.h"
00004 #include "RecoPixelVertexing/PixelLowPtUtilities/interface/HitInfo.h"
00005 #include "RecoPixelVertexing/PixelLowPtUtilities/interface/ClusterShapeHitFilter.h"
00006
00007 #include "FWCore/Framework/interface/EventSetup.h"
00008 #include "FWCore/Framework/interface/ESHandle.h"
00009 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00010 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00011
00012 #include "DataFormats/TrackerRecHit2D/interface/SiPixelRecHit.h"
00013 #include "DataFormats/TrackingRecHit/interface/TrackingRecHit.h"
00014
00015 #include "RecoTracker/Record/interface/CkfComponentsRecord.h"
00016
00017 inline float sqr(float x) { return x*x; }
00018
00019 using namespace std;
00020
00021
00022 LowPtClusterShapeSeedComparitor::LowPtClusterShapeSeedComparitor
00023 (const edm::ParameterSet& ps)
00024 {
00025
00026 }
00027
00028
00029 LowPtClusterShapeSeedComparitor::~LowPtClusterShapeSeedComparitor()
00030 {
00031 }
00032
00033
00034 float LowPtClusterShapeSeedComparitor::areaParallelogram
00035 (const Global2DVector& a, const Global2DVector& b)
00036 {
00037 return a.x() * b.y() - a.y() * b.x();
00038 }
00039
00040
00041 vector<GlobalVector> LowPtClusterShapeSeedComparitor::getGlobalDirs
00042 (const vector<GlobalPoint> & g)
00043 {
00044
00045 vector<Global2DVector> p;
00046 for(vector<GlobalPoint>::const_iterator ig = g.begin();
00047 ig!= g.end(); ig++)
00048 p.push_back( Global2DVector(ig->x(), ig->y()) );
00049
00050
00051 vector<GlobalVector> globalDirs;
00052
00053
00054 CircleFromThreePoints circle(g[0],g[1],g[2]);
00055
00056 if(circle.curvature() != 0.)
00057 {
00058 Global2DVector c (circle.center().x(), circle.center().y());
00059
00060 float rad2 = (p[0] - c).mag2();
00061 float area = fabsf(areaParallelogram(p[1] - p[0], p[1] - c));
00062
00063 float a12;
00064 if(area >= rad2) a12 = M_PI/2;
00065 else a12 = asin(area / rad2);
00066
00067 float slope = (g[1].z() - g[0].z()) / a12;
00068
00069 float cotTheta = slope * circle.curvature();
00070 float coshEta = sqrt(1 + sqr(cotTheta));
00071
00072
00073 float sinTheta = 1. / coshEta;
00074 float cosTheta = cotTheta * sinTheta;
00075
00076 int dir;
00077 if(areaParallelogram(p[0] - c, p[1] - c) > 0) dir = 1; else dir = -1;
00078
00079 float curvature = circle.curvature();
00080
00081 for(vector<Global2DVector>::const_iterator ip = p.begin();
00082 ip!= p.end(); ip++)
00083 {
00084 Global2DVector v = (*ip - c)*curvature*dir;
00085 globalDirs.push_back(GlobalVector(-v.y()*sinTheta,
00086 v.x()*sinTheta,
00087 cosTheta));
00088 }
00089 }
00090 else{
00091 LogDebug("LowPtClusterShapeSeedComparitor")<<"the curvature is null:"
00092 <<"\n point1: "<<g[0]
00093 <<"\n point2: "<<g[1]
00094 <<"\n point3: "<<g[2];
00095 }
00096 return globalDirs;
00097 }
00098
00099
00100 vector<GlobalPoint> LowPtClusterShapeSeedComparitor::getGlobalPoss
00101 (const TransientTrackingRecHit::ConstRecHitContainer & thits)
00102 {
00103 vector<GlobalPoint> globalPoss;
00104
00105 for(TransientTrackingRecHit::ConstRecHitContainer::const_iterator recHit = thits.begin();
00106 recHit!= thits.end();
00107 recHit++)
00108 {
00109 DetId detId = (*recHit)->hit()->geographicalId();
00110
00111 GlobalPoint gpos = (*recHit)->globalPosition();
00112
00113 globalPoss.push_back(gpos);
00114 }
00115
00116 return globalPoss;
00117 }
00118
00119
00120 bool LowPtClusterShapeSeedComparitor::compatible(const SeedingHitSet &hits,
00121 const edm::EventSetup &es)
00122
00123 {
00124
00125
00126 edm::ESHandle<ClusterShapeHitFilter> shape;
00127 es.get<CkfComponentsRecord>().get("ClusterShapeHitFilter",shape);
00128 theFilter = shape.product();
00129
00130 const TransientTrackingRecHit::ConstRecHitContainer & thits = hits.container();
00131
00132
00133 vector<GlobalPoint> globalPoss = getGlobalPoss(thits);
00134
00135
00136 vector<GlobalVector> globalDirs = getGlobalDirs(globalPoss);
00137
00138 bool ok = true;
00139
00140
00141
00142
00143 if (globalDirs.size()!=globalPoss.size() || globalDirs.size()!=thits.size())
00144 {
00145 LogDebug("LowPtClusterShapeSeedComparitor")<<"not enough global dir calculated:"
00146 <<"\nnHits: "<<thits.size()
00147 <<"\nnPos: "<<globalPoss.size()
00148 <<"\nnDir: "<<globalDirs.size()
00149 <<" will say the seed is good anyway.";
00150 return true;
00151 }
00152
00153 for(int i = 0; i < 3; i++)
00154 {
00155 const SiPixelRecHit* pixelRecHit =
00156 dynamic_cast<const SiPixelRecHit *>(thits[i]->hit());
00157
00158 if (!pixelRecHit){
00159 edm::LogError("LowPtClusterShapeSeedComparitor")<<"this is not a pixel cluster";
00160 ok = false; break;
00161 }
00162
00163 if(!pixelRecHit->isValid())
00164 {
00165 ok = false; break;
00166 }
00167
00168 LogDebug("LowPtClusterShapeSeedComparitor")<<"about to compute compatibility."
00169 <<"hit ptr: "<<pixelRecHit
00170 <<"global direction:"<< globalDirs[i];
00171
00172
00173 if(! theFilter->isCompatible(*pixelRecHit, globalDirs[i]) )
00174 {
00175 LogTrace("LowPtClusterShapeSeedComparitor")
00176 << " clusShape is not compatible"
00177 << HitInfo::getInfo(*thits[i]->hit());
00178
00179 ok = false; break;
00180 }
00181 }
00182
00183 return ok;
00184 }
00185