1 /**************************************************************************
2 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
4 * Author: The ALICE Off-line Project. *
5 * Contributors are mentioned in the code where appropriate. *
7 * Permission to use, copy, modify and distribute this software and its *
8 * documentation strictly for non-commercial purposes is hereby granted *
9 * without fee, provided that the above copyright notice appears in all *
10 * copies and that both the copyright notice and this permission notice *
11 * appear in the supporting documentation. The authors make no claims *
12 * about the suitability of this software for any purpose. It is *
13 * provided "as is" without express or implied warranty. *
14 **************************************************************************/
18 Revision 1.18 2001/08/24 21:06:37 nilsen
19 Added more documentation, fixed up some coding violations, and some
22 Revision 1.17 2001/07/27 08:06:48 hristov
23 Use global gRandom generator (M.Ivanov)
25 Revision 1.16 2001/02/08 23:57:00 nilsen
26 Fixed up some informational printouts.
28 Revision 1.15 2001/02/07 20:23:21 nilsen
29 Fixed bug with HP and no unget in iostream.h. Now using putback instead.
30 Other changes and fixes also included.
32 Revision 1.14 2001/02/03 00:00:29 nilsen
33 New version of AliITSgeom and related files. Now uses automatic streamers,
34 set up for new formatted .det file which includes detector information.
35 Additional smaller modifications are still to come.
37 Revision 1.11 2000/10/02 16:32:35 barbera
38 Forward declaration added
40 Revision 1.4.4.15 2000/10/02 15:52:05 barbera
41 Forward declaration added
43 Revision 1.10 2000/09/05 14:25:50 nilsen
44 Made fixes for HP compiler. All function parameter default values placed
45 in .h file. Fixed the usual problem with HP compilers and the "for(Int_t i..."
46 business. Replaced casting (Double_t [3][3]) to (Double_t (*)[3]) for HP.
47 Lastly removed all "const" before function parameters which were 2 dim. arrays,
48 because on HP root generates some strange code (?). Thanks Peter for the
51 Revision 1.9 2000/08/29 20:19:03 nilsen
52 Removed dependency on structure AliITSeomS and replaced it with class
53 AliITSgeomMatrix. Added many new functions with many new arguments. Most
54 in the form of in line functions for speed.
56 Revision 1.4.4.6 2000/06/04 16:33:32 Nilsen
57 A restructured AliITSgeom class. Now used AliITSgeomMatrix.
59 Revision 1.4.4.5 2000/03/04 23:42:39 Nilsen
60 Updated the comments/documentations and improved the maintainability of the
63 Revision 1.4.4.4 2000/03/02 21:27:07 Nilsen
64 Added two functions, SetByAngles and SetTrans.
66 Revision 1.4.4.3 2000/01/23 03:09:10 Nilsen
67 // fixed compiler warnings for new function LtLErrorMatrix(...)
69 Revision 1.4.4.2 2000/01/19 23:18:20 Nilsen
70 Added transformations of Error matrix to AliITSgeom and fixed some typos
71 in AliITS.h and AliITShitIndex.h
73 Revision 1.4.4.1 2000/01/12 19:03:32 Nilsen
74 This is the version of the files after the merging done in December 1999.
75 See the ReadMe110100.txt file for details
77 Revision 1.4 1999/10/15 07:03:20 fca
78 Fixed bug in GetModuleId(Int_t index,Int_t &lay,Int_t &lad, Int_t &det) and
79 a typo in the creator. aliroot need to be rerun to get a fixed geometry.
81 Revision 1.3 1999/10/04 15:20:12 fca
82 Correct syntax accepted by g++ but not standard for static members, remove minor warnings
84 Revision 1.2 1999/09/29 09:24:20 fca
85 Introduction of the Copyright and cvs Log
89 ///////////////////////////////////////////////////////////////////////
90 // ITS geometry manipulation routines. //
91 // Created April 15 1999. //
93 // By: Bjorn S. Nilsen //
95 // Updated May 27 1999. //
96 // Added Cylindrical random and global based changes. //
97 // Added function PrintComparison. //
98 ///////////////////////////////////////////////////////////////////////
101 ////////////////////////////////////////////////////////////////////////
102 // The local coordinate system by, default, is show in the following
103 // figures. Also shown are the ladder numbering scheme.
106 <img src="picts/ITS/AliITSgeomMatrix_L1.gif">
109 <font size=+2 color=blue>
110 <p>This shows the relative geometry differences between the ALICE Global
111 coordinate system and the local detector coordinate system.
116 <img src="picts/ITS/its1+2_convention_front_5.gif">
119 <font size=+2 color=blue>
120 <p>This shows the front view of the SPDs and the orientation of the local
121 pixel coordinate system. Note that the inner pixel layer has its y coordinate
122 in the opposite direction from all of the other layers.
127 <img src="picts/ITS/its3+4_convention_front_5.gif">
130 <font size=+2 color=blue>
131 <p>This shows the front view of the SDDs and the orientation of the local
132 pixel coordinate system.
137 <img src="picts/ITS/its5+6_convention_front_5.gif">
140 <font size=+2 color=blue>
141 <p>This shows the front view of the SSDs and the orientation of the local
142 pixel coordinate system.
148 ////////////////////////////////////////////////////////////////////////
150 ////////////////////////////////////////////////////////////////////////
153 // Written by Bjorn S. Nilsen
158 // The number of ITS layers for this geometry. By default this
159 // is 6, but can be modified by the creator function if there are
160 // more layers defined.
163 // A pointer to an array fNlayers long containing the number of
164 // ladders for each layer. This array is typically created and filled
165 // by the AliITSgeom creator function.
168 // A pointer to an array fNlayers long containing the number of
169 // active detector volumes for each ladder. This array is typically
170 // created and filled by the AliITSgeom creator function.
172 // AliITSgeomMatrix *fGm
173 // A pointer to an array of AliITSgeomMatrix classes. One element
174 // per module (detector) in the ITS. AliITSgeomMatrix basicly contains
175 // all of the necessary information about the detector and it's coordinate
179 // A pointer to an array of TObjects containing the detailed shape
180 // information for each type of detector used in the ITS. For example
181 // I have created AliITSgeomSPD, AliITSgeomSDD, and AliITSgeomSSD as
182 // example structures, derived from TObjects, to hold the detector
183 // information. I would recommend that one element in each of these
184 // structures, that which describes the shape of the active volume,
185 // be one of the ROOT classes derived from TShape. In this way it would
186 // be easy to have the display program display the correct active
187 // ITS volumes. See the example classes AliITSgeomSPD, AliITSgeomSDD,
188 // and AliITSgeomSSD for a more detailed example.
189 ////////////////////////////////////////////////////////////////////////
190 #include <iostream.h>
201 #include "AliITSgeom.h"
202 #include "AliITSgeomSPD.h"
203 #include "AliITSgeomSDD.h"
204 #include "AliITSgeomSSD.h"
208 //______________________________________________________________________
209 AliITSgeom::AliITSgeom(){
210 // The default constructor for the AliITSgeom class. It, by default,
211 // sets fNlayers to zero and zeros all pointers.
212 // Do not allocate anything zero everything.
214 fTrans = 0; // standard GEANT global/local coordinate system.
220 strcpy(fVersion,"test");
223 //______________________________________________________________________
224 AliITSgeom::AliITSgeom(Int_t itype,Int_t nlayers,Int_t *nlads,Int_t *ndets,
226 // A simple constructor to set basic geometry class variables
228 // Int_t itype the type of transformation kept.
229 // bit 0 => Standard GEANT
230 // bit 1 => ITS tracking
231 // bit 2 => A change in the coordinate system has been made.
232 // others are still to be defined as needed.
233 // Int_t nlayers The number of ITS layers also set the size of the arrays
234 // Int_t *nlads an array of the number of ladders for each layer. This
235 // array must be nlayers long.
236 // Int_t *ndets an array of the number of detectors per ladder for each
237 // layer. This array must be nlayers long.
238 // Int_t mods The number of modules. Typicaly the sum of all the
239 // detectors on every layer and ladder.
246 fNlad = new Int_t[nlayers];
247 fNdet = new Int_t[nlayers];
248 for(i=0;i<nlayers;i++){fNlad[i] = nlads[i];fNdet[i] = ndets[i];}
250 fGm = new TObjArray(mods,0);
251 fShape = new TObjArray(5); // default value
252 for(i=0;i<5;i++) fShape->AddAt(0,i);
253 strcpy(fVersion,"test");
256 //______________________________________________________________________
257 void AliITSgeom::CreatMatrix(Int_t mod,Int_t lay,Int_t lad,Int_t det,
258 AliITSDetector idet,const Double_t tran[3],
259 const Double_t rot[10]){
260 // Given the translation vector tran[3] and the rotation matrix rot[1],
261 // this function creates and adds to the TObject Array fGm the
262 // AliITSgeomMatrix object.
264 // Int_t mod The module number. The location in TObjArray
265 // Int_t lay The layer where this module is
266 // Int_t lad On which ladder this module is
267 // Int_t det Which detector on this ladder this module is
268 // AliITSDetector idet The type of detector see AliITSgeom.h
269 // Double_t tran[3] The translation vector
270 // Double_t rot[10] The rotation matrix.
273 // The rot[10] matrix is set up like:
274 /* / rot[0] rot[1] rot[2] \
275 // | rot[3] rot[4] rot[5] |
276 // \ rot[6] rot[7] rot[8] / if(rot[9]!=0) then the Identity matrix
277 // is used regardless of the values in rot[0]-rot[8].
280 Double_t r[3][3] = {{1.0,0.0,0.0},{0.0,1.0,0.0},{0.0,0.0,1.0}};
282 if(fGm->At(mod)!=0) delete fGm->At(mod);
283 id[0] = lay; id[1] = lad; id[2] = det;
284 if(rot[9]!=0.0) { // null rotation
285 r[0][0] = rot[0]; r[0][1] = rot[1]; r[0][2] = rot[2];
286 r[1][0] = rot[3]; r[1][1] = rot[4]; r[1][2] = rot[5];
287 r[2][0] = rot[6]; r[2][1] = rot[7]; r[2][2] = rot[8];
289 fGm->AddAt(new AliITSgeomMatrix(idet,id,r,tran),mod);
291 //______________________________________________________________________
292 AliITSgeom::~AliITSgeom(){
293 // The destructor for the AliITSgeom class. If the arrays fNlad,
294 // fNdet, or fGm have had memory allocated to them, there pointer values
295 // are non zero, then this memory space is freed and they are set
296 // to zero. In addition, fNlayers is set to zero. The destruction of
297 // TObjArray fShape is, by default, handled by the TObjArray destructor.
300 //for(Int_t i=0;i<fNlayers;i++) delete fGm->At(i);
304 if(fNlad!=0) delete[] fNlad;
305 if(fNdet!=0) delete[] fNdet;
312 //______________________________________________________________________
313 void AliITSgeom::ReadNewFile(const char *filename){
314 // It is generaly preferred to define the geometry in AliITSgeom
315 // directly from the GEANT geometry, see AliITSvPPRasymm.cxx for
316 // and example. Under some circumstances this may not be possible.
317 // This function will read in a formatted file for all of the
318 // information needed to define the geometry in AliITSgeom.
319 // Unlike the older file format, this file may contain comments
320 // and the order of the data does not need to be completely
321 // respected. A file can be created using the function WriteNewFile
324 // const char *filename The file name of the file to be read in.
328 const char *cmda[]={"Version" ,"fTrans" ,"fNmodules",
329 "fNlayers" ,"fNladers","fNdetectors",
330 "fNDetectorTypes","fShape" ,"Matrix"};
331 Int_t i,j,lNdetTypes,ldet;
340 filtmp = gSystem->ExpandPathName(filename);
341 cout << "AliITSgeom, Reading New .det file " << filtmp << endl;
342 fp = new ifstream(filtmp,ios::in); // open file to write
343 while(fp->get(c)!=NULL){ // for ever loop
344 if(c==' ') continue; // remove blanks
345 if(c=='\n') continue;
346 if(c=='#' || c=='!'){for(;fp->get(c)!=NULL,c!='\n';); continue;}
349 if(c=='/'){for(;fp->get(c)!=NULL,c!='\n';);continue;}
352 for(;fp->get(c)!=NULL,c!='*';);
362 for(i=0;i<ncmd;i++) if(strcmp(cmd,cmda[i])==0) break;
373 for(j=0;j<fGm->GetEntriesFast();j++) delete fGm->At(j);
376 fGm = new TObjArray(fNmodules,0);
380 if(fNlad!=0) delete fNlad;
381 if(fNdet!=0) delete fNdet;
382 fNlad = new Int_t[fNlayers];
383 fNdet = new Int_t[fNlayers];
386 for(j=0;j<fNlayers;j++) *fp >> fNlad[j];
388 case 5: // fNdetectors
389 for(j=0;j<fNlayers;j++) *fp >> fNdet[j];
391 case 6: // fNDetectorTypes
394 for(j=0;j<fShape->GetEntriesFast();j++) delete fShape->At(j);
397 fShape = new TObjArray(lNdetTypes,0);
401 if(fShape==0) fShape = new TObjArray(5,0);
404 ReSetShape(ldet,(TObject*) new AliITSgeomSPD());
405 spd = (AliITSgeomSPD*) (fShape->At(ldet));
410 ReSetShape(ldet,(TObject*) new AliITSgeomSDD());
411 sdd = (AliITSgeomSDD*) (fShape->At(ldet));
415 case kSSD : case kSSDp :
416 ReSetShape(ldet,(TObject*) new AliITSgeomSSD());
417 ssd = (AliITSgeomSSD*) (fShape->At(ldet));
422 Error("ReadNewFile","Unknown fShape type number=%d c=%c",ldet,c);
423 for(;fp->get(c)==NULL,c!='\n';); // skip to end of line.
429 if(fGm==0) fGm = new TObjArray(2270,0);
430 if(fGm->At(ldet)!=0) delete (fGm->At(ldet));
431 fGm->AddAt((TObject*)new AliITSgeomMatrix(),ldet);
432 m = (AliITSgeomMatrix*) fGm->At(ldet);
437 Error("ReadNewFile","Data line i=%d c=%c",i,c);
438 for(;fp->get(c)==NULL,c!='\n';); // skip this line
446 //______________________________________________________________________
447 void AliITSgeom::WriteNewFile(const char *filename){
448 // Writes AliITSgeom, AliITSgeomMatrix, and the defined AliITSgeomS*D
449 // classes to a file in a format that is more readable and commendable.
451 // const char *filename The file name of the file to be write to.
458 filtmp = gSystem->ExpandPathName(filename);
459 cout << "AliITSgeom, Writing New .det file " << filtmp << endl;
460 fp = new ofstream(filtmp,ios::out); // open file to write
461 *fp << "//Comment lines begin with two //, one #, or one !" << endl;
462 *fp << "#Blank lines are skipped including /* and */ sections." << endl;
463 *fp << "!and, in principle the order of the lines is not important" <<endl;
464 *fp << "/* In AliITSgeom.h are defined an enumerated type called" << endl;
465 *fp << " AliITSDetectors These are kSPD=" << (Int_t) kSPD ;
466 *fp << ", kSDD=" << (Int_t) kSDD << ", kSSD=" << (Int_t) kSSD;
467 *fp << ", kSSDp=" << (Int_t) kSSDp << ", and kSDDp=" << (Int_t) kSDDp;
469 *fp << "Version " << fVersion << endl;//This should be consistent with the
471 *fp << "fTrans " << fTrans << endl;
472 *fp << "fNmodules " << fNmodules << endl;
473 *fp << "fNlayers " << fNlayers << endl;
475 for(i=0;i<fNlayers;i++) *fp << fNlad[i] << " ";
477 *fp << "fNdetectors ";
478 for(i=0;i<fNlayers;i++) *fp << fNdet[i] << " ";
480 *fp << "fNDetectorTypes " << fShape->GetEntriesFast() << endl;
481 for(i=0;i<fShape->GetEntriesFast();i++){
482 if(!IsShapeDefined(i)) continue; // only print out used shapes.
485 *fp << "fShape " << (Int_t) kSPD << " ";
486 *fp << *((AliITSgeomSPD*)(fShape->At(i)));
489 *fp << "fShape " << (Int_t) kSDD << " ";
490 *fp << *((AliITSgeomSDD*)(fShape->At(i)));
492 case kSSD : case kSSDp :
493 *fp << "fShape " << i << " ";
494 *fp << *((AliITSgeomSSD*)(fShape->At(i)));
497 Error("AliITSgeom::WriteNewFile","Unknown Shape value");
500 for(i=0;i<fNmodules;i++){
501 *fp << "Matrix " << i << " ";
502 *fp << *GetGeomMatrix(i);
504 *fp << "//End of File" << endl;;
509 //______________________________________________________________________
510 AliITSgeom::AliITSgeom(const char *filename){
511 // The constructor for the AliITSgeom class. All of the data to fill
512 // this structure is read in from the file given my the input filename.
514 // const char *filename The file name of the file to be read in.
520 Float_t x,y,z,o,p,q,r,s,t;
521 Double_t rot6[6],tran[3];
522 char buf[200],*buff=0; // input character buffer;
525 filtmp = gSystem->ExpandPathName(filename);
526 cout << "AliITSgeom reading old .det file " << filtmp << endl;
528 strcpy(fVersion,"DefauleV5");
529 pf = fopen(filtmp,"r");
531 fNlayers = 6; // set default number of ladders
533 fNlad = new Int_t[fNlayers];
534 fNdet = new Int_t[fNlayers];
536 // find the number of ladders and detectors in this geometry.
537 for(i=0;i<fNlayers;i++){fNlad[i]=fNdet[i]=0;} // zero out arrays
538 while(fgets(buf,200,pf)!=NULL){ // for ever loop
539 for(i=0;i<200;i++)if(buf[i]!=' '){ // remove blank spaces.
543 // remove blank lines and comments.
544 if(buff[0]=='\n'||buff[0]=='#'||buff[0]=='!'||
545 (buff[0]=='/'&&buff[1]=='/')) continue;
546 if(isalpha(buff[0])) { // must be the new file formated file.
548 delete[] fNlad;delete[] fNdet;
549 ReadNewFile(filename);
551 } // end if isalpha(buff[0])
552 sscanf(buff,"%d %d %d %f %f %f %f %f %f %f %f %f",
553 &l,&a,&d,&x,&y,&z,&o,&p,&q,&r,&s,&t);
555 if(l<1 || l>fNlayers) {
556 printf("error in file %s layer=%d min. is 1 max is %d\n",
557 filename,l,fNlayers);
561 if(l<=fNlayers&&fNlad[l-1]<a) fNlad[l-1] = a;
562 if(l<=fNlayers&&fNdet[l-1]<d) fNdet[l-1] = d;
563 } // end while ever loop
569 } // end if lm>fNlayers
570 // counted the number of ladders and detectors now allocate space.
571 fGm = new TObjArray(fNmodules,0);
573 // Set up Shapes for a default configuration of 6 layers.
574 fTrans = 0; // standard GEANT global/local coordinate system.
575 // prepare to read in transforms
576 lm = 0; // reuse lm as counter of modules.
577 rewind(pf); // start over reading file
578 while(fgets(buf,200,pf)!=NULL){ // for ever loop
579 for(i=0;i<200;i++)if(buf[i]!=' '){ // remove blank spaces.
583 // remove blank lines and comments.
584 if(buff[0]=='\n'||buff[0]=='#'||buff[0]=='!'||
585 (buff[0]=='/'&&buff[1]=='/')) continue;
586 x = y = z = o = p = q = r = s = t = 0.0;
587 sscanf(buff,"%d %d %d %f %f %f %f %f %f %f %f %f",
588 &l,&a,&d,&x,&y,&z,&o,&p,&q,&r,&s,&t);
589 if(l<1 || l>fNlayers) {
590 printf("error in file %s layer=%d min. is 1 max is %d/n",
591 filename,l,fNlayers);
594 id[0] = l;id[1] = a;id[2] = d;
595 tran[0] = tran[1] = tran[2] = 0.0;
596 tran[0] = (Double_t)x;tran[1] = (Double_t)y;tran[2] = (Double_t)z;
597 rot6[0] = rot6[1] = rot6[2] = rot6[3] = rot6[4] = rot6[5] =0.0;
598 rot6[0] = (Double_t)o;rot6[1] = (Double_t)p;rot6[2] = (Double_t)q;
599 rot6[3] = (Double_t)r;rot6[4] = (Double_t)s;rot6[5] = (Double_t)t;
601 case 1: case 2: // layer 1 or2 SPD
602 fGm->AddAt(new AliITSgeomMatrix(rot6,kSPD,id,tran),lm++);
604 case 3: case 4: // layer 3 or 4 SDD
605 fGm->AddAt(new AliITSgeomMatrix(rot6,kSDD,id,tran),lm++);
607 case 5: case 6: // layer 5 or 6 SSD
608 fGm->AddAt(new AliITSgeomMatrix(rot6,kSSD,id,tran),lm++);
611 } // end while ever loop
614 //______________________________________________________________________
615 AliITSgeom::AliITSgeom(AliITSgeom &source){
616 // The copy constructor for the AliITSgeom class. It calls the
617 // = operator function. See the = operator function for more details.
619 // AliITSgeom &source The AliITSgeom class with which to make this
624 *this = source; // Just use the = operator for now.
627 //______________________________________________________________________
628 AliITSgeom& AliITSgeom::operator=(AliITSgeom &source){
629 // The = operator function for the AliITSgeom class. It makes an
630 // independent copy of the class in such a way that any changes made
631 // to the copied class will not affect the source class in any way.
632 // This is required for many ITS alignment studies where the copied
633 // class is then modified by introducing some misalignment.
635 // AliITSgeom &source The AliITSgeom class with which to make this
638 // return *this The a new copy of source.
641 if(this == &source) return *this; // don't assign to ones self.
643 // if there is an old structure allocated delete it first.
645 for(i=0;i<this->fNmodules;i++) delete this->fGm->At(i);
648 if(fNlad != 0) delete[] fNlad;
649 if(fNdet != 0) delete[] fNdet;
651 this->fTrans = source.fTrans;
652 this->fNmodules = source.fNmodules;
653 this->fNlayers = source.fNlayers;
654 this->fNlad = new Int_t[fNlayers];
655 for(i=0;i<this->fNlayers;i++) this->fNlad[i] = source.fNlad[i];
656 this->fNdet = new Int_t[fNlayers];
657 for(i=0;i<this->fNlayers;i++) this->fNdet[i] = source.fNdet[i];
658 this->fShape = new TObjArray(*(source.fShape));//This does not make a proper copy.
659 this->fGm = new TObjArray(this->fNmodules,0);
660 for(i=0;i<this->fNmodules;i++){
661 this->fGm->AddAt(new AliITSgeomMatrix(*(
662 (AliITSgeomMatrix*)(source.fGm->At(i)))),i);
666 //______________________________________________________________________
667 Int_t AliITSgeom::GetModuleIndex(Int_t lay,Int_t lad,Int_t det){
668 // This routine computes the module index number from the layer,
669 // ladder, and detector numbers. The number of ladders and detectors
670 // per layer is determined when this geometry package is constructed,
671 // see AliITSgeom(const char *filename) for specifics.
673 // Int_t lay The layer number. Starting from 1.
674 // Int_t lad The ladder number. Starting from 1.
675 // Int_t det The detector number. Starting from 1.
677 // return the module index number, starting from zero.
680 i = fNdet[lay-1] * (lad-1) + det - 1;
682 for(k=0;k<lay-1;k++) j += fNdet[k]*fNlad[k];
684 GetGeomMatrix(i)->GetIndex(id);
685 if(id[0]==lay&&id[1]==lad&&id[2]==det) return i;
686 // Array of modules fGm is not in expected order. Search for this index
687 for(i=0;i<fNmodules;i++){
688 GetGeomMatrix(i)->GetIndex(id);
689 if(id[0]==lay&&id[1]==lad&&id[2]==det) return i;
691 // This layer ladder and detector combination does not exist return -1.
694 //______________________________________________________________________
695 void AliITSgeom::GetModuleId(Int_t index,Int_t &lay,Int_t &lad,Int_t &det){
696 // This routine computes the layer, ladder and detector number
697 // given the module index number. The number of ladders and detectors
698 // per layer is determined when this geometry package is constructed,
699 // see AliITSgeom(const char *filename) for specifics.
701 // Int_t index The module index number, starting from zero.
703 // Int_t lay The layer number. Starting from 1.
704 // Int_t lad The ladder number. Starting from 1.
705 // Int_t det The detector number. Starting from 1.
708 GetGeomMatrix(index)->GetIndex(id);
709 lay = id[0]; lad = id[1]; det = id[2];
712 // The old way kept for posterity.
716 for(k=0;k<fNlayers;k++){
717 j += fNdet[k]*fNlad[k];
721 i = index -j + fNdet[k]*fNlad[k];
723 for(k=0;k<fNlad[lay-1];k++){
728 det = 1+i-fNdet[lay-1]*k;
732 //______________________________________________________________________
733 Int_t AliITSgeom::GetStartDet(Int_t dtype){
734 // returns the starting module index value for a give type of detector id.
735 // This assumes that the detector types are different on different layers
736 // and that they are not mixed up.
738 // Int_t dtype A detector type number. 0 for SPD, 1 for SDD, and 2 for SSD.
740 // return the module index for the first occurance of that detector type.
744 return GetModuleIndex(1,1,1);
747 return GetModuleIndex(3,1,1);
750 return GetModuleIndex(5,1,1);
753 Warning("GetStartDet","undefined detector type %d",dtype);
757 Warning("GetStartDet","undefined detector type %d",dtype);
760 //______________________________________________________________________
761 Int_t AliITSgeom::GetLastDet(Int_t dtype){
762 // returns the last module index value for a give type of detector id.
763 // This assumes that the detector types are different on different layers
764 // and that they are not mixed up.
766 // Int_t dtype A detector type number. 0 for SPD, 1 for SDD, and 2 for SSD.
768 // return the module index for the last occurance of that detector type.
781 Warning("GetLastDet","undefined detector type %d",dtype);
785 Warning("GetLastDet","undefined detector type %d",dtype);
788 //______________________________________________________________________
789 void AliITSgeom::PrintComparison(FILE *fp,AliITSgeom *other){
790 // This function was primarily created for diagnostic reasons. It
791 // print to a file pointed to by the file pointer fp the difference
792 // between two AliITSgeom classes. The format of the file is basicly,
793 // define d? to be the difference between the same element of the two
794 // classes. For example dfrx = this->GetGeomMatrix(i)->frx
795 // - other->GetGeomMatrix(i)->frx.
796 // if(at least one of dfx0, dfy0, dfz0,dfrx,dfry,dfrz are non zero) then
797 // print layer ladder detector dfx0 dfy0 dfz0 dfrx dfry dfrz
798 // if(at least one of the 9 elements of dfr[] are non zero) then print
799 // layer ladder detector dfr[0] dfr[1] dfr[2]
800 // dfr[3] dfr[4] dfr[5]
801 // dfr[6] dfr[7] dfr[8]
802 // Only non zero values are printed to save space. The differences are
803 // typical written to a file because there are usually a lot of numbers
804 // printed out and it is usually easier to read them in some nice editor
805 // rather than zooming quickly past you on a screen. fprintf is used to
806 // do the printing. The fShapeIndex difference is not printed at this time.
808 // FILE *fp A file pointer to an opened file for writing in which
809 // the results of the comparison will be written.
810 // AliITSgeom *other The other AliITSgeom class to which this one is
814 Int_t i,j,idt[3],ido[3];
815 Double_t tt[3],to[3]; // translation
816 Double_t rt[3],ro[3]; // phi in radians
817 Double_t mt[3][3],mo[3][3]; // matrixes
818 AliITSgeomMatrix *gt,*go;
821 for(i=0;i<this->fNmodules;i++){
822 gt = this->GetGeomMatrix(i);
823 go = other->GetGeomMatrix(i);
827 for(i=0;i<3;i++) t = t&&idt[i]!=ido[i];
828 if(t) fprintf(fp,"%4.4d %1.1d %2.2d %2.2d %1.1d %2.2d %2.2d\n",i,
829 idt[0],idt[1],idt[2],ido[0],ido[1],ido[2]);
830 gt->GetTranslation(tt);
831 go->GetTranslation(to);
835 for(i=0;i<3;i++) t = t&&tt[i]!=to[i];
836 if(t) fprintf(fp,"%1.1d %2.2d %2.2d dTrans=%f %f %f drot=%f %f %f\n",
837 idt[0],idt[1],idt[2],
838 tt[0]-to[0],tt[1]-to[1],tt[2]-to[2],
839 rt[0]-ro[0],rt[1]-ro[1],rt[2]-ro[2]);
843 for(i=0;i<3;i++)for(j=0;j<3;j++) t = mt[i][j] != mo[i][j];
845 fprintf(fp,"%1.1d %2.2d %2.2d dfr= %e %e %e\n",
846 idt[0],idt[1],idt[2],
847 mt[0][0]-mo[0][0],mt[0][1]-mo[0][1],mt[0][2]-mo[0][2]);
848 fprintf(fp," dfr= %e %e %e\n",
849 mt[1][0]-mo[1][0],mt[1][1]-mo[1][1],mt[1][2]-mo[1][2]);
850 fprintf(fp," dfr= %e %e %e\n",
851 mt[2][0]-mo[2][0],mt[2][1]-mo[2][1],mt[2][2]-mo[2][2]);
856 //______________________________________________________________________
857 void AliITSgeom::PrintData(FILE *fp,Int_t lay,Int_t lad,Int_t det){
858 // This function prints out the coordinate transformations for
859 // the particular detector defined by layer, ladder, and detector
860 // to the file pointed to by the File pointer fp. fprintf statements
861 // are used to print out the numbers. The format is
862 // layer ladder detector Trans= fx0 fy0 fz0 rot= frx fry frz
864 // dfr= fr[0] fr[1] fr[2]
865 // dfr= fr[3] fr[4] fr[5]
866 // dfr= fr[6] fr[7] fr[8]
867 // By indicating which detector, some control over the information
868 // is given to the user. The output it written to the file pointed
869 // to by the file pointer fp. This can be set to stdout if you want.
871 // FILE *fp A file pointer to an opened file for writing in which
872 // the results of the comparison will be written.
873 // Int_t lay The layer number. Starting from 1.
874 // Int_t lad The ladder number. Starting from 1.
875 // Int_t det The detector number. Starting from 1.
878 AliITSgeomMatrix *gt;
879 Double_t t[3],r[3],m[3][3];
881 gt = this->GetGeomMatrix(GetModuleIndex(lay,lad,det));
882 gt->GetTranslation(t);
884 fprintf(fp,"%1.1d %2.2d %2.2d Trans=%f %f %f rot=%f %f %f Shape=%d\n",
885 lay,lad,det,t[0],t[1],t[2],r[0],r[1],r[2],
886 gt->GetDetectorIndex());
888 fprintf(fp," dfr= %e %e %e\n",m[0][0],m[0][1],m[0][2]);
889 fprintf(fp," dfr= %e %e %e\n",m[1][0],m[1][1],m[1][2]);
890 fprintf(fp," dfr= %e %e %e\n",m[2][0],m[2][1],m[2][2]);
893 //______________________________________________________________________
894 ofstream & AliITSgeom::PrintGeom(ofstream &rb){
895 // Stream out an object of class AliITSgeom to standard output.
897 // ofstream &rb The output streaming buffer.
899 // ofstream &rb The output streaming buffer.
902 rb.setf(ios::scientific);
904 rb << fNmodules << " ";
905 rb << fNlayers << " ";
906 for(i=0;i<fNlayers;i++) rb << fNlad[i] << " ";
907 for(i=0;i<fNlayers;i++) rb << fNdet[i] << "\n";
908 for(i=0;i<fNmodules;i++) {
909 rb <<setprecision(16) << *(GetGeomMatrix(i)) << "\n";
913 //______________________________________________________________________
914 ifstream & AliITSgeom::ReadGeom(ifstream &rb){
915 // Stream in an object of class AliITSgeom from standard input.
917 // ifstream &rb The input streaming buffer.
919 // ifstream &rb The input streaming buffer.
922 fNlad = new Int_t[fNlayers];
923 fNdet = new Int_t[fNlayers];
925 for(i=0;i<fNmodules;i++) delete GetGeomMatrix(i);
929 rb >> fTrans >> fNmodules >> fNlayers;
930 fNlad = new Int_t[fNlayers];
931 fNdet = new Int_t[fNlayers];
932 for(i=0;i<fNlayers;i++) rb >> fNlad[i];
933 for(i=0;i<fNlayers;i++) rb >> fNdet[i];
934 fGm = new TObjArray(fNmodules,0);
935 for(i=0;i<fNmodules;i++){
936 fGm->AddAt(new AliITSgeomMatrix,i);
937 rb >> *(GetGeomMatrix(i));
941 //______________________________________________________________________
942 // The following routines modify the transformation of "this"
943 // geometry transformations in a number of different ways.
944 //______________________________________________________________________
945 void AliITSgeom::GlobalChange(const Float_t *tran,const Float_t *rot){
946 // This function performs a Cartesian translation and rotation of
947 // the full ITS from its default position by an amount determined by
948 // the three element arrays tran and rot. If every element
949 // of tran and rot are zero then there is no change made
950 // the geometry. The change is global in that the exact same translation
951 // and rotation is done to every detector element in the exact same way.
952 // The units of the translation are those of the Monte Carlo, usually cm,
953 // and those of the rotation are in radians. The elements of tran
954 // are tran[0] = x, tran[1] = y, and tran[2] = z.
955 // The elements of rot are rot[0] = rx, rot[1] = ry, and
956 // rot[2] = rz. A change in x will move the hole ITS in the ALICE
957 // global x direction, the same for a change in y. A change in z will
958 // result in a translation of the ITS as a hole up or down the beam line.
959 // A change in the angles will result in the inclination of the ITS with
960 // respect to the beam line, except for an effective rotation about the
961 // beam axis which will just rotate the ITS as a hole about the beam axis.
963 // Float_t *tran A 3 element array representing the global translations.
964 // the elements are x,y,z in cm.
965 // Float_t *rot A 3 element array representing the global rotation
966 // angles about the three axis x,y,z in radians
973 fTrans = (fTrans && 0xfffd) + 2; // set bit 1 true.
974 for(i=0;i<fNmodules;i++){
975 g = this->GetGeomMatrix(i);
976 g->GetTranslation(t);
982 g->SetTranslation(t);
987 //______________________________________________________________________
988 void AliITSgeom::GlobalCylindericalChange(const Float_t *tran,
990 // This function performs a cylindrical translation and rotation of
991 // each ITS element by a fixed about in radius, rphi, and z from its
992 // default position by an amount determined by the three element arrays
993 // tran and rot. If every element of tran and
994 // rot are zero then there is no change made the geometry. The
995 // change is global in that the exact same distance change in translation
996 // and rotation is done to every detector element in the exact same way.
997 // The units of the translation are those of the Monte Carlo, usually cm,
998 // and those of the rotation are in radians. The elements of tran
999 // are tran[0] = r, tran[1] = rphi, and tran[2] = z.
1000 // The elements of rot are rot[0] = rx, rot[1] = ry, and
1001 // rot[2] = rz. A change in r will results in the increase of the
1002 // radius of each layer by the same about. A change in rphi will results in
1003 // the rotation of each layer by a different angle but by the same
1004 // circumferential distance. A change in z will result in a translation
1005 // of the ITS as a hole up or down the beam line. A change in the angles
1006 // will result in the inclination of the ITS with respect to the beam
1007 // line, except for an effective rotation about the beam axis which will
1008 // just rotate the ITS as a hole about the beam axis.
1010 // Float_t *tran A 3 element array representing the global translations.
1011 // the elements are r,theta,z in cm/radians.
1012 // Float_t *rot A 3 element array representing the global rotation
1013 // angles about the three axis x,y,z in radians
1017 Double_t t[3],ro[3],r,r0,phi,rphi;
1018 AliITSgeomMatrix *g;
1020 fTrans = (fTrans && 0xfffd) + 2; // set bit 1 true.
1021 for(i=0;i<fNmodules;i++){
1022 g = this->GetGeomMatrix(i);
1023 g->GetTranslation(t);
1025 r = r0= TMath::Hypot(t[1],t[0]);
1026 phi = TMath::ATan2(t[1],t[0]);
1031 t[0] = r*TMath::Cos(phi);
1032 t[1] = r*TMath::Sin(phi);
1037 g->SetTranslation(t);
1042 //______________________________________________________________________
1043 void AliITSgeom::RandomChange(const Float_t *stran,const Float_t *srot){
1044 // This function performs a Gaussian random displacement and/or
1045 // rotation about the present global position of each active
1046 // volume/detector of the ITS. The sigma of the random displacement
1047 // is determined by the three element array stran, for the
1048 // x y and z translations, and the three element array srot,
1049 // for the three rotation about the axis x y and z.
1051 // Float_t *stran A 3 element array representing the global translations
1052 // variances. The elements are x,y,z in cm.
1053 // Float_t *srot A 3 element array representing the global rotation
1054 // angles variances about the three axis x,y,z in radians.
1059 AliITSgeomMatrix *g;
1061 fTrans = (fTrans && 0xfffd) + 2; // set bit 1 true.
1062 for(i=0;i<fNmodules;i++){
1063 g = this->GetGeomMatrix(i);
1064 g->GetTranslation(t);
1067 t[j] += gRandom->Gaus(0.0,stran[j]);
1068 r[j] += gRandom->Gaus(0.0, srot[j]);
1070 g->SetTranslation(t);
1075 //______________________________________________________________________
1076 void AliITSgeom::RandomCylindericalChange(const Float_t *stran,
1077 const Float_t *srot){
1078 // This function performs a Gaussian random displacement and/or
1079 // rotation about the present global position of each active
1080 // volume/detector of the ITS. The sigma of the random displacement
1081 // is determined by the three element array stran, for the
1082 // r rphi and z translations, and the three element array srot,
1083 // for the three rotation about the axis x y and z. This random change
1084 // in detector position allow for the simulation of a random uncertainty
1085 // in the detector positions of the ITS.
1087 // Float_t *stran A 3 element array representing the global translations
1088 // variances. The elements are r,theta,z in cm/readians.
1089 // Float_t *srot A 3 element array representing the global rotation
1090 // angles variances about the three axis x,y,z in radians.
1094 Double_t t[3],ro[3],r,r0,phi,rphi;
1096 AliITSgeomMatrix *g;
1098 fTrans = (fTrans && 0xfffd) + 2; // set bit 1 true.
1099 for(i=0;i<fNmodules;i++){
1100 g = this->GetGeomMatrix(i);
1101 g->GetTranslation(t);
1103 r = r0= TMath::Hypot(t[1],t[0]);
1104 phi = TMath::ATan2(t[1],t[0]);
1106 r += ran.Gaus(0.0,stran[0]);
1107 rphi += ran.Gaus(0.0,stran[1]);
1109 t[0] = r*TMath::Cos(phi);
1110 t[1] = r*TMath::Sin(phi);
1111 t[2] += ran.Gaus(0.0,stran[2]);
1113 ro[j] += ran.Gaus(0.0, srot[j]);
1115 g->SetTranslation(t);
1120 //______________________________________________________________________
1121 void AliITSgeom::GeantToTracking(AliITSgeom &source){
1122 // Copy the geometry data but change it to go between the ALICE
1123 // Global coordinate system to that used by the ITS tracking. A slightly
1124 // different coordinate system is used when tracking. This coordinate
1125 // system is only relevant when the geometry represents the cylindrical
1126 // ALICE ITS geometry. For tracking the Z axis is left alone but X-> -Y
1127 // and Y-> X such that X always points out of the ITS cylinder for every
1128 // layer including layer 1 (where the detectors are mounted upside down).
1130 // AliITSgeom &source The AliITSgeom class with which to make this
1133 // return *this The a new copy of source.
1136 <img src="picts/ITS/AliITSgeomMatrix_T1.gif">
1139 Int_t i,j,k,l,id[3];
1140 Double_t r0[3][3],r1[3][3];
1141 Double_t a0[3][3] = {{0.,+1.,0.},{-1.,0.,0.},{0.,0.,+1.}};
1142 Double_t a1[3][3] = {{0.,-1.,0.},{+1.,0.,0.},{0.,0.,+1.}};
1144 *this = source; // copy everything
1145 for(i=0;i<GetIndexMax();i++){
1146 GetGeomMatrix(i)->GetIndex(id);
1147 GetGeomMatrix(i)->GetMatrix(r0);
1148 if(id[0]==1){ // Layer 1 is treated different from the others.
1149 for(j=0;j<3;j++) for(k=0;k<3;k++){
1151 for(l=0;l<3;l++) r1[j][k] += a0[j][l]*r0[l][k];
1154 for(j=0;j<3;j++) for(k=0;k<3;k++){
1156 for(l=0;l<3;l++) r1[j][k] += a1[j][l]*r0[l][k];
1159 GetGeomMatrix(i)->SetMatrix(r1);
1161 this->fTrans = (this->fTrans && 0xfffe) + 1; // set bit 0 true.
1164 //______________________________________________________________________
1165 Int_t AliITSgeom::GetNearest(const Double_t g[3],Int_t lay){
1166 // Finds the Detector (Module) that is nearest the point g [cm] in
1167 // ALICE Global coordinates. If layer !=0 then the search is restricted
1168 // to Detectors (Modules) in that particular layer.
1170 // Double_t g[3] The ALICE Cartesean global coordinate from which the
1171 // distance is to be calculated with.
1172 // Int_t lay The layer to restrict the search to. If layer=0 then
1173 // all layers are searched. Default is lay=0.
1175 // return The module number representing the nearest module.
1177 Double_t d,dn=1.0e10;
1178 Bool_t t=lay!=0; // skip if lay = 0 default value check all layers.
1180 for(i=0;i<fNmodules;i++){
1181 if(t){GetModuleId(i,l,a,e);if(l!=lay) continue;}
1182 if((d=GetGeomMatrix(i)->Distance2(g))<dn){
1189 //______________________________________________________________________
1190 void AliITSgeom::GetNearest27(const Double_t g[3],Int_t n[27],Int_t lay){
1191 // Finds 27 Detectors (Modules) that are nearest the point g [cm] in
1192 // ALICE Global coordinates. If layer !=0 then the search is restricted
1193 // to Detectors (Modules) in that particular layer. The number 27 comes
1194 // from including the nearest detector and all those around it (up, down,
1195 // left, right, forwards, backwards, and the corners).
1197 // Double_t g[3] The ALICE Cartesean global coordinate from which the
1198 // distance is to be calculated with.
1199 // Int_t lay The layer to restrict the search to. If layer=0 then
1200 // all layers are searched. Default is lay=0.
1202 // Int_t n[27] The module number representing the nearest 27 modules
1204 Int_t i,l,a,e,in[27]={0,0,0,0,0,0,0,0,0,
1206 0,0,0,0,0,0,0,0,0,};
1207 Double_t d,dn[27]={1.0e10,1.0e10,1.0e10,1.0e10,1.0e10,1.0e10,
1208 1.0e10,1.0e10,1.0e10,1.0e10,1.0e10,1.0e10,
1209 1.0e10,1.0e10,1.0e10,1.0e10,1.0e10,1.0e10,
1210 1.0e10,1.0e10,1.0e10,1.0e10,1.0e10,1.0e10,
1211 1.0e10,1.0e10,1.0e10};
1212 Bool_t t=(lay!=0); // skip if lay = 0 default value check all layers.
1214 for(i=0;i<fNmodules;i++){
1215 if(t){GetModuleId(i,l,a,e);if(l!=lay) continue;}
1217 d = GetGeomMatrix(i)->Distance2(g);
1219 for(e=26;e>a;e--){dn[e] = dn[e-1];in[e] = in[e-1];}
1220 dn[a] = d; in[a] = i;
1224 for(i=0;i<27;i++) n[i] = in[i];
1226 //----------------------------------------------------------------------