CMS 3D CMS Logo

/afs/cern.ch/work/a/aaltunda/public/www/CMSSW_6_2_7/src/Alignment/LaserAlignment/src/LASProfileJudge.cc

Go to the documentation of this file.
00001 
00002 
00003 #include "Alignment/LaserAlignment/interface/LASProfileJudge.h"
00004 
00005 
00006 // terminal colors
00007 #define _R "\033[1;31m"
00008 #define _B "\033[1;34m"
00009 #define _G "\033[1;32m"
00010 #define _N "\033[22;30m"
00011 
00012 
00016 LASProfileJudge::LASProfileJudge() :
00017   overdriveThreshold(0)
00018 {
00019 
00020   // switch on the zero filter by default
00021   isZeroFilter = true;
00022 
00023 }
00024 
00025 
00026 
00027 
00028 
00034 bool LASProfileJudge::IsSignalIn( const LASModuleProfile& aProfile, double offset ) {
00035 
00036   profile = aProfile;
00037   
00038   // need only approx values, so cast here to use integers throughout
00039   const int approxOffset = static_cast<int>( offset );
00040 
00041   const double negativity = GetNegativity( approxOffset );
00042   const bool isPeaks = IsPeaksInProfile( approxOffset );
00043   const bool isNegativePeaks = IsNegativePeaksInProfile( approxOffset );
00044   
00045   bool result = 
00046     ( negativity < -1000. ) ||  // if we see negativity, there was laser..
00047     ( isPeaks )             ||  // if we see a peak, " " "
00048     ( isNegativePeaks );    // same here
00049   
00050   return( result );
00051 
00052 
00053 }
00054 
00055 
00056 
00057 
00058 
00063 bool LASProfileJudge::JudgeProfile( const LASModuleProfile& aProfile, double offset = 0. ) {
00064 
00065   profile = aProfile;
00066 
00067   // need only approx values, so cast here to use integers throughout
00068   const int approxOffset = static_cast<int>( offset );
00069 
00070   // run the tests
00071   const double negativity = GetNegativity( approxOffset );
00072 
00073   bool isPeaks;
00074   if( !isZeroFilter ) isPeaks = true; // disable this test if set in cfg
00075   else isPeaks = IsPeaksInProfile( approxOffset );
00076 
00077   const bool isNegativePeaks = IsNegativePeaksInProfile( approxOffset );
00078 
00079   bool isOverdrive; // disable this test if set in cfg
00080   if( !isZeroFilter ) isOverdrive = false;
00081   else isOverdrive = IsOverdrive( approxOffset );
00082 
00083   bool result = 
00084     ( negativity > -1000. ) &&  // < 1000. = distorted profile
00085     ( isPeaks )             &&  // want to see a peak (zero filter)
00086     !( isNegativePeaks )    &&  // no negative peaks
00087     !( isOverdrive );           // no overdrive
00088 
00089   return( result );
00090 
00091 }
00092 
00093 
00094 
00095 
00096 
00100 void LASProfileJudge::EnableZeroFilter( bool zeroFilter ) {
00101 
00102   if( !zeroFilter ) {
00103     std::cerr << " [LASProfileJudge::EnableZeroFilter] ** WARNING: Zero filter has been disabled." << std::endl;
00104   }
00105 
00106   isZeroFilter = zeroFilter;
00107 
00108 }
00109 
00110 
00111 
00112 
00113 
00117 void LASProfileJudge::SetOverdriveThreshold( unsigned int aThreshold ) {
00118 
00119   overdriveThreshold = aThreshold;
00120 
00121 }
00122 
00123 
00124 
00125 
00126 
00132 double LASProfileJudge::GetNegativity( int offset ) {
00133 
00134   // here we could later run the sum only on the affected (pair of) APV
00135 
00136   // expected beam position (in strips)
00137   const unsigned int meanPosition = 256 + offset;
00138   // backplane "alignment hole" (="signal region") approx. half size 
00139   const unsigned int halfWindowSize = 33;
00140   // half size of range over which is summed (must be > halfWindowSize)
00141   const unsigned int sumHalfRange = 128;
00142 
00143   double neg = 0;
00144   
00145   // need only x values, so cast here
00146   for( unsigned int i = meanPosition - sumHalfRange; i < meanPosition - halfWindowSize; ++i ) {
00147     neg += profile.GetValue( i );
00148   }
00149 
00150   for( unsigned int i = meanPosition + halfWindowSize; i < meanPosition + sumHalfRange; ++i ) {
00151     neg += profile.GetValue( i );
00152   }
00153 
00154   return( neg );
00155 
00156 }
00157 
00158 
00159 
00160 
00165 bool LASProfileJudge::IsPeaksInProfile( int offset ) {
00166 
00167   // expected beam position (in strips)
00168   const unsigned int meanPosition = 256 + offset;
00169   // backplane "alignment hole" approx. half size (in strips)
00170   const unsigned int halfWindowSize = 33;
00171 
00172   bool returnValue = false;
00173   
00174   // calculate average out-of-signal
00175   double average = 0., counterD = 0.;
00176   for( unsigned int strip = 0; strip < 512; ++strip ) {
00177     if( strip < meanPosition - halfWindowSize || strip > meanPosition + halfWindowSize ) {
00178       average += profile.GetValue( strip );
00179       counterD += 1.;
00180     }
00181   }
00182   average /= counterD;
00183 
00184   // find peaks well above noise level
00185   const double noiseLevel = 2.; // to be softcoded..
00186   for( unsigned int strip = meanPosition - halfWindowSize; strip < meanPosition + halfWindowSize; ++strip ) {
00187     if( profile.GetValue( strip ) > ( average + 10. * noiseLevel ) ) { 
00188       returnValue = true;
00189       thePeak.first = strip; thePeak.second = profile.GetValue( strip );
00190       break;
00191     }
00192   }
00193 
00194   return( returnValue );
00195 
00196 }
00197 
00198 
00199 
00200 
00205 bool LASProfileJudge::IsNegativePeaksInProfile( int offset ) {
00206 
00207   // expected beam position in middle of module (in strips)
00208   const unsigned int meanPosition = 256 + offset;
00209   // backplane "alignment hole" approx. half size (in strips)
00210   const unsigned int halfWindowSize = 33;
00211 
00212   bool returnValue = false;
00213   
00214   // calculate average out-of-signal
00215   double average = 0., counterD = 0.;
00216   for( unsigned int strip = 0; strip < 512; ++strip ) {
00217     if( strip < meanPosition - halfWindowSize || strip > meanPosition + halfWindowSize ) {
00218       average += profile.GetValue( strip );
00219       counterD += 1.;
00220     }
00221   }
00222   average /= counterD;
00223   
00224   // find strips with negative amplitude way above noise level
00225   const double noiseLevel = 2.;
00226   for( unsigned int strip = 0; strip < 512; ++strip ) {
00227     if( profile.GetValue( strip ) < ( average - 10. * noiseLevel ) ) { 
00228       returnValue = true;
00229       thePeak.first = strip; thePeak.second = profile.GetValue( strip );
00230       break;
00231     }
00232   }
00233 
00234   return( returnValue );
00235 
00236 }
00237 
00238 
00239 
00240 
00241 
00246 bool LASProfileJudge::IsOverdrive( int offset ) {
00247 
00248   
00249   // expected beam position in middle of module (in strips)
00250   const unsigned int meanPosition = 256 + offset;
00251   // backplane "alignment hole" approx. half size (in strips)
00252   const unsigned int halfWindowSize = 33;
00253 
00254   // find maximum strip amplitude in range
00255   for( unsigned int strip = meanPosition - halfWindowSize; strip < meanPosition + halfWindowSize; ++strip ) {
00256     if( profile.GetValue( strip ) > overdriveThreshold ) return true;
00257   }
00258 
00259   return false;
00260 
00261 }