]> git.uio.no Git - u/mrichter/AliRoot.git/blob - GEODB/AliGSphere.cxx
This commit was generated by cvs2svn to compensate for changes in r209,
[u/mrichter/AliRoot.git] / GEODB / AliGSphere.cxx
1    // -*- C++ -*-
2 // 
3 // 1998/07/23
4 // ---------------------------------------------------------------------------
5 //
6 // AliGSphere Class
7 //
8 // This file is part of the ALICE Geometry Database .
9 //
10 // Author:  Joana E. Santo
11 //
12 // ---------------------------------------------------------------------------
13
14 #include <TView.h>
15 #include <TVirtualPad.h>
16 #include <iostream.h>
17 #include <TCanvas.h>
18 #include <TGLKernelABC.h>
19 #include "TROOT.h"
20 #include "AliGSphere.h"
21
22
23 ClassImp(AliGSphere)
24
25 AliGSphere::AliGSphere()
26 {
27     /* Default Constructor */
28     faX          = 1.;  // Coeff along Ox
29     faY          = 1.;  // Coeff along Oy
30     faZ          = 1.;  // Coeff along Oz
31     fAspectRatio = 1.;  // Relation between asumth and grid size (by default 1.0)
32     fCoTab       = NULL;// Table of cos(fPhimin) .... cos(Phi)
33     fCoThetaTab  = NULL;// Table of sin(gThemin) .... cos(Theta)
34     fName        = "";
35     fNdiv        = 0;   // number of divisions
36     fNz          = 0;   // number of sections
37     fPhimax      = 0.;  // maximum phi
38     fPhimin      = 0.;  // minimum phi
39     fRmax        = 0.;  // maximum radius
40     fRmin        = 0.;  // minimum radius
41     fSiTab       = NULL;// Table of sin(fPhimin) .... sin(Phi)
42     fThemax      = 0.;  // maximum theta
43     fThemin      = 0.;  // minimum theta
44     fTitle       = "";
45 }
46
47 // ---------------------------------------------------------------------------
48
49 AliGSphere::AliGSphere(Text_t *name, Text_t *title, Float_t rmin, Float_t rmax, Float_t themin, Float_t themax, Float_t phimin, Float_t phimax) : AliGShape(name, title)
50 {
51     /* Constructor */
52     faX          = 1.;    // Coeff along Ox
53     faY          = 1.;    // Coeff along Oy
54     faZ          = 1.;    // Coeff along Oz
55     fAspectRatio = 1.;    // Relation between asumth and grid size (by default 1.0)
56     fCoTab       = NULL;  // Table of cos(fPhimin) .... cos(Phi)
57     fCoThetaTab  = NULL;  // Table of sin(gThemin) .... cos(Theta)
58     fNdiv        = 0;     // number of divisions
59     fNz          = 0;     // number of sections
60     fPhimax      = phimax;// maximum phi
61     fPhimin      = phimin;// minimum phi
62     fRmax        = rmax;  // maximum radius
63     fRmin        = rmin;  // minimum radius
64     fSiTab       = NULL;  // Table of sin(fPhimin) .... sin(Phi)
65     fThemax      = themax;// maximum theta
66     fThemin      = themin;// minimum theta
67
68     SetNumberOfDivisions (20);
69 }
70
71 // ---------------------------------------------------------------------------
72
73 AliGSphere::AliGSphere(AliGSphere *sphere) 
74 {
75     /* Copy Constructor */
76     faX          = 1.;    // Coeff along Ox
77     faY          = 1.;    // Coeff along Oy
78     faZ          = 1.;    // Coeff along Oz
79     fAspectRatio = 1.;    // Relation between asumth and grid size (by default 1.0)
80     fColor       = sphere->fColor;
81     fCoTab       = NULL;  // Table of cos(fPhimin) .... cos(Phi)
82     fCoThetaTab  = NULL;  // Table of sin(gThemin) .... cos(Theta)
83     fNdiv        = 0;     // number of divisions
84     fNz          = 0;     // number of sections
85     fPhimax      = sphere->fPhimax;// maximum phi
86     fPhimin      = sphere->fPhimin;// minimum phi
87     fRmax        = sphere->fRmax;  // maximum radius
88     fRmin        = sphere->fRmin;  // minimum radius
89     fSiTab       = NULL;  // Table of sin(fPhimin) .... sin(Phi)
90     fThemax      = sphere->fThemax;// maximum theta
91     fThemin      = sphere->fThemin;// minimum theta
92
93     SetNumberOfDivisions (20);
94 }
95 // ---------------------------------------------------------------------------
96
97 AliGSphere::AliGSphere(Text_t *name, Text_t *title, Float_t rmax) : AliGShape(name, title)
98 {
99     /* Simplified Constructor */
100     faX          = 1.;   // Coeff along Ox
101     faY          = 1.;   // Coeff along Oy
102     faZ          = 1.;   // Coeff along Oz
103     fAspectRatio = 1.;   // Relation between asumth and grid size (by default 1.0)
104     fCoTab       = NULL; // Table of cos(fPhimin) .... cos(Phi)
105     fCoThetaTab  = NULL; // Table of sin(gThemin) .... cos(Theta)
106     fNdiv        = 0;    // number of divisions
107     fNz          = 0;    // number of sections
108     fPhimax      = 360.; // maximum phi
109     fPhimin      = 0.;   // minimum phi
110     fRmax        = rmax; // maximum radius
111     fRmin        = 0.;   // minimum radius
112     fSiTab       = NULL; // Table of sin(fPhimin) .... sin(Phi)
113     fThemax      = 180.; // maximum theta
114     fThemin      = 0.;   // minimum theta
115
116     SetNumberOfDivisions (20);
117 }
118
119 // ---------------------------------------------------------------------------
120
121 AliGSphere::~AliGSphere() {
122     /* Destructor */
123     delete [] fCoThetaTab;  // Table of sin(gThemin) .... cos(Theta)
124     delete [] fCoTab;
125     delete [] fSiTab;
126 }
127
128 // ---------------------------------------------------------------------------
129
130 void AliGSphere::DrawShape(Option_t *option)
131 {
132     Draw(option);
133     gPad->Update();
134 }
135
136 //-------------------------------------------------------------------------
137
138 //void AliGSphere::Draw()
139 void AliGSphere::Draw(Option_t *option)
140 {
141     TString opt = option;
142     opt.ToLower();
143
144     if( !gPad ) {
145         gPad = new TCanvas("AliGSphere","AliGSphere",0,0,400,300);
146         gPad->Range(0,0,1,1);
147         gPad->SetFillColor(32); // Light Green
148         gPad->SetBorderSize(3);
149         gPad->SetBorderMode(0); // -1 (down) 0 (no) 1 (up)
150     }
151     else {
152         if( !opt.Contains("same") ) {
153             gPad->Clear();
154             gPad->SetName("AliGSphere");
155             gPad->SetTitle("AliGSphere");
156         }
157         else {
158             gPad->SetName("AliShapes");
159             gPad->SetTitle("AliShapes"); 
160         }
161     }
162
163     AppendPad(option);
164     TView *view = gPad->GetView();
165
166     if (!view)
167         view = new TView(1);
168
169     view->SetAutoRange(kTRUE);
170     Paint(option);
171     view->SetAutoRange(kFALSE);   
172 }
173
174 // ---------------------------------------------------------------------------
175
176 void AliGSphere::Paint(Option_t *option)
177 {
178 //*-*-*-*-*-*-*-*Paint this 3-D shape with its current attributes*-*-*-*-*-*-*-*
179 //*-*            ================================================
180
181     SetLineColor( GetCol() );
182
183     Int_t i, j;
184     const Int_t n = GetNumberOfDivisions()+1;
185     Int_t nz = fNz+1;
186     Int_t numpoints = 2*n*nz;
187     if (nz < 2) return;
188
189     if (numpoints <= 0) return;
190     //*-* Allocate memory for points *-*
191
192     Float_t *points = new Float_t[3*numpoints];
193     if (!points) return;
194     SetPoints(points);
195
196     if (gPad->GetView3D()) PaintGLPoints(points);
197
198  //==  for (i = 0; i < numpoints; i++)
199  //==          gNode->Local2Master(&points[3*i],&points[3*i]);
200
201     Bool_t specialCase = kFALSE;
202
203     if (TMath::Abs(TMath::Sin(2*(fPhimax - fPhimin))) <= 0.01)  //mark this as a very special case, when
204         specialCase = kTRUE;                                  //we have to draw this PCON like a TUBE
205
206     X3DBuffer *buff = new X3DBuffer;
207     if (buff) {
208         buff->numPoints = numpoints;
209         buff->numSegs   = 4*(nz*n-1+(specialCase == kTRUE));
210         buff->numPolys  = 2*(nz*n-1+(specialCase == kTRUE));
211     }
212
213 //*-* Allocate memory for points *-*
214
215     buff->points = points;
216
217     Int_t c = ((GetLineColor() % 8) - 1) * 4;     // Basic colors: 0, 1, ... 7
218     if (c < 0) c = 0;
219
220 //*-* Allocate memory for segments *-*
221
222     Int_t indx, indx2, k;
223     indx = indx2 = 0;
224
225     buff->segs = new Int_t[buff->numSegs*3];
226     if (buff->segs) {
227
228         //inside & outside spheres, number of segments: 2*nz*(n-1)
229         //             special case number of segments: 2*nz*n
230         for (i = 0; i < nz*2; i++) {
231             indx2 = i*n;
232             for (j = 1; j < n; j++) {
233                 buff->segs[indx++] = c;
234                 buff->segs[indx++] = indx2+j-1;
235                 buff->segs[indx++] = indx2+j;
236             }
237             if (specialCase) {
238                 buff->segs[indx++] = c;
239                 buff->segs[indx++] = indx2+j-1;
240                 buff->segs[indx++] = indx2;
241             }
242         }
243
244         //bottom & top lines, number of segments: 2*n
245         for (i = 0; i < 2; i++) {
246             indx2 = i*(nz-1)*2*n;
247             for (j = 0; j < n; j++) {
248                 buff->segs[indx++] = c;
249                 buff->segs[indx++] = indx2+j;
250                 buff->segs[indx++] = indx2+n+j;
251             }
252         }
253
254         //inside & outside spheres, number of segments: 2*(nz-1)*n
255         for (i = 0; i < (nz-1); i++) {
256
257             //inside sphere
258             indx2 = i*n*2;
259             for (j = 0; j < n; j++) {
260                 buff->segs[indx++] = c+2;
261                 buff->segs[indx++] = indx2+j;
262                 buff->segs[indx++] = indx2+n*2+j;
263             }
264             //outside sphere
265             indx2 = i*n*2+n;
266             for (j = 0; j < n; j++) {
267                 buff->segs[indx++] = c+3;
268                 buff->segs[indx++] = indx2+j;
269                 buff->segs[indx++] = indx2+n*2+j;
270             }
271         }
272
273         //left & right sections, number of segments: 2*(nz-2)
274         //          special case number of segments: 0
275         /*if (!specialCase) {
276             for (i = 1; i < (nz-1); i++) {
277                 for (j = 0; j < 2; j++) {
278                     buff->segs[indx++] = c;
279                     buff->segs[indx++] =  2*i    * n + j*(n-1);
280                     buff->segs[indx++] = (2*i+1) * n + j*(n-1);
281                 }
282             }
283         }*/
284     }
285
286
287     Int_t m = n - 1 + (specialCase == kTRUE);
288
289 //*-* Allocate memory for polygons *-*
290
291     indx = 0;
292
293     buff->polys = new Int_t[buff->numPolys*6];
294
295     if (buff->polys) {
296         //bottom & top, number of polygons: 2*(n-1)
297         // special case number of polygons: 2*n
298         for (i = 0; i < 2; i++) {
299             for (j = 0; j < n-1; j++) {
300                 buff->polys[indx++] = c+3;
301                 buff->polys[indx++] = 4;
302                 buff->polys[indx++] = 2*nz*m+i*n+j;
303                 buff->polys[indx++] = i*(nz*2-2)*m+m+j;
304                 buff->polys[indx++] = 2*nz*m+i*n+j+1;
305                 buff->polys[indx++] = i*(nz*2-2)*m+j;
306             }
307             if (specialCase) {
308                 buff->polys[indx++] = c+3;
309                 buff->polys[indx++] = 4;
310                 buff->polys[indx++] = 2*nz*m+i*n+j;
311                 buff->polys[indx++] = i*(nz*2-2)*m+m+j;
312                 buff->polys[indx++] = 2*nz*m+i*n;
313                 buff->polys[indx++] = i*(nz*2-2)*m+j;
314             }
315         }
316
317
318         //inside & outside, number of polygons: (nz-1)*2*(n-1)
319         for (k = 0; k < (nz-1); k++) {
320             for (i = 0; i < 2; i++) {
321                 for (j = 0; j < n-1; j++) {
322                     buff->polys[indx++] = c+i;
323                     buff->polys[indx++] = 4;
324                     buff->polys[indx++] = (2*k+i*1)*m+j;
325                     buff->polys[indx++] = nz*2*m+(2*k+i*1+2)*n+j;
326                     buff->polys[indx++] = (2*k+i*1+2)*m+j;
327                     buff->polys[indx++] = nz*2*m+(2*k+i*1+2)*n+j+1;
328                 }
329                 if (specialCase) {
330                     buff->polys[indx++] = c+i;
331                     buff->polys[indx++] = 4;
332                     buff->polys[indx++] = (2*k+i*1)*m+j;
333                     buff->polys[indx++] = nz*2*m+(2*k+i*1+2)*n+j;
334                     buff->polys[indx++] = (2*k+i*1+2)*m+j;
335                     buff->polys[indx++] = nz*2*m+(2*k+i*1+2)*n;
336                 }
337             }
338         }
339
340         //left & right sections, number of polygons: 2*(nz-1)
341         //          special case number of polygons: 0
342         /*if (!specialCase) {
343             indx2 = nz*2*(n-1);
344             for (k = 0; k < (nz-1); k++) {
345                 for (i = 0; i < 2; i++) {
346                     buff->polys[indx++] = c+2;
347                     buff->polys[indx++] = 4;
348                     buff->polys[indx++] = k==0 ? indx2+i*(n-1) : indx2+2*nz*n+2*(k-1)+i;
349                     buff->polys[indx++] = indx2+2*(k+1)*n+i*(n-1);
350                     buff->polys[indx++] = indx2+2*nz*n+2*k+i;
351                     buff->polys[indx++] = indx2+(2*k+3)*n+i*(n-1);
352                 }
353             }
354             buff->polys[indx-8] = indx2+n;
355             buff->polys[indx-2] = indx2+2*n-1;
356         }*/
357     }
358
359     //*-* Paint in the pad
360     //*-* Paint in the pad
361     Bool_t rangeView = strcmp(option,"range")==0 ? kTRUE : kFALSE;
362     PaintShape(buff,rangeView);
363     //PaintShape(buff);
364
365     if (strstr(option, "x3d")) {
366         if(buff && buff->points && buff->segs)
367             FillX3DBuffer(buff);
368         else {
369             gSize3D.numPoints -= buff->numPoints;
370             gSize3D.numSegs   -= buff->numSegs;
371             gSize3D.numPolys  -= buff->numPolys;
372         }
373     }
374
375     delete [] points;
376     if (buff->segs)     delete [] buff->segs;
377     if (buff->polys)    delete [] buff->polys;
378     if (buff)           delete    buff;
379
380     
381
382 }
383
384 // ---------------------------------------------------------------------------
385
386 void AliGSphere::SetEllipse(Float_t *factors)
387 {
388   if (factors[0] > 0) faX = factors[0];
389   if (factors[1] > 0) faY = factors[1];
390   if (factors[2] > 0) faZ = factors[2];
391   MakeTableOfCoSin();
392 }
393
394 // ---------------------------------------------------------------------------
395
396 void AliGSphere::SetNumberOfDivisions (Int_t p)
397 {
398     if (GetNumberOfDivisions () == p)
399         return;
400     fNdiv = p;
401     fNz   = Int_t(fAspectRatio*fNdiv*(fThemax - fThemin )/(fPhimax - fPhimin )) + 1;
402     MakeTableOfCoSin();
403 }
404
405 // ---------------------------------------------------------------------------
406
407 void AliGSphere::SetPoints(Float_t *buff)
408 {
409 //*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*Create SPHE points*-*-*-*-*-*-*-*-*-*-*-*-*-*-*
410 //*-*                            ==================
411     Int_t i, j;
412     Int_t indx = 0;
413
414     if (buff) {
415         Int_t n = GetNumberOfDivisions()+1;
416
417 //*-* We've to check whether the table does exist and create it
418 //*-* since fCoTab/fSiTab are not saved with any TShape::Streamer function
419         if (!fCoTab)   MakeTableOfCoSin();
420
421         Float_t z;
422         for (i = 0; i < fNz+1; i++)
423         {
424             z = fRmin * fCoThetaTab[i]; // fSinPhiTab[i];
425             Float_t sithet = TMath::Sqrt(TMath::Abs(1-fCoThetaTab[i]*fCoThetaTab[i]));
426             Float_t zi = fRmin*sithet;
427             for (j = 0; j < n; j++)
428             {
429                 buff[indx++] = zi * fCoTab[j];
430                 buff[indx++] = zi * fSiTab[j];
431                 buff[indx++] = z;
432             }
433             z = fRmax * fCoThetaTab[i];
434             zi = fRmax*sithet;
435             for (j = 0; j < n; j++)
436             {
437                 buff[indx++] = zi * fCoTab[j];
438                 buff[indx++] = zi * fSiTab[j];
439                 buff[indx++] = z;
440             }
441         }
442     }
443 }
444
445 // ---------------------------------------------------------------------------
446
447 void AliGSphere::MakeTableOfCoSin()
448 {
449     const Double_t PI  = TMath::ATan(1) * 4.0;
450     const Double_t ragrad  = PI/180.0;
451
452     Float_t dphi = fPhimax - fPhimin;
453     while (dphi > 360) dphi -= 360;
454
455     Float_t dtet = fThemax - fThemin;
456     while (dtet > 180) dtet -= 180;
457
458     Int_t j;
459     Int_t n = GetNumberOfDivisions () + 1;
460     if (fCoTab)
461         delete [] fCoTab; // Delete the old tab if any
462         fCoTab = new Double_t [n];
463     if (!fCoTab ) return;
464
465     if (fSiTab)
466         delete [] fSiTab; // Delete the old tab if any
467     fSiTab = new Double_t [n];
468     if (!fSiTab ) return;
469
470     Double_t range   = Double_t(dphi * ragrad);
471     Double_t phi1    = Double_t(fPhimin  * ragrad);
472     Double_t angstep = range/(n-1);
473
474     Double_t ph = phi1;
475     for (j = 0; j < n; j++)
476     {
477         ph = phi1 + j*angstep;
478         fCoTab[j] = TMath::Cos(ph);
479         fSiTab[j] = TMath::Sin(ph);
480     }
481
482     n  = fNz + 1;
483
484     if (fCoThetaTab)
485         delete [] fCoThetaTab; // Delete the old tab if any
486     fCoThetaTab = new Double_t [n];
487     if (!fCoThetaTab ) return;
488
489     range   = Double_t(dtet * ragrad);
490     phi1    = Double_t(fThemin  * ragrad);
491     angstep = range/(n-1);
492
493     ph = phi1;
494     for (j = 0; j < n; j++)
495     {
496         fCoThetaTab[n-j-1] = TMath::Cos(ph);
497         ph += angstep;
498     }
499
500 }
501
502 // ---------------------------------------------------------------------------
503
504 void AliGSphere::PaintGLPoints(Float_t *vertex)
505 {
506     gGLKernel->PaintCone(vertex,-(GetNumberOfDivisions()+1),fNz+1);
507 }
508
509 // ---------------------------------------------------------------------------
510
511 void AliGSphere::Sizeof3D() const
512 {
513 //*-*-*-*-*-*-*Return total X3D size of this shape with its attributes*-*-*-*-*-*
514 //*-*          =======================================================
515
516     cout << " Entra en AliGSphere::Sizeof3D() " << endl;
517
518     Int_t n;
519
520     n = GetNumberOfDivisions()+1;
521     Int_t nz = fNz+1;
522
523     //cout << " n = " << n << "   y   nz = " << nz << endl;
524
525     Bool_t specialCase = kFALSE;
526
527     if (TMath::Abs(TMath::Sin(2*(fPhimax - fPhimin))) <= 0.01)  //mark this as a very special case, when
528           specialCase = kTRUE;                                  //we have to draw this PCON like a TUBE
529
530     gSize3D.numPoints += 2*n*nz;
531     gSize3D.numSegs   += 4*(nz*n-1+(specialCase == kTRUE));
532     gSize3D.numPolys  += 2*(nz*n-1+(specialCase == kTRUE));
533 }
534
535 // ---------------------------------------------------------------------------
536
537 void AliGSphere::Streamer(TBuffer &R__b)
538 {
539    // Stream an object of class AliGSphere.
540
541    if (R__b.IsReading()) {
542       Version_t R__v = R__b.ReadVersion(); if (R__v) { }
543       AliGShape::Streamer(R__b);
544       R__b >> fAspectRatio;
545       R__b.ReadArray(fCoTab); //
546       R__b.ReadArray(fCoThetaTab); //
547       R__b >> fNdiv;
548       R__b >> fNz;
549       R__b.ReadArray(fSiTab); //
550       R__b >> faX;
551       R__b >> faY;
552       R__b >> faZ;
553       R__b >> fPhimax;
554       R__b >> fPhimin;
555       R__b >> fRmax;
556       R__b >> fRmin;
557       R__b >> fThemax;
558       R__b >> fThemin;
559    } else {
560       R__b.WriteVersion(AliGSphere::IsA());
561       AliGShape::Streamer(R__b);
562       R__b << fAspectRatio;
563       R__b.WriteArray(fCoTab, GetNumberOfDivisions()+1); //
564       R__b.WriteArray(fCoThetaTab, fNz+1); //
565       R__b << fNdiv;
566       R__b << fNz;
567       R__b.WriteArray(fSiTab, GetNumberOfDivisions()+1); //
568       R__b << faX;
569       R__b << faY;
570       R__b << faZ;
571       R__b << fPhimax;
572       R__b << fPhimin;
573       R__b << fRmax;
574       R__b << fRmin;
575       R__b << fThemax;
576       R__b << fThemin;
577    }
578 }
579
580 // ---------------------------------------------------------------------------
581