00001 #include "AcdReconDigiAlg.h"
00002
00004 #include "GaudiKernel/MsgStream.h"
00005 #include "GaudiKernel/AlgFactory.h"
00006 #include "GaudiKernel/IDataProviderSvc.h"
00007 #include "GaudiKernel/SmartDataPtr.h"
00008
00009 #include "GaudiKernel/SmartDataPtr.h"
00010 #include "GaudiKernel/StatusCode.h"
00011
00013 #include "GlastEvent/TopLevel/EventModel.h"
00014 #include "GlastEvent/TopLevel/Event.h"
00015
00017 #include "TkrRecon/SiRecObjs.h"
00018 #include "TkrRecon/GFparticle.h"
00019 #include "TkrRecon/GFdata.h"
00020 #include "TkrRecon/GFgamma.h"
00021
00022 #include "geometry/Point.h"
00023 #include "geometry/Vector.h"
00024
00025 #include "idents/AcdId.h"
00026 #include "xml/IFile.h"
00027
00028 #include <fstream>
00029 #include <algorithm>
00030 #include <cstdio>
00031 #include <stdlib.h>
00032
00033 static float maxDOCA = 200.0;
00034
00036 static const AlgFactory<AcdReconDigiAlg> Factory;
00037 const IAlgFactory& AcdReconDigiAlgFactory = Factory;
00038
00041 AcdReconDigiAlg::AcdReconDigiAlg(const std::string& name, ISvcLocator* pSvcLocator) :
00042 Algorithm(name, pSvcLocator) {
00043
00045 declareProperty("tupleName", m_tupleName="");
00046 declareProperty("xmlFile", m_xmlFileStr="");
00047 declareProperty("vetoThreshFile", m_vetoThreshFileStr="");
00048
00049 }
00050
00051
00056 StatusCode AcdReconDigiAlg::initialize ( )
00057 {
00058
00059 StatusCode sc = StatusCode::SUCCESS;
00060
00061 MsgStream log(msgSvc(), name());
00062 log << MSG::INFO << "initialize" << endreq;
00063
00064
00066
00067
00068 sc = serviceLocator()->getService("GlastDetSvc",
00069 IID_IGlastDetSvc, reinterpret_cast<IInterface*&>( m_glastDetSvc));
00070
00071 if( sc.isFailure() ) {
00072 log << MSG::ERROR << "AcdReconDigiAlg failed to get the GlastDetSvc" << endreq;
00073 return sc;
00074 }
00075
00076 getParameters();
00077
00078 readThresholds();
00079
00080
00081 sc = serviceLocator()->getService("ntupleWriterSvc",
00082 IID_INTupleWriterSvc, reinterpret_cast<IInterface*&>( ntupleWriteSvc));
00083
00084 if( sc.isFailure() ) {
00085 log << MSG::ERROR << "AcdReconDigiAlg failed to get the ntupleWriterSvc" << endreq;
00086 return sc;
00087 }
00088
00089 return sc;
00090 }
00091
00092
00093
00094
00097 StatusCode AcdReconDigiAlg::execute() {
00098
00099 StatusCode sc = StatusCode::SUCCESS;
00100 MsgStream log( msgSvc(), name() );
00101 log << MSG::DEBUG << "execute" << endreq;
00102
00110 DataObject *tempObj;
00111 sc = eventSvc()->retrieveObject("/Event/Digi/AcdDigis", tempObj);
00112 if (sc.isFailure()) {
00113 log << MSG::DEBUG << "No ACD Data available" << endreq;
00114 return StatusCode::SUCCESS;
00115 }
00116
00117 m_AcdData = dynamic_cast<AcdDigiVector*>(tempObj);
00118
00119 if (m_AcdData == 0) {
00120 log << MSG::DEBUG << "No ACD Data available " << endreq;
00121 return StatusCode::SUCCESS;
00122 }
00123
00124
00125 reconstruct(m_AcdData);
00126
00130
00131 log << MSG::DEBUG << "exiting ACD Recon " << endreq;
00132
00133 return sc;
00134 }
00135
00136
00137
00138
00139
00140
00141
00142 StatusCode AcdReconDigiAlg::finalize() {
00143
00144 MsgStream log(msgSvc(), name());
00145 log << MSG::INFO << "finalize" << endreq;
00146
00147 return StatusCode::SUCCESS;
00148 }
00149
00150
00152 void AcdReconDigiAlg::getParameters ()
00153 {
00154
00155 MsgStream log( msgSvc(), name() );
00156
00158 xml::IFile *m_ifile = new xml::IFile(m_xmlFileStr.c_str());
00159
00160 std::vector<int> topIds = m_ifile->getIntVector("acdTop", "ids");
00161 std::vector<double> topX = m_ifile->getDoubleVector("acdTop", "x_center");
00162 std::vector<double> topY = m_ifile->getDoubleVector("acdTop", "y_center");
00163 std::vector<double> topZ = m_ifile->getDoubleVector("acdTop", "z_center");
00164 std::vector<double> topXlen = m_ifile->getDoubleVector("acdTop", "xlen");
00165 std::vector<double> topYlen = m_ifile->getDoubleVector("acdTop", "ylen");
00166 std::vector<double> topZlen = m_ifile->getDoubleVector("acdTop", "zlen");
00167
00168
00169 for (int i=0; i < topIds.size(); i++) {
00170 m_tileCenters[topIds[i]] = Point(topX[i], topY[i], topZ[i]);
00171 m_tileDims[topIds[i]] = Vector(topXlen[i], topYlen[i], topZlen[i]);
00172 }
00173
00174
00175 int id = m_ifile->getInt("bigtile", "id");
00176 double bigX = m_ifile->getDouble("bigtile", "x_center");
00177 double bigY = m_ifile->getDouble("bigtile", "y_center");
00178 double bigZ = m_ifile->getDouble("bigtile", "z_center");
00179 double bigXlen = m_ifile->getDouble("bigtile", "xlen");
00180 double bigYlen = m_ifile->getDouble("bigtile", "ylen");
00181 double bigZlen = m_ifile->getDouble("bigtile", "zlen");
00182
00183 m_tileCenters[id] = Point(bigX, bigY, bigZ);
00184 m_tileDims[id] = Vector(bigXlen, bigYlen, bigZlen);
00185
00186
00187 std::vector<int> sideIds = m_ifile->getIntVector("acdSide", "ids");
00188 std::vector<double> sideX = m_ifile->getDoubleVector("acdSide", "x_center");
00189 std::vector<double> sideY = m_ifile->getDoubleVector("acdSide", "y_center");
00190 std::vector<double> sideZ = m_ifile->getDoubleVector("acdSide", "z_center");
00191 std::vector<double> sideXlen = m_ifile->getDoubleVector("acdSide", "xlen");
00192 std::vector<double> sideYlen = m_ifile->getDoubleVector("acdSide", "ylen");
00193 std::vector<double> sideZlen = m_ifile->getDoubleVector("acdSide", "zlen");
00194
00195 for (int j=0; j < sideIds.size(); j++) {
00196 m_tileCenters[sideIds[j]] = Point(sideX[j], sideY[j], sideZ[j]);
00197 m_tileDims[sideIds[j]] = Vector(sideXlen[j], sideYlen[j], sideZlen[j]);
00198 }
00199
00200 std::vector<int> xgtIds = m_ifile->getIntVector("xgt", "ids");
00201 std::vector<double> xgtX = m_ifile->getDoubleVector("xgt", "x_center");
00202 std::vector<double> xgtY = m_ifile->getDoubleVector("xgt", "y_center");
00203 std::vector<double> xgtZ = m_ifile->getDoubleVector("xgt", "z_center");
00204
00205 for (int k = 0; k < xgtIds.size(); k++)
00206 m_tileCenters[xgtIds[k]] = Point(xgtX[k], xgtY[k], xgtZ[k]);
00207
00209 for( std::map<int,Point>::const_iterator it= m_tileCenters.begin(); it != m_tileCenters.end(); ++it) {
00210 Point cen = (*it).second;
00211 log << MSG::DEBUG << "id = " << (*it).first << " center = (" << cen.x() << "," << cen.y() << "," << cen.z() << ")" << endreq;
00212 }
00213
00214 m_numSideRows = m_ifile->getInt("acd", "num_side_tiles");
00215
00216 log << MSG::DEBUG << "number of ACD rows = " << m_numSideRows << endreq;
00217
00218
00219 }
00220
00221 void AcdReconDigiAlg::readThresholds() {
00222
00223 xml::IFile::extractEnvVar(&m_vetoThreshFileStr);
00224 std::ifstream threshFile( m_vetoThreshFileStr.c_str() );
00225
00226 if (threshFile.eof() || !threshFile.good()) return;
00227 int id = 0;
00228 double thresh = 0.0;
00229
00230 threshFile >> id >> thresh;
00231
00232 while ( ( !threshFile.eof() ) && ( id >= 0 )) {
00233 m_vetoThresh[id] = thresh;
00234 threshFile >> id >> thresh;
00235 }
00236
00237 threshFile.close();
00238 }
00239
00240
00241 void AcdReconDigiAlg::clear() {
00242 m_totEnergy = 0.0;
00243 m_tileCount = 0.0;
00244 m_gammaDOCA = maxDOCA;
00245 m_DOCA = maxDOCA;
00246 m_rowDOCA_vec.clear();
00247 m_rowDOCA_vec.resize(m_numSideRows+1, maxDOCA);
00248 m_act_dist = -200.0;
00249
00250 }
00251
00252 StatusCode AcdReconDigiAlg::reconstruct (const AcdDigiVector* v)
00253 {
00254
00255 StatusCode sc = StatusCode::SUCCESS;
00256
00257 MsgStream log( msgSvc(), name() );
00258
00259
00260 clear();
00261
00262
00263 for( AcdDigiVector::const_iterator it= v->begin(); it != v->end(); ++it) {
00264
00265
00266 idents::AcdId id = (*it)->ID();
00267
00268
00269
00270 if ((*it)->PulseHeight() < m_vetoThresh[id.id()]) continue;
00271
00272 m_tileCount++;
00273
00274 }
00275
00276 log << MSG::DEBUG << "num Tiles = " << m_tileCount << endreq;
00277
00278 acdTileDOCA();
00279
00280 sc = writeNTuple();
00281
00282 return sc;
00283 }
00284
00285
00286 StatusCode AcdReconDigiAlg::acdTileDOCA() {
00287
00288 StatusCode sc = StatusCode::SUCCESS;
00289
00290 MsgStream log( msgSvc(), name() );
00291
00292 SmartDataPtr<SiRecObjs> tkrRecData(eventSvc(),"/Event/TkrRecon/SiRecObjs");
00293 if (tkrRecData == 0) {
00294 log << MSG::DEBUG << "No TKR Reconstruction available " << endreq;
00295 return sc;
00296 }
00297
00298 std::vector<const GFtrack*> xtracks;
00299 std::vector<const GFtrack*> ytracks;
00300
00301 int nparticles = tkrRecData->numParticles();
00302 if (nparticles > 0) {
00303
00304 log << MSG::DEBUG << "Number of particles " << nparticles << endreq;
00305
00306 unsigned int iParticle;
00307 for (iParticle = 0; iParticle < nparticles; iParticle++) {
00308 GFparticle *particle = tkrRecData->Particle(iParticle);
00309 xtracks.push_back(particle->getXGFtrack());
00310 ytracks.push_back(particle->getYGFtrack());
00311 }
00312 } else {
00313 log << MSG::DEBUG << "No reconstructed particles " << endreq;
00314 }
00315
00316 int ngammas = tkrRecData->numGammas();
00317 log << MSG::DEBUG << "number of gammas = " << ngammas << endreq;
00318
00319 if (ngammas > 0) {
00320 unsigned int iGamma;
00321
00322
00323
00324 std::vector<double> temprowDOCA_vec;
00325 temprowDOCA_vec.resize(m_numSideRows+1, maxDOCA);
00326 for (iGamma = 0; iGamma < ngammas; iGamma++) {
00327 GFgamma *gamma = tkrRecData->Gamma(iGamma);
00328 Point gammaVertex = gamma->vertex();
00329 Vector gammaDirection = gamma->direction();
00330 double tempDOCA = DOCA(gammaVertex, gammaDirection, m_rowDOCA_vec);
00331 if (tempDOCA < m_gammaDOCA) m_gammaDOCA = tempDOCA;
00332
00333 xtracks.push_back(gamma->getPair(SiCluster::X));
00334 xtracks.push_back(gamma->getBest(SiCluster::X));
00335 ytracks.push_back(gamma->getPair(SiCluster::Y));
00336 ytracks.push_back(gamma->getBest(SiCluster::Y));
00337 }
00338 } else {
00339 log << MSG::DEBUG << "No reconstructed gammas " << endreq;
00340 }
00341
00342
00343
00344
00345
00346 for (std::vector<const GFtrack*>::const_iterator xtrk = xtracks.begin(); xtrk != xtracks.end(); xtrk++) {
00347 for(std::vector<const GFtrack*>::const_iterator ytrk = ytracks.begin(); ytrk != ytracks.end(); ytrk++) {
00348 Vector dir = Vector((*xtrk)->slope(), (*ytrk)->slope(), 1.).unit();
00349 Point x0((*xtrk)->positionAtZ(0), (*ytrk)->positionAtZ(0), 0.);
00350
00351 float testDOCA = DOCA(x0, dir, m_rowDOCA_vec);
00352 if(testDOCA < m_DOCA) m_DOCA = testDOCA;
00353
00354 float test_dist= hitTileDist(x0, dir);
00355 if(test_dist > m_act_dist) m_act_dist = test_dist;
00356 }
00357 }
00358
00359 log << MSG::DEBUG << "ACD_DOCA = " << m_DOCA << endreq;
00360
00361 return sc;
00362
00363 }
00364
00365
00366 double AcdReconDigiAlg::DOCA (const Point &x0, const Vector &t0, std::vector<double> &doca_values)
00367 {
00368
00369
00370 float minDOCA = maxDOCA;
00371 float dist;
00372
00373
00374 for( AcdDigiVector::const_iterator it= m_AcdData->begin(); it != m_AcdData->end(); ++it) {
00375
00376 idents::AcdId type = (*it)->ID();
00377
00378
00379
00380 if ((*it)->PulseHeight() < m_vetoThresh[type.id()]) continue;
00381
00382
00383 Point tileCenter = m_tileCenters[type.id()];
00384 Vector dX = tileCenter - x0;
00385
00386 float prod = dX * t0;
00387 dist = sqrt(dX.mag2() - prod*prod);
00388 if(dist < minDOCA){
00389 minDOCA = dist;
00390 }
00391
00392
00393
00394
00395 if (type.top() && dist < doca_values[0]) doca_values[0] = dist;
00396 if (type.side()) {
00397 if (dist < doca_values[type.row()+1]) doca_values[type.row()+1] = dist;
00398 }
00399 }
00400
00401 return minDOCA;
00402 }
00403
00404
00405 double AcdReconDigiAlg::hitTileDist(const Point &x0, const Vector &t0)
00406 {
00407 double return_dist = -200.;
00408
00409 if(!m_AcdData) return return_dist;
00410
00411
00412 for( AcdDigiVector::const_iterator it= m_AcdData->begin(); it != m_AcdData->end(); ++it) {
00413
00414
00415 idents::AcdId type = (*it)->ID();
00416
00417 if ((*it)->PulseHeight() < m_vetoThresh[type.id()]) continue;
00418
00419
00420
00421 if (type.layer() > 1) continue;
00422
00423 int iFace = type.face();
00424
00425
00426 Point xT = m_tileCenters[type.id()];
00427
00428 float dX = m_tileDims[type.id()].x();
00429 float dY = m_tileDims[type.id()].y();
00430 float dZ = m_tileDims[type.id()].z();
00431
00432
00433 double arc_dist = -1.;
00434 if(iFace == 0) {
00435 arc_dist = (xT.z()-x0.z())/t0.z();
00436 }
00437 else if(iFace == 1 || iFace == 3) {
00438 arc_dist = (xT.x()-x0.x())/t0.x();
00439 }
00440 else if(iFace == 2 || iFace == 4) {
00441 arc_dist = (xT.y()-x0.y())/t0.y();
00442 }
00443
00444 if(arc_dist < 0.) continue;
00445
00446 Point x_isec = x0 + arc_dist*t0;
00447
00448 Vector local_x0 = xT - x_isec;
00449 if(iFace == 0) {
00450 double dist_x = dX/2. - fabs(local_x0.x());
00451 double dist_y = dY/2. - fabs(local_x0.y());
00452 double test_dist = (dist_x < dist_y) ? dist_x : dist_y;
00453 if(test_dist > return_dist) return_dist = test_dist;
00454 }
00455 else if(iFace == 1 || iFace == 3) {
00456 double dist_z = dZ/2. - fabs(local_x0.z());
00457 double dist_y = dY/2. - fabs(local_x0.y());
00458 double test_dist = (dist_z < dist_y) ? dist_z : dist_y;
00459 if(test_dist > return_dist) return_dist = test_dist;
00460 }
00461 else if(iFace == 2 || iFace == 4) {
00462 double dist_z = dZ/2. - fabs(local_x0.z());
00463 double dist_x = dY/2. - fabs(local_x0.x());
00464 double test_dist = (dist_z < dist_x) ? dist_z : dist_x;
00465 if(test_dist > return_dist) return_dist = test_dist;
00466 }
00467 }
00468 return return_dist;
00469 }
00470
00471
00472
00473 StatusCode AcdReconDigiAlg::writeNTuple() {
00474
00475 StatusCode sc = StatusCode::SUCCESS;
00476 MsgStream log( msgSvc(), name() );
00477
00479
00480 sc = ntupleWriteSvc->addItem(m_tupleName.c_str(), "ACD_TileCount", m_tileCount);
00481 sc = ntupleWriteSvc->addItem(m_tupleName.c_str(), "ACD_DOCA", m_DOCA);
00482 sc = ntupleWriteSvc->addItem(m_tupleName.c_str(), "ACD_GammaDOCA", m_gammaDOCA);
00483 sc = ntupleWriteSvc->addItem(m_tupleName.c_str(), "ACD_TopDOCA", m_rowDOCA_vec[0]);
00484 sc = ntupleWriteSvc->addItem(m_tupleName.c_str(), "ACD_Act_Dist", m_act_dist);
00485
00486
00487 unsigned int iDOCA;
00488 for (iDOCA = 1; iDOCA <= m_numSideRows; iDOCA++) {
00489 std::string label("ACD_S");
00490 char num[5];
00491 _itoa((iDOCA-1), num, 10);
00492 label += num;
00493 label += "DOCA";
00494 sc = ntupleWriteSvc->addItem(m_tupleName.c_str(), label.c_str(), m_rowDOCA_vec[iDOCA]);
00495 }
00496
00497 return sc;
00498 }
00499