56363b6d40929771a140ce7fdcc56e46facefa9f
[u/mrichter/AliRoot.git] / STRUCT / AliALIFE.cxx
1 /**************************************************************************
2  * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
3  *                                                                        *
4  * Author: The ALICE Off-line Project.                                    *
5  * Contributors are mentioned in the code where appropriate.              *
6  *                                                                        *
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  **************************************************************************/
15
16 /*
17 $Log$
18 Revision 1.3.6.1  2002/08/29 18:08:17  hristov
19 Replace strcpy by assignment operator
20
21 Revision 1.3  2001/10/31 15:56:54  morsch
22 Correction in OnionCone.
23
24 Revision 1.2  2000/10/10 06:40:25  hristov
25 Bug fixes
26
27 Revision 1.1  2000/07/26 15:10:57  morsch
28 Helper class to write geometry in ALIFE format in parallel with Geant geometry definition.
29
30 */
31
32 #include <AliALIFE.h>
33
34 ClassImp(AliALIFE)
35
36     AliALIFE::AliALIFE(const char* file1, const char* file2)
37 {  
38 // Constructor
39     fNBodies = 0; 
40     fNVolumes= 0; 
41     fBodyFile   = file1;   // File for Fluka bodies
42     fVolumeFile = file2;
43     fFile1=fopen(fBodyFile,"w");
44     fFile2=fopen(fVolumeFile,"w");
45     BodyHeader();
46     VolumeHeader();
47     fDefaultVolume1 = "DEFAU1";
48     fDefaultVolume2 = "DEFAU2";    
49 }
50
51     AliALIFE::AliALIFE()
52 {
53 // Default constructor
54     fBodyFile   = "FlukaBody.inp";  
55     fVolumeFile = "FlukaVolume.inp";
56     fFile1=fopen(fBodyFile,"w");
57     fFile2=fopen(fVolumeFile,"w");
58     BodyHeader();
59     VolumeHeader();
60 }
61
62 void AliALIFE::BodyHeader()
63 {
64 // Write header for body definitions
65     fprintf(fFile1,"*\n");        
66     fprintf(fFile1,"GEOBEGIN                                                              COMBINAT\n");
67     fprintf(fFile1,"    0    0         AliRoot Generated\n");
68     fprintf(fFile1,"*\n");
69     fprintf(fFile1,"*== Body Definitions ================================================\n");
70     fprintf(fFile1,"*\n");
71                             
72 }
73
74
75 void AliALIFE::VolumeHeader()
76 {
77 // Write header for region (volume)  definitions
78     fprintf(fFile2,"REGIONS\n");
79     fprintf(fFile2,"*\n");
80     fprintf(fFile2,"*== Region Definitions =================================================\n");
81     fprintf(fFile2,"*\n");
82 }
83
84
85 void AliALIFE:: Cylinder(Float_t rmin, Float_t rmax, 
86                          Float_t zmin, Float_t zmax, 
87                          Float_t pos[3], 
88                          char* Material, char* Field, char* Cuts) 
89 {
90 // Simple cylinder
91 //
92 // Bodies
93 // ^^^^^^
94     char name1[5], name2[5], name3[5], name4[5];
95
96 //  outer radius
97     sprintf(name1, "R%4.4d", fNBodies++);
98     fprintf(fFile1,"%5s ZCC%10.3f%10.3f%10.3f\n",name1, pos[0], pos[1], rmax); // inner radius
99     sprintf(name2, "R%4.4d", fNBodies++);
100     fprintf(fFile1,"%5s ZCC%10.3f%10.3f%10.3f\n",name2, pos[0], pos[1], rmin); 
101 // z-max
102     sprintf(name3, "Z%4.4d", fNBodies++);
103     fprintf(fFile1,"%5s XYP%10.3f\n",name3, zmax); 
104 // z-min
105     sprintf(name4, "Z%4.4d", fNBodies++);
106     fprintf(fFile1,"%5s XYP%10.3f\n",name4, zmin); 
107 //
108 // Volumes
109 // ^^^^^^^
110
111     fprintf(fFile2,">%s:%s\n", Material, Field);
112     fprintf(fFile2,"EMFCUT=%s\n", Cuts);
113     fprintf(fFile2,"WW-FACTOR=%s\n", Cuts);
114     if (rmin >0) {
115         fprintf(fFile2,"+%s-%s+%s-%s\n", name1, name2, name3, name4);
116     } else {
117         fprintf(fFile2,"+%s+%s-%s\n", name1, name3, name4);
118     }
119     
120     fprintf(fFile2,"\n");    
121 }
122
123 void AliALIFE::OnionCylinder(Float_t* r, Int_t nr, Float_t zmin, Float_t zmax,
124                              Float_t pos[3], char** Materials, 
125                              char** Fields, char** Cuts) 
126 {
127 //
128 // Concentric cylinders
129 //
130
131 // Bodies
132 // ^^^^^^
133     char nameRin[6], nameRou[6], nameZin[6], nameZou[6];
134 // z-limits
135 // z-max
136     sprintf(nameZou, "Z%4.4d", fNBodies++);
137     nameZou[5]='\0';
138     
139     fprintf(fFile1,"%5s XYP%10.3f\n",nameZou, zmax); 
140 // z-min
141     sprintf(nameZin, "Z%4.4d", fNBodies++);
142     nameZin[5]='\0';
143     fprintf(fFile1,"%5s XYP%10.3f\n",nameZin, zmin); 
144
145 // inner radius
146     sprintf(nameRin, "R%4.4d", fNBodies++);
147     nameRin[5]='\0';
148     fprintf(fFile1,"%5s ZCC%10.3f%10.3f%10.3f\n",nameRin, pos[0], pos[1], r[0]); 
149
150     Int_t i;
151     for (i=1; i<nr; i++) {
152 //  outer radius
153         sprintf(nameRou, "R%4.4d", fNBodies++);
154         nameRou[5]='\0';
155         fprintf(fFile1,"%5s ZCC%10.3f%10.3f%10.3f\n",
156                 nameRou, pos[0], pos[1], r[i]);         
157 //
158 // Volumes
159 // ^^^^^^^
160         if (Fields && Cuts) {
161             fprintf(fFile2,">%s:%s\n", Materials[i-1], Fields[i-1]);
162             fprintf(fFile2,"EMFCUT=%s\n", Cuts[i-1]);
163             fprintf(fFile2,"WW-FACTOR=%s\n", Cuts[i-1]);
164         } else {
165             fprintf(fFile2,">%s:%s\n", Materials[i-1], "MF");
166             fprintf(fFile2,"EMFCUT=%s\n", "$UNSHIELDED");
167             fprintf(fFile2,"WW-FACTOR=%s\n", "$UNSHIELDED");
168         }
169         if (r[i-1] != 0.) {
170             fprintf(fFile2,"+%5s-%5s+%5s-%5s\n", nameZou, nameZin, nameRou, nameRin);
171         } else {
172             fprintf(fFile2,"+%5s-%5s+%5s\n", nameZou, nameZin, nameRou);
173         }
174         fprintf(fFile2,"\n");
175         strcpy(nameRin,nameRou);
176     }
177 }
178
179
180 void AliALIFE::Cone(Float_t rmin1, Float_t rmin2, 
181                      Float_t rmax1, Float_t rmax2,
182                      Float_t zmin, Float_t zmax, 
183                      Float_t pos[3], 
184                      char* Material, char* Field, char* Cuts) 
185 {
186 // Simple cone 
187
188 //
189 // Bodies
190 // ^^^^^^
191     char nameCou[6], nameCin[6];
192     Float_t d, r1, r2;
193     char nameZin[6], nameZou[6];
194 // z-max
195     sprintf(nameZou, "Z%4.4d", fNBodies++);
196     fprintf(fFile1,"%5s XYP%10.3f\n",nameZou, zmax); 
197 // z-min
198     sprintf(nameZin, "Z%4.4d", fNBodies++);
199     fprintf(fFile1,"%5s XYP%10.3f\n",nameZin, zmin); 
200     
201 //  outer radius
202     d=zmax-zmin;
203     if (rmax1 >= 0. && rmax2 >= 0.) {
204         if (rmax1!=rmax2) {
205             if (rmax1 > rmax2) {
206                 pos[2]=zmin;
207                 r1=rmax1;
208                 r2=rmax2;
209             } else {
210                 d=-d;
211                 pos[2]=zmax;
212                 r1=rmax2;
213                 r2=rmax1;
214             }
215             sprintf(nameCou, "C%4.4d", fNBodies++);
216             fprintf(fFile1,"%5s TRC%10.3f%10.3f%10.3f%10.3f%10.3f%10.3f\n",
217                     nameCou, pos[0], pos[1], pos[2], 0., 0., d); 
218             fprintf(fFile1,"         %10.3f%10.3f\n",r1,r2);
219         } else {
220             sprintf(nameCou, "C%4.4d", fNBodies++);
221             fprintf(fFile1,"%5s ZCC%10.3f%10.3f%10.3f\n",
222                     nameCou, pos[0], pos[1], rmax1); 
223         } 
224     }else {
225       fDefaultVolume1 = nameCou;
226     }
227
228     
229     
230 // inner radius
231     if (rmin1 >= 0. && rmin2 >= 0.) {
232         if (rmin1!=rmin2) {
233             if (rmin1 != 0 && rmin2 !=0) {
234                 d=zmax-zmin;
235                 if (rmin1 > rmin2) {
236                     pos[2]=zmin;
237                     r1=rmin1;
238                     r2=rmin2;
239                 } else {
240                     pos[2]=zmax;
241                     r1=rmin2;
242                     r2=rmin1;
243                     d=-d;
244                 }
245                 sprintf(nameCin, "C%4.4d", fNBodies++);
246                 fprintf(fFile1,"%5s TRC%10.3f%10.3f%10.3f%10.3f%10.3f%10.3f\n",
247                         nameCin, pos[0], pos[1], pos[2], 0., 0., d); 
248                 fprintf(fFile1,"         %10.3f%10.3f\n",r1,r2);
249             } 
250         } else {
251             sprintf(nameCin, "C%4.4d", fNBodies++);
252             fprintf(fFile1,"%5s ZCC%10.3f%10.3f%10.3f\n",
253                     nameCin, pos[0], pos[1], rmin1); 
254         } 
255     }else {
256       fDefaultVolume2 = nameCin;
257     }
258
259
260
261 //
262 // Volumes
263 // ^^^^^^^
264     fprintf(fFile2,">%s:%s\n", Material, Field);
265     fprintf(fFile2,"EMFCUT=%s\n", Cuts);
266     fprintf(fFile2,"WW-FACTOR=%s\n", Cuts);
267     if (rmin1 != 0 && rmin2 !=0) {
268         fprintf(fFile2,"+%s-%s+%s-%s\n", nameCou, nameCin, nameZou, nameZin);
269     } else {
270         fprintf(fFile2,"+%s+%s-%s\n", nameCou, nameZou, nameZin);
271     }
272     fprintf(fFile2,"\n");        
273 }
274
275 void AliALIFE::OnionCone (Float_t* r1, Float_t* r2, Int_t nr, 
276                           Float_t zmin, Float_t zmax,
277                           Float_t pos[3], char** Materials, char** Fields,
278                           char** Cuts) 
279 {
280 // Concentric cones
281 //
282     char nameCin[6], nameCou[6], nameZin[6], nameZou[6];
283 //
284 // Bodies
285 // ^^^^^^
286     Float_t ri1, ri2, ro1, ro2, d;
287
288 // z-max
289     sprintf(nameZou, "Z%4.4d", fNBodies++);
290     fprintf(fFile1,"%5s XYP%10.3f\n",nameZou, zmax); 
291 // z-min
292     sprintf(nameZin, "Z%4.4d", fNBodies++);
293     fprintf(fFile1,"%5s XYP%10.3f\n",nameZin, zmin); 
294      
295 //  inner radius
296     d=zmax-zmin;
297     Bool_t hasInner=kFALSE;
298     Bool_t isCylinder=kFALSE;
299     if (r1[0]>=0 && r2[0]>=0) {
300         if (r1[0] != 0. &&  r2[0] !=0.) {
301             if (r1[0]!=r2[0]) {
302                 hasInner=kTRUE;
303                 if (r1[0] > r2[0]) {
304                     pos[2]=zmin;
305                     ri1=r1[0];
306                     ri2=r2[0];
307                 } else {
308                     d=-d;
309                     pos[2]=zmax;
310                     ri1=r2[0];
311                     ri2=r1[0];
312                 }
313                 sprintf(nameCin, "C%4.4d", fNBodies++);
314                 nameCin[5]='\0';
315                 fprintf(fFile1,"%5s TRC%10.3f%10.3f%10.3f%10.3f%10.3f%10.3f\n",
316                         nameCin, pos[0], pos[1], pos[2], 0., 0., d); 
317                 fprintf(fFile1,"         %10.3f%10.3f\n",ri1,ri2);
318             } else {
319                 isCylinder=kTRUE;
320                 sprintf(nameCin, "C%4.4d", fNBodies++);
321                 nameCin[5]='\0';
322                 fprintf(fFile1,"%5s ZCC%10.3f%10.3f%10.3f\n",
323                         nameCin, pos[0], pos[1], r1[0]); 
324             }
325         }
326     } else {
327       fDefaultVolume1 = nameCin;
328     }
329     
330     
331     
332 // outer radius
333     Int_t i;
334     for (i=1; i<nr; i++) {
335         if (r1[i] >= 0. && r2[i] >=0) {
336             if (r1[i]!=r2[i]) {
337                 d=zmax-zmin;
338                 if (r1[i] > r2[i]) {
339                     pos[2]=zmin;
340                     ro1=r1[i];
341                     ro2=r2[i];
342                 } else {
343                     pos[2]=zmax;
344                     ro1=r2[i];
345                     ro2=r1[i];
346                     d=-d;
347                 }
348                 sprintf(nameCou, "C%4.4d", fNBodies++);
349                 nameCou[5]='\0';
350                 fprintf(fFile1,"%5s TRC%10.3f%10.3f%10.3f%10.3f%10.3f%10.3f\n",
351                         nameCou, pos[0], pos[1], pos[2], 0., 0., d); 
352                 fprintf(fFile1,"         %10.3f%10.3f\n",ro1,ro2);
353             } else {
354                 isCylinder=kTRUE;
355                 sprintf(nameCou, "C%4.4d", fNBodies++);
356                 nameCou[5]='\0';
357                 fprintf(fFile1,"%5s ZCC%10.3f%10.3f%10.3f\n",
358                         nameCou, pos[0], pos[1], r1[i]); 
359             }
360         } else {
361           fDefaultVolume1 = nameCou;
362         }
363         
364 // Volumes
365 // ^^^^^^^
366         if (Fields && Cuts) {
367             fprintf(fFile2,">%s:%s\n", Materials[i-1], Fields[i-1]);
368             fprintf(fFile2,"EMFCUT=%s\n", Cuts[i-1]);
369             fprintf(fFile2,"WW-FACTOR=%s\n", Cuts[i-1]);
370         } else {
371             fprintf(fFile2,">%s:%s\n", Materials[i-1], "MF");
372             fprintf(fFile2,"EMFCUT=%s\n", "$UNSHIELDED");
373             fprintf(fFile2,"WW-FACTOR=%s\n", "$UNSHIELDED");
374         }
375         if (hasInner || isCylinder) {
376             if (!isCylinder) fprintf(fFile2,"+%5s-%5s+%5s-%5s\n", 
377                     nameCou, nameCin, nameZou, nameZin);
378             if (isCylinder)  fprintf(fFile2,"+%5s+%5s-%5s\n",
379                     nameCou, nameZou, nameZin); 
380         } else {
381             fprintf(fFile2,"+%5s\n", nameCou);
382             hasInner=kTRUE;
383         }
384         fprintf(fFile2,"\n");        
385         strcpy(nameCin,nameCou);
386     }
387 }
388
389
390 void AliALIFE::PolyCone(Float_t* rmin, Float_t* rmax, Float_t* z, 
391                         Int_t nz,
392                         Float_t pos[3], 
393                         char* Material, char* Field, char* Cuts) 
394 {
395 //
396 // Equivalent to the Geant3 PCON
397     Int_t i;
398     for (i=0; i<nz-1; i++) {
399 // skip (z_i = z_i+1)
400         if (z[i] == z[i+1]) continue;
401         Cone(rmin[i], rmin[i+1], rmax[i], rmax[i+1], z[i], z[i+1], pos,
402              Material, Field, Cuts);
403     }
404 }
405
406 void AliALIFE::OnionPolyCone(Float_t** r, Float_t* z,
407                              Int_t nr, Int_t nz,
408                              Float_t pos[3], 
409                              char** Materials, char** Fields, char** Cuts)
410 {
411 //
412 // Concentric PCONS
413     Int_t i, j;
414     for (i=0; i<nz-1; i++) {
415 // skip (z_i = z_i+1)
416         if (z[i] == z[i+1]) continue;
417         for (j=0; j<nr-1; j++) {
418             if (Fields && Cuts) {
419                 Cone(r[i][j], r[i+1][j], r[i][j+1], r[i+1][j+1], 
420                      z[i], z[i+1], pos,
421                      Materials[i], Fields[i], Cuts[i]);
422             } else {
423                 Cone(r[i][j], r[i+1][j], r[i][j+1], r[i+1][j+1], 
424                      z[i], z[i+1], pos,
425                      Materials[i]);
426             }
427         }
428     }
429 }
430
431 void AliALIFE::Comment(char* Comment)
432 {
433 // Insert comment line
434     fprintf(fFile1,"*%s\n", Comment);        
435     fprintf(fFile2,"*%s\n", Comment);        
436 }
437
438
439 void AliALIFE::Finish()
440 {
441 // Finish geometry definition
442     char s[BUFSIZ];
443     fprintf(fFile1,"      END\n");
444     fclose(fFile2);
445     fFile2=fopen(fVolumeFile,"r");
446     while (fgets(s, BUFSIZ, fFile2)) {
447         fputs(s,fFile1);
448     }
449     
450     fclose(fFile1);
451     fclose(fFile2);    
452 }
453
454
455
456
457
458
459
460
461
462
463