// ------------------------------------------------------------------------- // ----- CbmEcalStructure source file ----- // ----- Created 27/01/06 by M.Prokudin ----- // ------------------------------------------------------------------------- /** CbmEcalStructure.cxx *@author Mikhail Prokudin ** ** ECAL structure, consisting of modules **/ /* $Id: CbmEcalStructure.cxx,v 1.11 2006/07/19 09:33:34 prokudin Exp $ */ #include "CbmEcalStructure.h" #include "CbmEcal.h" #include "CbmEcalDetailed.h" #include "CbmEcalCellMC.h" #include "CbmEcalCell.h" #include #include #include using namespace std; class __CbmEcalCellWrapper { public: CbmEcalCell* cell; Char_t isPsTen; }; CbmEcalCell* CbmEcalStructure::GetCell(Int_t volId, Int_t& ten, Bool_t& isPS) { UInt_t i; static Int_t volidmax = 0; if (volidmax==0) { if (fEcalVersion==0) volidmax=CbmEcal::GetVolIdMax()*2; if (fEcalVersion==1) volidmax=10000000; } if ((Int_t)fHash.size()volidmax) return NULL; if (fHash[volId]==NULL) { Bool_t lisPS; Int_t iten; Float_t x; Float_t y; fHash[volId]=new __CbmEcalCellWrapper(); if (fEcalVersion==0) lisPS=CbmEcal::GetCellCoord(volId,x,y,iten); if (fEcalVersion==1) lisPS=CbmEcalDetailed::GetCellCoordInf(volId, x, y, iten); fHash[volId]->cell=GetCell(x+0.025,y+0.025); fHash[volId]->isPsTen=iten*2; if (lisPS) fHash[volId]->isPsTen+=1; } ten=fHash[volId]->isPsTen/2; isPS=fHash[volId]->isPsTen%2; return fHash[volId]->cell; } //----------------------------------------------------------------------------- void CbmEcalStructure::Serialize() { fCells.clear(); for(UInt_t i=0;i cells=fStructure[i]->GetCells(); copy(cells.begin(),cells.end(), back_inserter(fCells)); } } //----------------------------------------------------------------------------- CbmEcalModule* CbmEcalStructure::CreateModule(char type, Int_t number, Float_t x1, Float_t y1, Float_t x2, Float_t y2) { return new CbmEcalModule(type, number, x1, y1, x2, y2, fUseMC); } //----------------------------------------------------------------------------- CbmEcalStructure::CbmEcalStructure(CbmEcalInf* ecalinf) : TNamed("CbmEcalStructure", "Calorimeter structure"), fUseMC(0), fX1(0.), fY1(0.), fEcalInf(ecalinf), fStructure(), fCells(), fHash(), fEcalVersion(0) { fX1=fEcalInf->GetXPos()-\ fEcalInf->GetModuleSize()*fEcalInf->GetXSize()/2.0; fY1=fEcalInf->GetYPos()-\ fEcalInf->GetModuleSize()*fEcalInf->GetYSize()/2.0; fEcalVersion=(Int_t)fEcalInf->GetVariable("ecalversion"); if (fEcalVersion<0) fEcalVersion=0; } //----------------------------------------------------------------------------- void CbmEcalStructure::Construct() { if (!fEcalInf) return; Float_t x1=GetX1(); Float_t y1=GetY1(); Float_t x; Float_t y; Float_t dx; Float_t dy; Int_t i; Int_t j; Int_t k; Int_t number; char type; fStructure.resize(fEcalInf->GetXSize()*fEcalInf->GetYSize(), NULL); dx=fEcalInf->GetModuleSize(); dy=fEcalInf->GetModuleSize(); //Creating ECAL Matrix for(i=0;iGetXSize();i++) for(j=0;jGetYSize();j++) { type=fEcalInf->GetType(i,j); if (type) { x=x1+i*dx; y=y1+j*dy; number=(i*100+j)*100; fStructure[GetNum(i,j)]=CreateModule(type,number,x,y,x+dx,y+dy); } else fStructure[GetNum(i,j)]=NULL; } #ifdef _DECALSTRUCT cerr << "-I- CbmEcalStructure::Construct(): calorimeter matrix created." << endl; #endif //Now ECAL matrix created list neib[5]; vector cl; vector::const_iterator pcl; Int_t num; //We want neighbors for EcalModules be EcalModules for(i=0;iGetXSize();i++) for(j=0;jGetYSize();j++) if (fStructure[GetNum(i,j)]) { for(k=0;k<5;k++) neib[k].clear(); num=GetNumber(i-1,j); if (-1!=num) { neib[0].push_back(fStructure[num]); neib[1].push_back(fStructure[num]); neib[4].push_back(fStructure[num]); } num=GetNumber(i-1,j+1); if (-1!=num) { neib[0].push_back(fStructure[num]); neib[4].push_back(fStructure[num]); } num=GetNumber(i,j+1); if (-1!=num) { neib[0].push_back(fStructure[num]); neib[3].push_back(fStructure[num]); neib[4].push_back(fStructure[num]); } num=GetNumber(i+1,j+1); if (-1!=num) { neib[0].push_back(fStructure[num]); neib[3].push_back(fStructure[num]); } num=GetNumber(i+1,j); if (-1!=num) { neib[0].push_back(fStructure[num]); neib[2].push_back(fStructure[num]); neib[3].push_back(fStructure[num]); } num=GetNumber(i+1,j-1); if (-1!=num) { neib[0].push_back(fStructure[num]); neib[2].push_back(fStructure[num]); } num=GetNumber(i,j-1); if (-1!=num) { neib[0].push_back(fStructure[num]); neib[1].push_back(fStructure[num]); neib[2].push_back(fStructure[num]); } num=GetNumber(i-1,j-1); if (-1!=num) { neib[0].push_back(fStructure[num]); neib[1].push_back(fStructure[num]); } num=GetNumber(i,j); for(k=0;k<5;k++) fStructure[num]->SetNeighborsList(k,neib[k]); cl=fStructure[num]->GetCells(); for(pcl=cl.begin();pcl!=cl.end();++pcl) CreateNLists(*pcl); } Serialize(); } //----------------------------------------------------------------------------- void _add_not_null(CbmEcalModule* mod, list& lst) { if (mod) if (find(lst.begin(),lst.end(),mod)==lst.end()) lst.push_back(mod); } //----------------------------------------------------------------------------- void _add_not_null(list from, list& where) { list::const_iterator p; for(p=from.begin();p!=from.end();++p) if (find(where.begin(),where.end(),(*p))==where.end()) //this p uniq! where.push_back(*p); } //----------------------------------------------------------------------------- void _add_not_null(CbmEcalCell* cell, list& lst) { if (find(lst.begin(),lst.end(),cell)==lst.end()) lst.push_back(cell); } //----------------------------------------------------------------------------- void CbmEcalStructure::CreateNLists(CbmEcalCell* cell) { Float_t x=cell->GetCenterX(); Float_t y=cell->GetCenterY(); Float_t dx=(cell->GetX2()-cell->GetX1())/2.0; Float_t dy=(cell->GetX2()-cell->GetX1())/2.0; Float_t x1; Float_t x2; Float_t y1; Float_t y2; Float_t mx1=cell->GetX1(); Float_t mx2=cell->GetX2(); Float_t my1=cell->GetY1(); Float_t my2=cell->GetY2(); Float_t cx; Float_t cy; Float_t d=0.1; Float_t dd=1e-6; list neib[5]; list tl; list tml; list::const_iterator ptml; list::const_iterator ptl; Int_t i; //1 - lu, 2 - ru, 3 - rd, 4 - ld for(i=0;i<5;i++) neib[i].clear(); tml.clear(); _add_not_null(GetModule(x-2*dx,y-2*dy),tml); _add_not_null(GetModule(x-2*dx,y ),tml); _add_not_null(GetModule(x-2*dx,y+2*dy),tml); _add_not_null(GetModule(x ,y-2*dy),tml); _add_not_null(GetModule(x ,y ),tml); _add_not_null(GetModule(x ,y+2*dy),tml); _add_not_null(GetModule(x+2*dx,y-2*dy),tml); _add_not_null(GetModule(x+2*dx,y ),tml); _add_not_null(GetModule(x+2*dx,y+2*dy),tml); if (tml.empty()) { cerr << "Error during creating neighbors lists." << endl; cerr << "Can't' find any modules neighbors to cell." << endl; cerr << "Cell: CenterX=" << x << ", CenterY=" << y << "." << endl; return; } tl.empty(); for(ptml=tml.begin();ptml!=tml.end();++ptml) { _add_not_null((*ptml)->GetCellsY(y-dy-d),tl); _add_not_null((*ptml)->GetCellsY(y+dy+d),tl); _add_not_null((*ptml)->GetCellsX(x-dx-d),tl); _add_not_null((*ptml)->GetCellsX(x+dx+d),tl); } if (tl.empty()) { cerr << "Error during creating neighbors lists." << endl; cerr << "Can't' find any cells neighbors to cell." << endl; cerr << "Cell: CenterX=" << x << ", CenterY=" << y << "." << endl; return; } for(ptl=tl.begin();ptl!=tl.end();++ptl) { x1=(*ptl)->GetX1(); x2=(*ptl)->GetX2(); y1=(*ptl)->GetY1(); y2=(*ptl)->GetY2(); cx=(*ptl)->GetCenterX(); cy=(*ptl)->GetCenterY(); if (fabs(mx1-x2)-dd&&cy-y-dy/2-dd)||fabs(y+dy-y1)-dd&&cx-x-dx/2-dd)||fabs(x+dx-x1)-dd&&cy-y-dy/2-dd)||fabs(y+dy-y1)-dd&&cx-x-dx/2-dd)||fabs(x+dx-x1)SetNeighborsList(i,neib[i]); } //----------------------------------------------------------------------------- void CbmEcalStructure::ResetModules() { list::const_iterator p=fCells.begin(); if (fUseMC==0) { for(;p!=fCells.end();++p) (*p)->ResetEnergyFast(); } else { for(;p!=fCells.end();++p) ((CbmEcalCellMC*)(*p))->ResetEnergy(); } } //----------------------------------------------------------------------------- void CbmEcalStructure::GetHitXY(const Int_t hitId, Float_t& x, Float_t& y) const { /** Hit Id -> (x,y) **/ // Some translation from x*100+y to y*sizex+x coding... Int_t mnum=hitId/100; Int_t cellx = mnum/100; Int_t celly = mnum%100; mnum = GetNum(cellx, celly); // end translation CbmEcalModule* module=fStructure[mnum]; CbmEcalCell* cell; Int_t cellnum=hitId%100; // change place Int_t cx=cellnum%10-1; Int_t cy=cellnum/10-1; if (module==NULL||cx<0||cy<0||cx>=module->GetType()||cy>=module->GetType()) {x=0; y=0; return;} cell=module->At(cx,cy); x=cell->GetCenterX(); y=cell->GetCenterY(); } //----------------------------------------------------------------------------- CbmEcalCell* CbmEcalStructure::GetHitCell(const Int_t hitId) const { /** Hit Id -> Cell **/ // Some translation from x*100+y to y*sizex+x coding... Int_t mnum=hitId/100; Int_t cellx = mnum/100; Int_t celly = mnum%100; mnum = GetNum(cellx, celly); // end translation CbmEcalModule* module=fStructure[mnum]; Int_t cellnum=hitId%100; Int_t cx=cellnum%10-1; Int_t cy=cellnum/10-1; if (module==NULL||cx<0||cy<0||cx>=module->GetType()||cy>=module->GetType()) return NULL; // cout << hitId << " --- " << module->At(cx,cy)->GetCellNumber() << endl; return module->At(cx,cy); } //----------------------------------------------------------------------------- void CbmEcalStructure::GetGlobalCellXY(const Int_t hitId, Int_t& x, Int_t& y) const { Int_t modulenum = hitId/100; Int_t cellx = modulenum/100; Int_t celly = modulenum%100; Int_t innernum = hitId%100; Int_t iny = innernum/10; Int_t inx = innernum%10; Int_t msize = fEcalInf->GetType(cellx,celly); x = (cellx-1)* msize + inx; y = (celly-1)* msize + iny; } // Int_t CbmEcalStructure::GetType(const Int_t hitId) const { Int_t modulenum = hitId/100; Int_t cellx = modulenum/100; Int_t celly = modulenum%100; Int_t msize = fEcalInf->GetType(cellx,celly); return msize; }