generate_gdml_test.pl
Go to the documentation of this file.
1 #!/usr/bin/perl
2 
3 # This program creates GDML sub-files, with values supplied by user
4 # parameters. Geometry/gdml/make_gdml.pl "zips" together those
5 # sub-files to make a single detector description.
6 
7 # Packages
8 use Math::Trig;
9 use XML::LibXML;
10 use Getopt::Long;
11 
12 # Get the input parameters from an XML file. Optionally append a
13 # suffix to the GDML sub-files we create.
14 
15 GetOptions( "input|i:s" => \$input,
16  "help|h" => \$help,
17  "suffix|s:s" => \$suffix,
18  "output|o:s" => \$output);
19 
20 if ( defined $help )
21 {
22  # If the user requested help, print the usage notes and exit.
23  usage();
24  exit;
25 }
26 
27 if ( ! defined $suffix )
28 {
29  # The user didn't supply a suffix, so append nothing to the file
30  # names.
31  $suffix = "";
32 }
33 else
34 {
35  # Otherwise, stick a "-" before the suffix, so that a suffix of
36  # "test" applied to filename.gdml becomes "filename-test.gdml".
37  $suffix = "-" . $suffix;
38 }
39 
40 # Create an XML parser.
41 $parser = new XML::LibXML;
42 
43 # Read in the parameters from an XML file. The following command
44 # slurps the entire file into a DOM data structure.
45 $xmldata = $parser->parse_file($input);
46 
47 # Go through each parameter in the DOM data structure:
48 foreach $parameter ( $xmldata->findnodes('/parameters/geometry/parameter') )
49 {
50  # Get the name and value attributes for that parameter:
51  $name = $parameter->getAttribute("name");
52  $value = $parameter->getAttribute("value");
53 
54  # Here's the clever part: The following eval creates a variable
55  # with the same name as $name. For example, if $name eq "TPCDepth",
56  # then the following statement assigns the value to $TPCDepth. The
57  # value is in quotes, because some of the parameters have text
58  # strings in them (like "kInch").
59 
60  eval "\$$name = '$value'";
61 }
62 
63 # Our calculations and constants depend on the geometry of the wires.
64 $SinUVAngle = sin( deg2rad($UVAngle) );
65 $CosUVAngle = cos( deg2rad($UVAngle) );
66 $TanUVAngle = tan( deg2rad($UVAngle) );
67 
68 # The routines that create the GDML sub-files. Most of the explanatory
69 # comments are in gen_defs().
70 $wires_on=1; # turn wires on=1 or off=0
71 $wire_int=20;
72 $NumberOfTPCPlanes=3;
73 $tpc_neg_length=1000;
74 $tpc_neg_width=200;
75 $tpc_neg_height=200;
76 $wire_frame_width=9.5;
77 $wire_plane_height=240;
78 $wire_plane_length=1042;
79 $wires_plength=($wire_plane_length - 2*$wire_frame_width) ;
80 $wires_pwidth=($wire_plane_height - 2*$wire_frame_width) ;
81 $field_cage_width = 200;
82 $field_cage_height = 180;
83 $field_cage_cross_length = sqrt(($field_cage_width)**2+($field_cage_height-50)**2);
84 $field_cage_length = 1000;
85 $field_cage_loop_interval = 1; # =1 is normal, =4 skips 3/4
86 $spacers_on_off = "off"; # "on" or "off" for tube spacers (off saves time)
87 $electronics_height=12;
88 $pmt_switch="off"; #turn on or off depending on pmts wanted
89 
90 
91 gen_defs();
92 gen_rotations();
93 gen_materials();
94 
95 gen_microplane();
96 gen_microvertplane();
97 #gen_tpcplanevert();
98 #gen_tpcplane();
99 
100  gen_groundplate(); # physical volumes defined in gen_tpc()
101  gen_cathode(); # physical volumes defined in gen_tpc()
102  gen_fieldcage(); # physical volumes defined in gen_tpc()
103 gen_tpc();
104 
105 if ( $pmt_switch eq "on" ) { gen_pmt(); } # physical volumes defined in gen_cryostat()
106 gen_cryostat();
107 
108 gen_enclosure();
109 gen_world();
110 write_fragments();
111 
112 exit;
113 
114 
115 
116 sub usage()
117 {
118  print "Usage: $0 [-h|--help] -i|--input <parameters-file> [-o|--output <fragments-file>] [-s|--suffix <string>]\n";
119  print " -i/--input can be omitted; <parameters-file> contains geometry and material parameters\n";
120  print " if -o is omitted, output goes to STDOUT; <fragments-file> is input to make_gdml.pl\n";
121  print " -s <string> appends the string to the file names; useful for multiple detector versions\n";
122  print " -h prints this message, then quits\n";
123 }
124 
125 
126 
127 # Create the detector constant file. This file is actually temporary,
128 # since the make_gdml.pl program will interpret its contents rather
129 # than include it in the final GDML file.
130 
131 sub gen_defs()
132 {
133  # Set up the output file.
134  $CONSTANTS = "microboone/micro-defs" . $suffix . ".gdml";
135  push (@gdmlFiles, $CONSTANTS); # Add file to list of constant files
136  $CONSTANTS = ">" . $CONSTANTS;
137  open(CONSTANTS) or die("Could not open file $CONSTANTS for writing");
138 
139  # Create some math constants.
140  my $pi = pi;
141 
142  # Though it's not strictly necessary, make each sub-file a valid
143  # XML (if not GDML) document; that makes it accessible to an XML
144  # parser if needed.
145 
146  # Here is a neat way to print out a block of text without getting
147  # involved in a lot of messy quoting and formatting with print
148  # statements.
149 
150  print CONSTANTS <<EOF;
151 <?xml version='1.0'?>
152 <define>
153 <constant name="kInch" value="2.54" />
154 <constant name="kPi" value="$pi" />
155 <constant name="kDetEnclosureWidth" value="$DetEnclosureWidth" />
156 <constant name="kDetEnclosureHeight" value="$DetEnclosureHeight" />
157 <constant name="kDetEnclosureLength" value="$DetEnclosureLength" />
158 <constant name="kDirtThickness" value="$DirtThickness" />
159 <constant name="kWorldW" value="100.0*kDetEnclosureWidth"/>
160 <constant name="kWorldH" value="100.0*kDetEnclosureHeight"/>
161 <constant name="kWorldL" value="100.0*kDetEnclosureLength"/>
162 
163 <constant name="kTPCWidth" value="$TPCWidth" />
164 <constant name="kTPCLength" value="$TPCLength" />
165 <constant name="kTPCDepth" value="$TPCDepth" />
166 <constant name="kTPCWallThickness" value="$TPCWallThickness" />
167 
168 <constant name="kTPCWirePlaneThickness" value="$TPCWirePlaneThickness" />
169 <constant name="kTPCWireThickness" value="$TPCWireThickness" />
170 <constant name="kTPCWirePlaneWidth" value="kTPCWidth" />
171 <constant name="kTPCWirePlaneLength" value="kTPCLength" />
172 <constant name="kWireFrameDepth" value="9" />
173 <constant name="kWireFrameWidth" value="$wire_frame_width" />
174 <constant name="kWirePlaneHeight" value="$wire_plane_height" />
175 <constant name="kWirePlaneLength" value="$wire_plane_length" />
176 <constant name="kWireFrameVInHeight" value="0.5*(kWirePlaneHeight-3*kWireFrameWidth)" />
177 
178 <constant name="kTPCWirePitch" value="$TPCWirePitch"/>
179 <constant name="kSinUVAngle" value="$SinUVAngle"/>
180 <constant name="kCosUVAngle" value="$CosUVAngle"/>
181 <constant name="kTanUVAngle" value="$TanUVAngle"/>
182 <constant name="kTPCWireXPitch" value="kTPCWirePitch/kCosUVAngle"/>
183 
184 <constant name="kCathodeFrameWidth" value="9" />
185 <constant name="kCathodeFrameDepth" value="5" />
186 <constant name="kCathodePlateDepth" value="0.1" />
187 <constant name="kCathodeWidth" value="5.1" />
188 <constant name="kCathodeHeight" value="240" />
189 <constant name="kCathodeLength" value="1042" />
190 <constant name="kCathodeFrameVInHeight" value="0.5*(kCathodeHeight-3*kCathodeFrameWidth)" />
191 
192 <constant name="kGroundPlateWidth" value="224" />
193 <constant name="kGroundPlateHeight" value="0.1" />
194 <constant name="kGroundPlateLength" value="1100" />
195 <constant name="kGroundBeamWidth" value="2.5" />
196 <constant name="kGroundBeamHeight" value="2.5" />
197 <constant name="kGroundBeamLength" value="kGroundPlateLength" />
198 <constant name="kGroundBeamThickness" value=".15" />
199 </define>
200 EOF
201 
202  close(CONSTANTS);
203 }
204 
205 
206 sub gen_rotations()
207 {
208  my $WirePlusRotation = $UVAngle + 90;
209  my $WireMinusRotation = $UVAngle - 90;
210 
211  $ROTATIONS = "microboone/micro-rotations" . $suffix . ".gdml";
212  push (@gdmlFiles, $ROTATIONS); # Add file to list of GDML fragments
213  $ROTATIONS = ">" . $ROTATIONS;
214  open(ROTATIONS) or die("Could not open file $ROTATIONS for writing");
215 
216  print ROTATIONS <<EOF;
217 <?xml version='1.0'?>
218 <define>
219  <rotation name="rPlus30AboutX" unit="deg" x="30" y="0" z="0"/>
220  <rotation name="rPlus60AboutX" unit="deg" x="60" y="0" z="0"/>
221  <rotation name="rPlus90AboutX" unit="deg" x="90" y="0" z="0"/>
222  <rotation name="rMinus90AboutX" unit="deg" x="-90" y="0" z="0"/>
223  <rotation name="rPlusUVAngleAboutX" unit="deg" x="150" y="0" z="0"/>
224  <rotation name="rPlus150AboutX" unit="deg" x="150" y="0" z="0"/>
225  <rotation name="rPlus180AboutX" unit="deg" x="180" y="0" z="0"/>
226  <rotation name="rMinusUVAngleAboutX" unit="deg" x="-30" y="0" z="0"/>
227  <rotation name="rPlus30AboutY" unit="deg" x="0" y="30" z="0"/>
228  <rotation name="rPlus60AboutY" unit="deg" x="0" y="60" z="0"/>
229  <rotation name="rPlus90AboutY" unit="deg" x="0" y="90" z="0"/>
230  <rotation name="rPlus180AboutY" unit="deg" x="0" y="180" z="0"/>
231  <rotation name="rMinus90AboutY" unit="deg" x="0" y="-90" z="0"/>
232  <rotation name="rPlus90AboutZ" unit="deg" x="0" y="0" z="90"/>
233  <rotation name="rMinus90AboutZ" unit="deg" x="0" y="0" z="-90"/>
234  <rotation name="rPlus180AboutZ" unit="deg" x="0" y="0" z="180"/>
235  <rotation name="rMinus180AboutZ" unit="deg" x="0" y="0" z="-180"/>
236  <rotation name="rMinus90AboutYPlus180AboutZ" unit="deg" x="0" y="-90" z="180"/>
237  <rotation name="rMinus90AboutYMinus90AboutZ" unit="deg" x="0" y="-90" z="-90"/>
238  <rotation name="rPlus90AboutYPlus180AboutZ" unit="deg" x="0" y="90" z="180"/>
239  <rotation name="rMinus90AboutYPlus90AboutZ" unit="deg" x="0" y="-90" z="90"/>
240  <rotation name="rPlus90AboutYMinus90AboutZ" unit="deg" x="0" y="90" z="-90"/>
241  <rotation name="rPlus90AboutXPlus90AboutZ" unit="deg" x="90" y="0" z="90"/>
242  <rotation name="rPlus90AboutXPlus180AboutZ" unit="deg" x="90" y="0" z="180"/>
243  <rotation name="rPlus90AboutXMinus90AboutY" unit="deg" x="90" y="-90" z="0"/>
244  <rotation name="rPlus90AboutXMinus90AboutZ" unit="deg" x="90" y="0" z="-90"/>
245  <rotation name="rPlus90AboutXPlus90AboutY" unit="deg" x="90" y="90" z="0"/>
246  <rotation name="rPMTRotation1" unit="deg" x="90" y="270" z="0"/>
247 </define>
248 EOF
249  close (ROTATIONS);
250 }
251 
252 
253 sub gen_materials()
254 {
255  # Create the materials file name and open it.
256  $MATERIALS = "materials" . $suffix . ".gdml";
257  push (@gdmlFiles, $MATERIALS); # Add file to list of GDML fragments
258  $MATERIALS = ">" . $MATERIALS;
259  open(MATERIALS) or die("Could not open file $MATERIALS for writing");
260 
261  # Write the standard XML prefix.
262  print MATERIALS <<EOF;
263 <?xml version='1.0'?>
264 EOF
265 
266  # Go back the DOM structure read in near the beginning of the
267  # program. For each <materials /> element (and there'll probably
268  # be only one):
269  foreach $materials ( $xmldata->findnodes('/parameters/materials') )
270  {
271  # Convert that element back to text, and write it out.
272  print MATERIALS $materials->toString;
273  }
274 
275  close (MATERIALS);
276 }
277 
278 
279 # This is a re-write of Brian Rebel's gen_microvertplane.C into
280 # Perl. It contructs the TPC wire plane for the Y view.
281 
282 sub gen_microvertplane()
283 {
284  my $NumberWires = int( $TPCLength / $TPCWirePitch ) - 1;
285 
286  $GDML = "micro-vertplane" . $suffix . ".gdml";
287  push (@gdmlFiles, $GDML); # Add file to list of GDML fragments
288  $GDML = ">" . $GDML;
289  open(GDML) or die("Could not open file $GDML for writing");
290 
291  # Define the solids and structures: the wires and the TPC wire plane.
292  print GDML <<EOF;
293 <?xml version='1.0'?>
294 <gdml>
295 <solids>
296 <tube name="TPCWireVert"
297  rmax="0.5*kTPCWireThickness"
298  z="kTPCWidth"
299  deltaphi="2*kPi"
300  aunit="rad"
301  lunit="cm"/>
302 <box name="TPCPlaneVert"
303  x="kTPCWirePlaneThickness"
304  y="kTPCWidth+1"
305  z="kTPCLength+1"
306  lunit="cm"/>
307 </solids>
308 <structure>
309  <volume name="volTPCWireVert">
310  <materialref ref="Titanium"/>
311  <solidref ref="TPCWireVert"/>
312  </volume>
313  <volume name="volTPCPlaneVert">
314  <materialref ref="LAr"/>
315  <solidref ref="TPCPlaneVert"/>
316 EOF
317 
318  # the wires
319  for ( $i = 0; $i < $NumberWires; ++$i)
320  {
321  print GDML <<EOF;
322  <physvol>
323  <volumeref ref="volTPCWireVert"/>
324  <position name="posTPCWireVert$i" unit="cm" z="(-0.5*kTPCLength)+(($i+1)*kTPCWirePitch)" x="0" y="0"/>
325  <rotationref ref="rPlus90AboutX"/>
326  </physvol>
327 EOF
328  }
329 
330  print GDML <<EOF;
331  </volume>
332 </structure>
333 </gdml>
334 EOF
335 
336  close(GDML);
337 }
338 
339 
340 # This is a re-write of Brian Rebel's gen_microplane.C into Perl. It
341 # constructs the TPC wire plane for the U or V view.
342 
343 sub gen_microplane()
344 {
345 
346 
347  $GDML = "micro-plane" . $suffix . ".gdml";
348  push (@gdmlFiles, $GDML); # Add file to list of GDML fragments
349  $GDML = ">" . $GDML;
350  open(GDML) or die("Could not open file $GDML for writing");
351 
352  # Calculate the number of wire ends on a given y-edge of the plane.
353  my $TPCYWirePitch = $TPCWirePitch / $CosUVAngle;
354  my $NumberWiresPerEdge = int( $TPCLength / $TPCYWirePitch );
355 
356  # How many side wires will be "cut off" by the lower or higher
357  # z-edge?
358  my $NumberSideWires = int( $TanUVAngle * $TPCWidth / $TPCYWirePitch );
359 
360  # The number of full-length "center" wires.
361  my $NumberCenterWires = $NumberWiresPerEdge - $NumberSideWires;
362 
363  # define the solids
364  print GDML <<EOF;
365 <?xml version='1.0'?>
366 <gdml>
367 <solids>
368 EOF
369 
370  # wires on either end of the tpc
371  for($i = 0; $i < $NumberSideWires; ++$i)
372  {
373  print GDML <<EOF;
374 <tube name="TPCWire$i"
375  rmax="0.5*kTPCWireThickness"
376  z="kTPCWireXPitch*($i+1)/kSinUVAngle"
377  deltaphi="2*kPi"
378  aunit="rad"
379  lunit="cm"/>
380 EOF
381  }
382 
383  # The solids for the middle wire and the TPC wire plane, and start off the structures.
384  print GDML <<EOF;
385 <tube name="TPCWireCommon"
386  rmax="0.5*kTPCWireThickness"
387  z="kTPCWidth/kCosUVAngle"
388  deltaphi="2*kPi"
389  aunit="rad"
390  lunit="cm"/>
391 <box name="TPCPlane"
392  x="kTPCWirePlaneThickness"
393  y="kTPCWidth+1"
394  z="kTPCLength+1"
395  lunit="cm"/>
396 </solids>
397 <structure>
398 EOF
399 
400  # the wires at either end of the plane
401  for ($i = 0; $i < $NumberSideWires; ++$i)
402  {
403  print GDML <<EOF;
404  <volume name="volTPCWire$i">
405  <materialref ref="Titanium"/>
406  <solidref ref="TPCWire$i"/>
407  </volume>
408 EOF
409  }
410 
411 
412  # The wires in the middle of the plane, and the plane itself.
413  print GDML <<EOF;
414  <volume name="volTPCWireCommon">
415  <materialref ref="Titanium"/>
416  <solidref ref="TPCWireCommon"/>
417  </volume>
418  <volume name="volTPCPlane">
419  <materialref ref="LAr"/>
420  <solidref ref="TPCPlane"/>
421 EOF
422 
423  # the wires at the -z end
424  for ($i = 0; $i < $NumberSideWires; ++$i)
425  {
426  print GDML <<EOF;
427  <physvol>
428  <volumeref ref="volTPCWire$i"/>
429  <position name="posTPCWire$i" unit="cm" y="-0.5*kTPCWidth+0.5*($i+1)*kTPCWireXPitch/kTanUVAngle" z="0.5*(-kTPCLength+($i+1)*kTPCWireXPitch)" x="0"/>
430  <rotationref ref="rPlusUVAngleAboutX"/>
431  </physvol>
432 EOF
433  }
434 
435  # The wires in the middle.
436  for ($i = 0; $i < $NumberCenterWires; ++$i)
437  {
438  my $j = $NumberSideWires+$i;
439  print GDML <<EOF;
440  <physvol>
441  <volumeref ref="volTPCWireCommon"/>
442  <position name="posTPCWire$j" unit="cm" y="0" z="-0.5*kTPCWirePlaneLength+kTPCWireXPitch*(0.5*$NumberSideWires + $i+1)" x="0"/>
443  <rotationref ref="rPlusUVAngleAboutX"/>
444  </physvol>
445 EOF
446  }
447 
448  # the wires at the +z end
449  for ($i = 0; $i < $NumberSideWires; ++$i)
450  {
451  my $j = $NumberSideWires-$i-1;
452  my $k = $NumberCenterWires+$NumberSideWires+$i;
453 
454  print GDML <<EOF;
455  <physvol>
456  <volumeref ref="volTPCWire$j"/>
457  <position name="posTPCWire$k" unit="cm" y="0.5*kTPCWidth-0.5*($j+1)*kTPCWireXPitch/kTanUVAngle" z="0.5*kTPCWirePlaneLength-0.5*kTPCWireXPitch*($j+1)" x="0"/>
458  <rotationref ref="rPlusUVAngleAboutX"/>
459  </physvol>
460 EOF
461  }
462 
463  print GDML <<EOF;
464  </volume>
465 </structure>
466 </gdml>
467 EOF
468 
469  close(GDML);
470 }
471 
472 
473 # This is a re-write of Brian Rebel's gen_microvertplane.C into
474 # Perl. It contructs the TPC wire plane for the Y view.
475 
476 sub gen_tpcplanevert_bad()
477 {
478 
479 
480 ##### temporary edits:
481 ##### - TPCPlaneVert y="TPCWidth" z="kTPCLength"
482 ##### - TPCWireVert y="TPCWidth"
483 ##### - (above)my $NumberWires = int($TPCLength / $TPCWirePitch ) - 1
484 
485 
486 
487  my $NumberWires = int( ( $wires_plength ) / $TPCWirePitch ) - 1;
488 
489  $GDML = "microboone/micro-vertplane" . $suffix . ".gdml";
490  push (@gdmlFiles, $GDML); # Add file to list of GDML fragments
491  $GDML = ">" . $GDML;
492  open(GDML) or die("Could not open file $GDML for writing");
493 
494  # Define the solids and structures: the wires and the TPC wire plane.
495 
496  print GDML <<EOF;
497 <?xml version='1.0'?>
498 <gdml>
499 <solids>
500 <tube name="TPCWireVert"
501  rmax="0.5*kTPCWireThickness"
502  z="$wires_pwidth"
503  deltaphi="2*kPi"
504  aunit="rad"
505  lunit="cm"/>
506 <box name="TPCPlaneVert"
507  x="kTPCWirePlaneThickness"
508  y="$wires_pwidth"
509  z="$wires_plength"
510  lunit="cm"/>
511 </solids>
512 <structure>
513  <volume name="volTPCWireVert">
514  <materialref ref="Titanium"/>
515  <solidref ref="TPCWireVert"/>
516  </volume>
517  <volume name="volTPCPlaneVert">
518  <materialref ref="LAr"/>
519  <solidref ref="TPCPlaneVert"/>
520 EOF
521 
522  # the wires
523  for ( $i = 0; $i < ( $NumberWires / $wire_int ); ++$i )
524  {
525  $j=($wire_int*$i);
526  print GDML <<EOF;
527  <physvol>
528  <volumeref ref="volTPCWireVert"/>
529  <position name="posTPCWireVert$i" unit="cm" z="(-0.5*kTPCWirePlaneLength)+kTPCWirePitch*($j+1)" x="0" y="0"/>
530  <rotationref ref="rPlus90AboutX"/>
531  </physvol>
532 EOF
533  }
534 
535  print GDML <<EOF;
536  </volume>
537 </structure>
538 </gdml>
539 EOF
540 
541  close(GDML);
542 }
543 
544 # This is a re-write of Brian Rebel's gen_microplane.C into Perl. It
545 # constructs the TPC wire plane for the U or V view.
546 
547 sub gen_tpcplane_bad()
548 {
549 
550  my $NumberWires = $TPCLength / $TPCWirePitch - 1;
551 
552  $GDML = "microboone/micro-plane" . $suffix . ".gdml";
553  push (@gdmlFiles, $GDML); # Add file to list of GDML fragments
554  $GDML = ">" . $GDML;
555  open(GDML) or die("Could not open file $GDML for writing");
556 
557  # Calculate the number of wire ends on a given y-edge of the plane.
558  my $TPCYWirePitch = $TPCWirePitch / $CosUVAngle;
559  my $NumberWiresPerEdge = int( $TPCLength / $TPCYWirePitch );
560  #my $NumberWiresPerEdge = int( ( $wires_plength ) / $TPCYWirePitch );
561 
562  # How many side wires will be "cut off" by the lower or higher
563  # z-edge?
564  #my $NumberSideWires = int( $TanUVAngle * ( $wires_pwidth ) / $TPCYWirePitch );
565  my $NumberSideWires = int( $TanUVAngle * $TPCWidth / $TPCYWirePitch ) - 1;
566 
567 
568  # The number of full-length "center" wires.
569  my $NumberCenterWires = $NumberWiresPerEdge - $NumberSideWires;
570 
571  # define the solids
572  print GDML <<EOF;
573 <?xml version='1.0'?>
574 <gdml>
575 <solids>
576 EOF
577 
578  # wires on either end of the tpc
579  for ($i = 0; $i < $NumberSideWires; ++$i)
580  {
581  print GDML <<EOF;
582 <tube name="TPCWire$i"
583  rmax="0.5*kTPCWireThickness"
584  z="kTPCWireXPitch*($i+1)/kSinUVAngle"
585  deltaphi="2*kPi"
586  aunit="rad"
587  lunit="cm"/>
588 EOF
589  }
590 
591  # The solids for the middle wire and the TPC wire plane, and start off the structures.
592  print GDML <<EOF;
593 <tube name="TPCWireCommon"
594  rmax="0.5*kTPCWireThickness"
595  z="kTPCWidth/kCosUVAngle"
596  deltaphi="2*kPi"
597  aunit="rad"
598  lunit="cm"/>
599 <box name="TPCPlane"
600  x="kTPCWirePlaneThickness"
601  y="kTPCWidth"
602  z="kTPCLength"
603  lunit="cm"/>
604 </solids>
605 <structure>
606 EOF
607 
608  # the wires at either end of the plane
609  for ($i = 0; $i < $NumberSideWires; ++$i)
610  {
611  print GDML <<EOF;
612  <volume name="volTPCWire$i">
613  <materialref ref="Titanium"/>
614  <solidref ref="TPCWire$i"/>
615  </volume>
616 EOF
617  }
618 
619 
620  # The wires in the middle of the plane, and the plane itself.
621  print GDML <<EOF;
622  <volume name="volTPCWireCommon">
623  <materialref ref="Titanium"/>
624  <solidref ref="TPCWireCommon"/>
625  </volume>
626  <volume name="volTPCPlane">
627  <materialref ref="LAr"/>
628  <solidref ref="TPCPlane"/>
629 EOF
630 
631  # the wires at the -z end
632  for ($i = 0; $i < $NumberSideWires; ++$i)
633  {
634  print GDML <<EOF;
635  <physvol>
636  <volumeref ref="volTPCWire$i"/>
637  <position name="posTPCWire$i" unit="cm" y="(-0.5*kTPCWirePlaneWidth)+0.5*($i+1)*kTPCWireXPitch/kTanUVAngle" z="-0.5*kTPCWirePlaneLength+0.5*kTPCWireXPitch*($i+1)" x="0"/>
638  <rotationref ref="rPlusUVAngleAboutX"/>
639  </physvol>
640 EOF
641  }
642 
643  # The wires in the middle.
644  for ($i = 0; $i < $NumberCenterWires - 1 ; ++$i)
645  {
646  my $j = $NumberSideWires+$i;
647  print GDML <<EOF;
648  <physvol>
649  <volumeref ref="volTPCWireCommon"/>
650  <position name="posTPCWire$j" unit="cm" y="0" z="(-0.5*kTPCWirePlaneLength)+kTPCWireXPitch*(0.5*$NumberSideWires + $i+1)" x="0"/>
651  <rotationref ref="rPlusUVAngleAboutX"/>
652  </physvol>
653 EOF
654  }
655 
656  # the wires at the +z end
657  for ($i = 0; $i < $NumberSideWires ; ++$i)
658  {
659  my $j = $NumberSideWires-$i-1;
660  my $k = $NumberCenterWires+$NumberSideWires+$i;
661 
662  print GDML <<EOF;
663  <physvol>
664  <volumeref ref="volTPCWire$j"/>
665  <position name="posTPCWire$k" unit="cm" y="0.5*kTPCWirePlaneWidth-0.5*($j+1)*kTPCWireXPitch/kTanUVAngle" z="0.5*kTPCWirePlaneLength-0.5*kTPCWireXPitch*($j+1)" x="0"/>
666  <rotationref ref="rPlusUVAngleAboutX"/>
667  </physvol>
668 EOF
669  }
670 
671  print GDML <<EOF;
672  </volume>
673 </structure>
674 </gdml>
675 EOF
676 
677  close(GDML);
678 }
679 
680 
681 #
682 # subdirectory to write field cage
683 sub gen_fieldcage() {
684 
685  # Set up the output file.
686  $FIELDCAGE = "microboone/micro-fieldcage.gdml";
687  push (@gdmlFiles, $FIELDCAGE); # Add file to list of constant files
688  $FIELDCAGE = ">" . $FIELDCAGE;
689  open(FIELDCAGE) or die("Could not open file $FIELDCAGE for writing");
690 
691  # Print the Field Cage constants
692  print FIELDCAGE <<EOF;
693 <define>
694  <constant name="kFieldCageTPCClearance" value="5*kInch" />
695 
696  <constant name="kFieldCageTubeRadius" value="0.5*kInch" />
697  <constant name="kFieldCageTubeThickness" value="0.25*kInch" />
698  <constant name="kFieldCageBeamDepth" value="12.5"/>
699  <constant name="kFieldCageBeamWidth" value="2.5"/>
700  <constant name="kFieldCageCrossDepth" value="2.5"/>
701  <constant name="kFieldCageCrossWidth" value="4"/>
702  <constant name="kFieldCageCrossLength" value="$field_cage_cross_length"/>
703 
704  <constant name="kTPCTotalLength" value="$field_cage_length"/>
705  <constant name="kTPCTotalWidth" value="$field_cage_width"/>
706  <constant name="kTPCTotalHeight" value="$field_cage_height"/>
707 
708  <constant name="kFieldCageLoopLength" value="kTPCTotalLength+2*(kFieldCageTPCClearance+2*kFieldCageTubeRadius)"/>
709  <constant name="kFieldCageLoopWidth" value="$field_cage_width"/>
710  <constant name="kFieldCageLoopHeight" value="kTPCTotalHeight+2*(kFieldCageTPCClearance+2*kFieldCageTubeRadius)"/>
711 
712  <constant name="kFieldCageCornerRadius" value="0.5*kFieldCageTPCClearance"/>
713  <constant name="kFieldCageCornerY" value="(0.5*kFieldCageLoopHeight)-kFieldCageCornerRadius-kFieldCageTubeRadius"/>
714  <constant name="kFieldCageCornerZ" value="(0.5*kFieldCageLoopLength)-kFieldCageCornerRadius-kFieldCageTubeRadius"/>
715 
716  <constant name="kFieldCageHeight" value="kFieldCageLoopHeight+2*(kFieldCageBeamDepth+kFieldCageCrossDepth)"/>
717  <constant name="kFieldCageLength" value="kFieldCageLoopLength+2*(kFieldCageBeamDepth+kFieldCageCrossDepth)"/>
718  <constant name="kFieldCageWidth" value="$field_cage_width"/>
719 
720  <constant name="kFieldCageBeamYInt" value="0.5*(kFieldCageLoopHeight-50)"/>
721  <constant name="kFieldCageBeamZPos" value="0.5*(kFieldCageLoopLength)"/>
722  <constant name="kFieldCageBeamYPos" value="0.5*(kFieldCageLoopHeight)"/>
723  <constant name="kFieldCageBeamZInt" value="0.5*(kFieldCageLoopLength-40)"/>
724 
725  <constant name="kFieldCageCrossYPos" value="0.5*(kFieldCageLoopHeight+kFieldCageCrossDepth)+kFieldCageBeamDepth"/>
726  <constant name="kFieldCageCrossZPos" value="0.5*(kFieldCageLoopLength+kFieldCageCrossDepth)+kFieldCageBeamDepth"/>
727 </define>
728 EOF
729 
730  # Prints Field Cage solids
731  print FIELDCAGE <<EOF;
732 <solids>
733  <tube name="FieldCageTubeZ"
734  rmin="kFieldCageTubeRadius - kFieldCageTubeThickness"
735  rmax="kFieldCageTubeRadius"
736  z="kFieldCageLoopLength-2*(kFieldCageCornerRadius+kFieldCageTubeRadius)"
737  deltaphi="2*kPi"
738  aunit="rad"
739  lunit="cm"/>
740  <tube name="FieldCageTubeY"
741  rmin="kFieldCageTubeRadius - kFieldCageTubeThickness"
742  rmax="kFieldCageTubeRadius"
743  z="kFieldCageLoopHeight-2*(kFieldCageCornerRadius+kFieldCageTubeRadius)"
744  deltaphi="2*kPi"
745  aunit="rad"
746  lunit="cm"/>
747 </solids>
748 EOF
749 
750  # Prints Field Cage tube loop sub-structure
751  print FIELDCAGE <<EOF;
752 <structure>
753  <volume name="volFieldCageTubeTop">
754  <materialref ref="STEEL_STAINLESS_Fe7Cr2Ni"/>
755  <solidref ref="FieldCageTubeZ"/>
756  </volume>
757  <volume name="volFieldCageTubeBot">
758  <materialref ref="STEEL_STAINLESS_Fe7Cr2Ni"/>
759  <solidref ref="FieldCageTubeZ"/>
760  </volume>
761  <volume name="volFieldCageTubeFront">
762  <materialref ref="STEEL_STAINLESS_Fe7Cr2Ni"/>
763  <solidref ref="FieldCageTubeY"/>
764  </volume>
765  <volume name="volFieldCageTubeBack">
766  <materialref ref="STEEL_STAINLESS_Fe7Cr2Ni"/>
767  <solidref ref="FieldCageTubeY"/>
768  </volume>
769 </structure>
770 EOF
771 
772 close(FIELDCAGE);
773 
774 }
775 
776 
777 # Cathode solids and volumes
778 sub gen_cathode() {
779 
780  $CATHODE = "microboone/micro-cathode" . $suffix . ".gdml";
781  push (@gdmlFiles, $CATHODE); # Add file to list of GDML fragments
782  $CATHODE = ">" . $CATHODE;
783  open(CATHODE) or die("Could not open file $CATHODE for writing");
784 
785  print CATHODE <<EOF;
786 
787 <?xml version='1.0'?>
788 <gdml>
789 <solids>
790  <box name="CathodePlate"
791  lunit="cm"
792  x="kCathodePlateDepth"
793  y="kCathodeHeight"
794  z="kCathodeLength"/>
795 </solids>
796 <structure>
797  <volume name="volCathodePlate">
798  <materialref ref="STEEL_STAINLESS_Fe7Cr2Ni"/>
799  <solidref ref="CathodePlate"/>
800  </volume>
801 </structure>
802 </gdml>
803 EOF
804 
805 }
806 
807 sub gen_groundplate() {
808 #this subroutine will produce the gdml fragment for ground plate
809 
810  $GROUNDPLATE = "microboone/micro-groundplate" . $suffix . ".gdml";
811  push (@gdmlFiles, $GROUNDPLATE); # Add file to list of GDML fragments
812  $GROUNDPLATE = ">" . $GROUNDPLATE;
813  open(GROUNDPLATE) or die("Could not open file $GROUNDPLATE for writing");
814 
815  print GROUNDPLATE <<EOF;
816 <?xml version='1.0'?>
817 <gdml>
818 <solids>
819  <box name="GroundPlate"
820  lunit="cm"
821  x="kGroundPlateWidth"
822  y="kGroundPlateHeight"
823  z="kGroundPlateLength"/>
824 </solids>
825 <structure>
826  <volume name="volGroundPlate">
827  <materialref ref="STEEL_STAINLESS_Fe7Cr2Ni"/>
828  <solidref ref="GroundPlate"/>
829  </volume>
830 </structure>
831 </gdml>
832 EOF
833 
834  close(GROUNDPLATE);
835 }
836 
837 
838 # Parameterize the TPC and the planes within it.
839 sub gen_tpc()
840 {
841  # Set up the output file.
842  $GDML = "microboone/micro-tpc" . $suffix . ".gdml";
843  push (@gdmlFiles, $GDML); # Add file to list of GDML fragments
844  $GDML = ">" . $GDML;
845  open(GDML) or die("Could not open file $GDML for writing");
846 
847  print GDML <<EOF;
848 <?xml version='1.0'?>
849 <gdml>
850 <solids>
851  <box name="TPC"
852  lunit="cm"
853  x="kTPCDepth+kTPCWallThickness+(2*kTPCWirePlaneThickness)"
854  y="kTPCWidth+(2*kTPCWallThickness)+($electronics_height)"
855  z="kTPCLength+(2*kTPCWallThickness)"/>
856 </solids>
857 <structure>
858  <volume name="volTPC">
859  <materialref ref="LAr"/>
860  <solidref ref="TPC"/>
861 EOF
862 
863  # Ground Plane physical volumes
864  # Center = (9,124,0)
865  $ground_plate_X=9;
866  $ground_plate_Y=124;
867  $ground_plate_Z=0;
868 
869  print GDML <<EOF;
870  <physvol>
871  <volumeref ref="volGroundPlate"/>
872  <position name="posGroundPlate" unit="cm" x="$ground_plate_X+0.25" y="$ground_plate_Y-0.5*(kGroundBeamHeight)" z="0"/>
873  </physvol>
874 EOF
875 
876 
877  # Cathode Plane physical volumes
878  # Center = (0.5*(kTPCWidth-kCathodeWidth),0,0)
879  $Cathode_X="0.5*(kTPCWidth-kCathodeWidth)";
880  $Cathode_plate_offset="0.5*kCathodePlateDepth";
881  $Cathode_frame_position="$Cathode_X+($Cathode_plate_offset)";
882 
883  print GDML <<EOF;
884  <physvol>
885  <volumeref ref="volCathodePlate"/>
886  <position name="posCathodePlate" unit="cm" x="$Cathode_X-0.5*(kCathodeFrameDepth)-0.1" y="0" z="0"/>
887  </physvol>
888 EOF
889 
890 
891  # Wire Plane physical volumes
892  # Center = ( -0.5*(kTPCWidth-kWireFrameWidth) , 0 , 0 )
893  print GDML <<EOF;
894  <physvol>
895  <volumeref ref="volTPCPlaneVert"/>
896  <position name="posTPCPlaneVert" unit="cm" x="-0.5*(kTPCWidth-kWireFrameWidth)-(2*$TPCWirePlaneSpacing)" y="0" z="0"/>
897  </physvol>
898  <physvol>
899  <volumeref ref="volTPCPlane"/>
900  <position name="posTPCPlane" unit="cm" x="-0.5*(kTPCWidth-kWireFrameWidth)-$TPCWirePlaneSpacing" y="0" z="0"/>
901  </physvol>
902  <physvol>
903  <volumeref ref="volTPCPlane"/>
904  <position name="posTPCPlane2" unit="cm" x="-0.5*(kTPCWidth-kWireFrameWidth)" y="0" z="0"/>
905  <rotationref ref="rPlus180AboutY"/>
906  </physvol>
907 EOF
908 
909 
910 $space=0;
911 $i=1;
912 while ( $space < ( $field_cage_width / 2 ) ) {
913  $xPos=$space+2;
914  print GDML <<EOF;
915  <physvol>
916  <volumeref ref="volFieldCageTubeTop"/>
917  <position name="posFieldCageTubeTopA$i" unit="cm" x="$xPos" y="0.5*(kFieldCageLoopHeight-2*kFieldCageTubeRadius)" z="0"/>
918  </physvol>
919  <physvol>
920  <volumeref ref="volFieldCageTubeBot"/>
921  <position name="posFieldCageTubeBotA$i" unit="cm" x="$xPos" y="-0.5*(kFieldCageLoopHeight-2*kFieldCageTubeRadius)" z="0"/>
922  </physvol>
923  <physvol>
924  <volumeref ref="volFieldCageTubeFront"/>
925  <position name="posFieldCageTubeFrontA$i" unit="cm" x="$xPos" y="0" z="0.5*(kFieldCageLoopLength-2*kFieldCageTubeRadius)"/>
926  <rotation name="rFieldCageVertPlusA$i" unit="deg" x="90" y="0" z="0"/>
927  </physvol>
928  <physvol>
929  <volumeref ref="volFieldCageTubeBack"/>
930  <position name="posFieldCageTubeBackA$i" unit="cm" x="$xPos" y="0" z="-0.5*(kFieldCageLoopLength-2*kFieldCageTubeRadius)"/>
931  <rotation name="rFieldCageVertMinusA$i" unit="deg" x="-90" y="0" z="0"/>
932  </physvol>
933 EOF
934  print GDML <<EOF;
935  <physvol>
936  <volumeref ref="volFieldCageTubeTop"/>
937  <position name="posFieldCageTubeTopB$i" unit="cm" x="-$xPos" y="0.5*(kFieldCageLoopHeight-2*kFieldCageTubeRadius)" z="0"/>
938  </physvol>
939  <physvol>
940  <volumeref ref="volFieldCageTubeBot"/>
941  <position name="posFieldCageTubeBotB$i" unit="cm" x="-$xPos" y="-0.5*(kFieldCageLoopHeight-2*kFieldCageTubeRadius)" z="0"/>
942  </physvol>
943  <physvol>
944  <volumeref ref="volFieldCageTubeFront"/>
945  <position name="posFieldCageTubeFrontB$i" unit="cm" x="-$xPos" y="0" z="0.5*(kFieldCageLoopLength-2*kFieldCageTubeRadius)"/>
946  <rotation name="rFieldCageVertFrontB$i" unit="deg" x="90" y="0" z="0"/>
947  </physvol>
948  <physvol>
949  <volumeref ref="volFieldCageTubeBack"/>
950  <position name="posFieldCageTubeBackB$i" unit="cm" x="-$xPos" y="0" z="-0.5*(kFieldCageLoopLength-2*kFieldCageTubeRadius)"/>
951  <rotation name="rFieldCageVertBackB$i" unit="deg" x="-90" y="0" z="0"/>
952  </physvol>
953 EOF
954  $space+=4*$field_cage_loop_interval;
955  $i++;
956 }
957 
958 
959 
960  # Closes TPC volume definition space
961  print GDML <<EOF;
962  </volume>
963 </structure>
964 </gdml>
965 EOF
966 
967  close(GDML);
968 }
969 
970 
971 # Generates Ben Jones's PMT micro-pmtdef (with temporary edit to ellipsoid shapes
972 sub gen_pmt {
973 
974  $PMT = "microboone/micro-pmtdef" . $suffix . ".gdml";
975  push (@gdmlFiles, $PMT); # Add file to list of GDML fragments
976  $PMT = ">" . $PMT;
977  open(PMT) or die("Could not open file $PMT for writing");
978 
979  print PMT <<EOF;
980 <solids>
981  <tube name="PMTVolume"
982  rmax="(6*2.54)"
983  z="(11.0*2.54)"
984  deltaphi="2*(3.1415926535897)"
985  aunit="rad"
986  lunit="cm"/>
987  <tube name="PMT_TPBCoating"
988  rmax="(6.0*2.54)"
989  z="0.01"
990  deltaphi="2*(3.1415926535897)"
991  aunit="rad"
992  lunit="cm"/>
993  <tube name="PMT_AcrylicPlate"
994  rmax="(6.0*2.54)"
995  z="(0.2)"
996  deltaphi="2*(3.1415926535897)"
997  aunit="rad"
998  lunit="cm"/>
999  <tube name="PMT_Stalk"
1000  rmax="(1.25*2.54)"
1001  z="(3.0*2.54)"
1002  deltaphi="2*(3.1415926535897)"
1003  aunit="rad"
1004  lunit="cm"/>
1005  <tube name="PMT_SteelBase"
1006  rmax="(6.0*2.54)"
1007  z="(1.5*2.54)"
1008  deltaphi="2*(3.1415926535897)"
1009  aunit="rad"
1010  lunit="cm"/>
1011  <tube name="PMT_Underside"
1012  rmax="2.54*4.0"
1013  z="2.54*2.5"
1014  deltaphi="2*3.1415926535897"
1015  aunit="rad"
1016  lunit="cm"/>
1017  <tube name="PMT_Lens"
1018  rmax="2.54*4.0"
1019  z="2.54*2.5"
1020  deltaphi="2*3.1415926535897"
1021  aunit="rad"
1022  lunit="cm"/>
1023 </solids>
1024 <structure>
1025  <volume name="vol_PMT_TPBCoating">
1026  <materialref ref="TPB"/>
1027  <solidref ref="PMT_TPBCoating"/>
1028  </volume>
1029  <volume name="vol_PMT_AcrylicPlate">
1030  <materialref ref="Acrylic"/>
1031  <solidref ref="PMT_AcrylicPlate"/>
1032  </volume>
1033  <volume name="vol_PMT_Stalk">
1034  <materialref ref="Glass"/>
1035  <solidref ref="PMT_Stalk"/>
1036  </volume>
1037  <volume name="vol_PMT_SteelBase">
1038  <materialref ref="STEEL_STAINLESS_Fe7Cr2Ni"/>
1039  <solidref ref="PMT_SteelBase"/>
1040  </volume>
1041  <volume name="vol_PMT_Underside">
1042  <materialref ref="Glass"/>
1043  <solidref ref="PMT_Underside"/>
1044  </volume>
1045  <volume name="volOpDetSensitive">
1046  <materialref ref="LAr"/>
1047  <solidref ref="PMT_Lens"/>
1048  </volume>
1049  <volume name="volPMT">
1050  <materialref ref="LAr"/>
1051  <solidref ref="PMTVolume"/>
1052  <physvol>
1053  <volumeref ref="vol_PMT_TPBCoating"/>
1054  <position name="pos_PMT_TPBCoating" unit="cm" x="0" y="0" z="(5.5 * 2.54) - (0.5 * 0.005)"/>
1055  </physvol>
1056  <physvol>
1057  <volumeref ref="vol_PMT_AcrylicPlate"/>
1058  <position name="pos_PMT_AcrylicPlate" unit="cm" x="0" y="0" z="(5.5 * 2.54) - 0.01 - (0.5 * 0.2)"/>
1059  </physvol>
1060  <physvol>
1061  <volumeref ref="vol_PMT_Stalk"/>
1062  <position name="pos_PMT_Stalk" unit="cm" x="0" y="0" z="(3.0 * 2.54)-(5.5 * 2.54)"/>
1063  </physvol>
1064  <physvol>
1065  <volumeref ref="vol_PMT_SteelBase"/>
1066  <position name="pos_PMT_SteelBase" unit="cm" x="0" y="0" z="(0.75 * 2.54)-(5.5 * 2.54)"/>
1067  </physvol>
1068  <physvol>
1069  <volumeref ref="volOpDetSensitive"/>
1070  <position name="pos_PMT_Lens" unit="cm" x="0" y="0" z="(7.0 * 2.54)-(5.5 * 2.54)"/>
1071  </physvol>
1072  <physvol>
1073  <volumeref ref="vol_PMT_Underside"/>
1074  <position name="pos_PMT_Underside" unit="cm" x="0" y="0" z="(7.0 * 2.54)-(5.5 * 2.54)"/>
1075  </physvol>
1076  </volume>
1077 </structure>
1078 EOF
1079 
1080 }
1081 
1082 
1083 
1084 
1085 #Parameterize the steel cryostat that encloses the TPC.
1086 sub gen_cryostat()
1087 {
1088  # Set up the output file.
1089  $CRYOSTAT = "microboone/micro-cryostat" . $suffix . ".gdml";
1090  push (@gdmlFiles, $CRYOSTAT); # Add file to list of GDML fragments
1091  $CRYOSTAT = ">" . $CRYOSTAT;
1092  open(CRYOSTAT) or die("Could not open file $CRYOSTAT for writing");
1093 
1094  print CRYOSTAT <<EOF;
1095 <?xml version='1.0'?>
1096 <gdml>
1097 <solids>
1098  <tube name="Cryostat"
1099  rmax="$CryostatOuterRadius"
1100  z="$CryostatLength+2*$CryostatEndcapThickness"
1101  deltaphi="2*kPi"
1102  aunit="rad"
1103  lunit="cm"/>
1104 <tube name="SteelTube"
1105  rmin="$CryostatInnerRadius"
1106  rmax="$CryostatOuterRadius"
1107  z="$CryostatLength"
1108  deltaphi="2*kPi"
1109  aunit="rad"
1110  lunit="cm"/>
1111 EOF
1112 
1113 
1114  print CRYOSTAT <<EOF;
1115 </solids>
1116 
1117 <structure>
1118  <volume name="volSteelTube">
1119  <materialref ref="STEEL_STAINLESS_Fe7Cr2Ni"/>
1120  <solidref ref="SteelTube"/>
1121  </volume>
1122  <volume name="volCryostat">
1123  <materialref ref="LAr"/>
1124  <solidref ref="Cryostat"/>
1125  <physvol>
1126  <volumeref ref="volSteelTube"/>
1127  <position name="posSteelTube" unit="cm" x="0" y="0" z="0"/>
1128  </physvol>
1129  <physvol>
1130  <volumeref ref="volTPC"/>
1131  <position name="posTPC" unit="cm" x="0.0" y="0.97" z="0"/>
1132  </physvol>
1133 EOF
1134 
1135 
1136  @pmt_pos = ( ' x="-147.8" y="3.21654" z="-463.358"',
1137  ' x="-147.76" y="-52.6635" z="-403.121"',
1138  ' x="-147.8" y="59.0965" z="-403.121"',
1139  ' x="-147.76" y="-52.6635" z="-361.449"',
1140  ' x="-147.8" y="59.0965" z="-361.449"',
1141  ' x="-147.8" y="3.21654" z="-308.81"',
1142  ' x="-147.8" y="3.21654" z="-249.591"',
1143  ' x="-147.76" y="-52.6635" z="-194.487"',
1144  ' x="-147.8" y="59.0965" z="-194.487"',
1145  ' x="-147.76" y="-52.6635" z="-155.932"',
1146  ' x="-147.8" y="59.0965" z="-155.932"',
1147  ' x="-147.8" y="3.21654" z="-104.833"',
1148  ' x="-147.8" y="3.21654" z="-38.3029"',
1149  ' x="-147.76" y="-52.6635" z="13.6988"',
1150  ' x="-147.8" y="59.0965" z="13.6988"',
1151  ' x="-147.76" y="-52.6635" z="54.0326"',
1152  ' x="-147.8" y="59.0965" z="54.0326"',
1153  ' x="-147.8" y="3.21654" z="108.648"',
1154  ' x="-147.8" y="3.21654" z="175.178"',
1155  ' x="-147.76" y="-52.6635" z="229.136"',
1156  ' x="-147.8" y="59.0965" z="229.136"',
1157  ' x="-147.76" y="-52.6635" z="267.023"',
1158  ' x="-147.8" y="59.0965" z="267.023"',
1159  ' x="-147.8" y="3.21654" z="314.818"',
1160  ' x="-147.8" y="3.21654" z="385.004"',
1161  ' x="-147.76" y="-52.6635" z="434.169"',
1162  ' x="-147.8" y="59.0965" z="434.169"',
1163  ' x="-147.76" y="-52.6635" z="474.285"',
1164  ' x="-147.8" y="59.0965" z="474.285"',
1165  ' x="-147.8" y="3.21654" z="514.408"' );
1166 
1167  if ( $pmt_switch eq "on" ) {
1168  for ( $i=0; $i<30; ++$i ){
1169  print CRYOSTAT <<EOF;
1170  <physvol>
1171  <volumeref ref="volPMT"/>
1172  <position name="posPMT$i" unit="cm" @pmt_pos[$i]/>
1173  <rotationref ref="rPMTRotation1"/>
1174  </physvol>
1175 EOF
1176  }
1177  }
1178 
1179  print CRYOSTAT <<EOF;
1180  </volume>
1181 </structure>
1182 </gdml>
1183 EOF
1184 
1185  close(CRYOSTAT);
1186 }
1187 
1188 
1189 # Parameterize the cryostat's surroundings.
1190 sub gen_enclosure()
1191 {
1192  # Set up the output file.
1193  $GDML = "micro-enclosure" . $suffix . ".gdml";
1194  push (@gdmlFiles, $GDML); # Add file to list of GDML fragments
1195  $GDML = ">" . $GDML;
1196  open(GDML) or die("Could not open file $GDML for writing");
1197 
1198  print GDML <<EOF;
1199 <?xml version='1.0'?>
1200 <gdml>
1201 <solids>
1202  <box name="DetEnclosure" lunit="cm"
1203  x="kDetEnclosureWidth" y="$CryostatRadius" z="kDetEnclosureLength"
1204  />
1205 </solids>
1206 
1207 <structure>
1208  <volume name="volDetEnclosure">
1209  <materialref ref="Air"/>
1210  <solidref ref="DetEnclosure"/>
1211  <physvol>
1212  <volumeref ref="volCryostat"/>
1213  <position name="posCryostat" unit="cm" x="0" y="0" z="0"/>
1214  </physvol>
1215  </volume>
1216 </structure>
1217 </gdml>
1218 EOF
1219 
1220  close(GDML);
1221 }
1222 
1223 
1224 sub gen_enclosure()
1225 {
1226  # Set up the output file.
1227  $GDML = "micro-enclosure" . $suffix . ".gdml";
1228  push (@gdmlFiles, $GDML); # Add file to list of GDML fragments
1229  $GDML = ">" . $GDML;
1230  open(GDML) or die("Could not open file $GDML for writing");
1231 
1232  print GDML <<EOF;
1233 <?xml version='1.0'?>
1234 <gdml>
1235 <solids>
1236  <box name="DetEnclosure" lunit="cm"
1237  x="kDetEnclosureWidth" y="2*$CryostatOuterRadius+100" z="kDetEnclosureLength"
1238  />
1239 </solids>
1240 
1241 <structure>
1242  <volume name="volDetEnclosure">
1243  <materialref ref="Air"/>
1244  <solidref ref="DetEnclosure"/>
1245  <physvol>
1246  <volumeref ref="volCryostat"/>
1247  <position name="posCryostat" unit="cm" x="0" y="0" z="0"/>
1248  </physvol>
1249  </volume>
1250 </structure>
1251 </gdml>
1252 EOF
1253 
1254  close(GDML);
1255 }
1256 
1257 
1258 # Parameterize the dirt mound that surrounds the enclosure.
1259 sub gen_world()
1260 {
1261  # Set up the output file.
1262  $GDML = "micro-world" . $suffix . ".gdml";
1263  push (@gdmlFiles, $GDML); # Add file to list of GDML fragments
1264  $GDML = ">" . $GDML;
1265  open(GDML) or die("Could not open file $GDML for writing");
1266 
1267  print GDML <<EOF;
1268 <?xml version='1.0'?>
1269 <gdml>
1270 <solids>
1271  <box name="World"
1272  lunit="cm"
1273  x="kWorldW"
1274  y="kWorldH"
1275  z="kWorldL"/>
1276  <tube name="Ground"
1277  rmin="620*2.54"
1278  rmax="((50*12)+620)*2.54"
1279  z="41*12*2.54"
1280  deltaphi="360"
1281  lunit="cm"
1282  aunit="deg"/>
1283  <tube name="ConcreteEnclosure"
1284  rmin="584*2.54"
1285  rmax="620*2.54"
1286  z="38*12*2.54"
1287  deltaphi="360"
1288  lunit="cm"
1289  aunit="deg"/>
1290  <tube name="ConcreteEnclosureBottom"
1291  rmin="0"
1292  rmax="620*2.54"
1293  z="36*2.54"
1294  deltaphi="360"
1295  lunit="cm"
1296  aunit="deg"/>
1297  <tube name="Overburden"
1298  rmin="0"
1299  rmax="584*2.54"
1300  z="10*12*2.54"
1301  deltaphi="360"
1302  lunit="cm"
1303  aunit="deg"/>
1304 </solids>
1305 
1306 <structure>
1307  <volume name="volGround" >
1308  <materialref ref="Dirt" />
1309  <solidref ref="Ground" />
1310  </volume>
1311  <volume name="volOverburden" >
1312  <materialref ref="Dirt" />
1313  <solidref ref="Overburden" />
1314  </volume>
1315  <volume name="volConcreteEnclosure" >
1316  <materialref ref="Concrete" />
1317  <solidref ref="ConcreteEnclosure" />
1318  </volume>
1319  <volume name="volConcreteEnclosureBottom" >
1320  <materialref ref="Concrete" />
1321  <solidref ref="ConcreteEnclosureBottom" />
1322  </volume>
1323  <volume name="volWorld" >
1324  <materialref ref="Air"/>
1325  <solidref ref="World"/>
1326  <physvol>
1327  <volumeref ref="volConcreteEnclosure"/>
1328  <position name="posConcreteEnclosure" unit="cm" x="0.5*kTPCDepth" y="36*2.54/2" z="0.5*kTPCLength"/>
1329  <rotationref ref="rPlus90AboutX"/>
1330  </physvol>
1331  <physvol>
1332  <volumeref ref="volConcreteEnclosureBottom"/>
1333  <position name="posConcreteEnclosureBottom" unit="cm" x="0.5*kTPCDepth" y="-38*12*2.54/2" z="0.5*kTPCLength"/>
1334  <rotationref ref="rPlus90AboutX"/>
1335  </physvol>
1336  <physvol>
1337  <volumeref ref="volGround"/>
1338  <position name="posGround" unit="cm" x="0.5*kTPCDepth" y="0" z="0.5*kTPCLength"/>
1339  <rotationref ref="rPlus90AboutX"/>
1340  </physvol>
1341  <physvol>
1342  <volumeref ref="volOverburden"/>
1343  <position name="posOverburden" unit="cm" x="0.5*kTPCDepth" y="(41-10)*12*2.54/2" z="0.5*kTPCLength"/>
1344  <rotationref ref="rPlus90AboutX"/>
1345  </physvol>
1346  <physvol>
1347  <volumeref ref="volDetEnclosure"/>
1348  <position name="posDetEnclosure" unit="cm" x="0.5*kTPCDepth" y="0" z="0.5*kTPCLength"/>
1349  </physvol>
1350  </volume>
1351 </structure>
1352 </gdml>
1353 EOF
1354 
1355  close(GDML);
1356 }
1357 
1358 
1359 
1360 sub write_fragments()
1361 {
1362  # The output file is a list of the GDML sub-files created by this
1363  # script.
1364 
1365  if ( ! defined $output )
1366  {
1367  $output = "-"; # write to STDOUT
1368  }
1369 
1370  # Set up the output file.
1371  $OUTPUT = ">" . $output;
1372  open(OUTPUT) or die("Could not open file $OUTPUT");
1373 
1374  print OUTPUT <<EOF;
1375 <?xml version='1.0'?>
1376 
1377 <!-- Input to Geometry/gdml/make_gdml.pl; define the GDML fragments
1378  that will be zipped together to create a detector description.
1379  -->
1380 
1381 <config>
1382 
1383  <constantfiles>
1384 
1385  <!-- These files contain GDML <constant></constant>
1386  blocks. They are read in separately, so they can be
1387  interpreted into the remaining GDML. See make_gdml.pl for
1388  more information.
1389  -->
1390 
1391 EOF
1392 
1393  foreach $filename (@defFiles)
1394  {
1395  print OUTPUT <<EOF;
1396  <filename> $filename </filename>
1397 EOF
1398  }
1399 
1400  print OUTPUT <<EOF;
1401 
1402  </constantfiles>
1403 
1404  <gdmlfiles>
1405 
1406  <!-- The GDML file fragments to be zipped together. -->
1407 
1408 EOF
1409 
1410  foreach $filename (@gdmlFiles)
1411  {
1412  print OUTPUT <<EOF;
1413  <filename> $filename </filename>
1414 EOF
1415  }
1416 
1417  print OUTPUT <<EOF;
1418 
1419  </gdmlfiles>
1420 
1421 </config>
1422 EOF
1423 
1424  close(OUTPUT);
1425 }