Logo ROOT  
Reference Guide
 
Loading...
Searching...
No Matches
TGDMLParse.cxx
Go to the documentation of this file.
1/* @(#)root/gdml:$Id$ */
2// Author: Ben Lloyd 09/11/06
3
4/*************************************************************************
5 * Copyright (C) 1995-2006, Rene Brun and Fons Rademakers. *
6 * All rights reserved. *
7 * *
8 * For the licensing terms see $ROOTSYS/LICENSE. *
9 * For the list of contributors see $ROOTSYS/README/CREDITS. *
10 *************************************************************************/
11
12/** \class TGDMLParse
13\ingroup Geometry_gdml
14
15 This class contains the implementation of the GDML parser associated to
16 all the supported GDML elements. User should never need to explicitly
17 instaciate this class. It is internally used by the TGeoManager.
18
19 Each element process has a 'Binding' to ROOT. The 'binding' is specific
20 mapping of GDML elements (materials, solids, etc) to specific objects which
21 should be instanciated by the converted. In the present case (ROOT) the
22 binding is implemented at the near the end of each process function. Most
23 bindings follow similar format, dependent on what is being added to the
24 geometry.
25
26 This file also contains the implementation of the TGDMLRefl class. This is
27 just a small helper class used internally by the 'reflection' method (for
28 reflected solids).
29
30 The presently supported list of TGeo classes is the following:
31
32#### Materials:
33 - TGeoElement
34 - TGeoMaterial
35 - TGeoMixture
36
37#### Solids:
38 - TGeoBBox
39 - TGeoArb8
40 - TGeoTubeSeg
41 - TGeoConeSeg
42 - TGeoCtub
43 - TGeoPcon
44 - TGeoTrap
45 - TGeoGtra
46 - TGeoTrd2
47 - TGeoSphere
48 - TGeoPara
49 - TGeoTorus
50 - TGeoHype
51 - TGeoPgon
52 - TGeoXtru
53 - TGeoEltu
54 - TGeoParaboloid
55 - TGeoCompositeShape (subtraction, union, intersection)
56
57#### Approximated Solids:
58 - Ellipsoid (approximated to a TGeoBBox)
59 - Elliptical cone (approximated to a TGeoCone)
60
61#### Geometry:
62 - TGeoVolume
63 - TGeoVolumeAssembly
64 - divisions
65 - reflection
66
67When most solids or volumes are added to the geometry they
68
69
70 Whenever a new element is added to GDML schema, this class needs to be extended.
71 The appropriate method (process) needs to be implemented, as well as the new
72 element process then needs to be linked thru the function TGDMLParse
73
74 For any question or remarks concerning this code, please send an email to
75 ben.lloyd@cern.ch
76
77*/
78
79#include "TGDMLParse.h"
80#include "TGDMLMatrix.h"
81
82#include "TGeoManager.h"
83#include "TGeoMatrix.h"
84#include "TXMLEngine.h"
85#include "TGeoVolume.h"
86#include "TGeoBBox.h"
87#include "TGeoParaboloid.h"
88#include "TGeoArb8.h"
89#include "TGeoTube.h"
90#include "TGeoCone.h"
91#include "TGeoTrd2.h"
92#include "TGeoPcon.h"
93#include "TGeoPgon.h"
94#include "TGeoSphere.h"
95#include "TGeoTorus.h"
96#include "TGeoPara.h"
97#include "TGeoHype.h"
98#include "TGeoEltu.h"
99#include "TGeoXtru.h"
100#include "TGeoScaledShape.h"
101#include "TGeoTessellated.h"
102#include "TMath.h"
103#include "TMap.h"
104#include "TObjString.h"
105#include "TGeoExtension.h"
106#include "TGeoMaterial.h"
107#include "TGeoBoolNode.h"
108#include "TGeoMedium.h"
109#include "TGeoElement.h"
110#include "TGeoShape.h"
111#include "TGeoCompositeShape.h"
112#include "TGeoRegion.h"
113#include "TGeoOpticalSurface.h"
114#include "TGeoSystemOfUnits.h"
115#include "TGeant4SystemOfUnits.h"
116
117#include <cstdlib>
118#include <string>
119#include <sstream>
120#include <locale>
121
123
124////////////////////////////////////////////////////////////////////////////////
125/// Constructor
126
128{
129 fWorldName = "";
130 fWorld = 0;
131 fVolID = 0;
132 fFILENO = 0;
133 for (Int_t i = 0; i < 20; i++)
134 fFileEngine[i] = 0;
135 fStartFile = 0;
136 fCurrentFile = 0;
137 auto def_units = gGeoManager->GetDefaultUnits();
138 switch (def_units) {
140 fDefault_lunit = "mm";
141 fDefault_aunit = "rad";
142 break;
144 fDefault_lunit = "cm";
145 fDefault_aunit = "deg";
146 break;
147 default: // G4 units
148 fDefault_lunit = "mm";
149 fDefault_aunit = "rad";
150 }
151}
152
153////////////////////////////////////////////////////////////////////////////////
154/// Creates the new instance of the XMLEngine called 'gdml', using the filename >>
155/// then parses the file and creates the DOM tree. Then passes the DOM to the
156/// next function to translate it.
157
159{
160 // First create engine
161 TXMLEngine *gdml = new TXMLEngine;
162 gdml->SetSkipComments(kTRUE);
163
164 // Now try to parse xml file
165 XMLDocPointer_t gdmldoc = gdml->ParseFile(filename);
166 if (gdmldoc == 0) {
167 delete gdml;
168 return 0;
169 } else {
170
171 // take access to main node
172 XMLNodePointer_t mainnode = gdml->DocGetRootElement(gdmldoc);
173
174 fFileEngine[fFILENO] = gdml;
177
178 // display recursively all nodes and subnodes
179 ParseGDML(gdml, mainnode);
180
181 // Release memory before exit
182 gdml->FreeDoc(gdmldoc);
183 delete gdml;
184 }
186 Warning("GDMLReadFile",
187 "\x1B[31m Found %d GDML entities missing explicit units, while the default "
188 "units are currently ROOT units [cm, deg]. This can cause unexpected behaviour with respect "
189 "to the GDML schema. To remove this warning, either use explicit units or call the static method "
190 "TGeoManager::SetDefaultUnits(kG4Units) before importing the GDML file \x1B[34m%s \x1B[0m",
192 }
193 return fWorld;
194}
195
196////////////////////////////////////////////////////////////////////////////////
197/// This function recursively moves thru the DOM tree of the GDML file. It checks for
198/// key words along the way and if a key word is found it calls the corresponding
199/// function to interpret the node.
200
202{
204 XMLAttrPointer_t attr = gdml->GetFirstAttr(node);
205 const char *name = gdml->GetNodeName(node);
206 XMLNodePointer_t parentn = gdml->GetParent(node);
207 const char *parent = gdml->GetNodeName(parentn);
208 XMLNodePointer_t childtmp = 0;
209
210 const char *posistr = "position";
211 const char *setustr = "setup";
212 const char *consstr = "constant";
213 const char *varistr = "variable";
214 const char *quanstr = "quantity";
215 const char *matrstr = "matrix";
216 const char *rotastr = "rotation";
217 const char *scalstr = "scale";
218 const char *elemstr = "element";
219 const char *istpstr = "isotope";
220 const char *matestr = "material";
221 const char *volustr = "volume";
222 const char *assestr = "assembly";
223 const char *twtrstr = "twistedtrap";
224 const char *cutTstr = "cutTube";
225 const char *bboxstr = "box";
226 const char *xtrustr = "xtru";
227 const char *arb8str = "arb8";
228 const char *tubestr = "tube";
229 const char *conestr = "cone";
230 const char *polystr = "polycone";
231 const char *hypestr = "hype";
232 const char *trapstr = "trap";
233 const char *trdstr = "trd";
234 const char *sphestr = "sphere";
235 const char *orbstr = "orb";
236 const char *parastr = "para";
237 const char *torustr = "torus";
238 const char *hedrstr = "polyhedra";
239 const char *eltustr = "eltube";
240 const char *subtstr = "subtraction";
241 const char *uniostr = "union";
242 const char *parbstr = "paraboloid";
243 const char *intestr = "intersection";
244 const char *reflstr = "reflectedSolid";
245 const char *ellistr = "ellipsoid";
246 const char *elcnstr = "elcone";
247 const char *optsstr = "opticalsurface";
248 const char *skinstr = "skinsurface";
249 const char *bordstr = "bordersurface";
250 const char *usrstr = "userinfo";
251 const char *tslstr = "tessellated";
252 Bool_t hasIsotopes;
253 Bool_t hasIsotopesExtended;
254
255 if ((strcmp(name, posistr)) == 0) {
256 node = PosProcess(gdml, node, attr);
257 } else if ((strcmp(name, rotastr)) == 0) {
258 node = RotProcess(gdml, node, attr);
259 } else if ((strcmp(name, scalstr)) == 0) {
260 node = SclProcess(gdml, node, attr);
261 } else if ((strcmp(name, setustr)) == 0) {
262 node = TopProcess(gdml, node);
263 } else if ((strcmp(name, consstr)) == 0) {
264 node = ConProcess(gdml, node, attr);
265 } else if ((strcmp(name, varistr)) == 0) {
266 node = ConProcess(gdml, node, attr);
267 } else if ((strcmp(name, quanstr)) == 0) {
268 node = QuantityProcess(gdml, node, attr);
269 } else if ((strcmp(name, matrstr)) == 0) {
270 node = MatrixProcess(gdml, node, attr);
271 } else if ((strcmp(name, optsstr)) == 0) {
272 node = OpticalSurfaceProcess(gdml, node, attr);
273 } else if ((strcmp(name, skinstr)) == 0) {
274 node = SkinSurfaceProcess(gdml, node, attr);
275 } else if ((strcmp(name, bordstr)) == 0) {
276 node = BorderSurfaceProcess(gdml, node, attr);
277 }
278 //*************eleprocess********************************
279
280 else if (((strcmp(name, "atom")) == 0) && ((strcmp(parent, elemstr)) == 0)) {
281 hasIsotopes = kFALSE;
282 hasIsotopesExtended = kFALSE;
283 node = EleProcess(gdml, node, parentn, hasIsotopes, hasIsotopesExtended);
284 } else if ((strcmp(name, elemstr) == 0) && !gdml->HasAttr(node, "Z")) {
285 hasIsotopes = kTRUE;
286 hasIsotopesExtended = kFALSE;
287 node = EleProcess(gdml, node, parentn, hasIsotopes, hasIsotopesExtended);
288 }
289
290 else if ((strcmp(name, elemstr) == 0) && gdml->HasAttr(node, "Z")) {
291 childtmp = gdml->GetChild(node);
292 if ((strcmp(gdml->GetNodeName(childtmp), "fraction") == 0)) {
293 hasIsotopes = kFALSE;
294 hasIsotopesExtended = kTRUE;
295 node = EleProcess(gdml, node, parentn, hasIsotopes, hasIsotopesExtended);
296 }
297 }
298
299 //********isoprocess******************************
300
301 else if (((strcmp(name, "atom")) == 0) && ((strcmp(parent, istpstr)) == 0)) {
302 node = IsoProcess(gdml, node, parentn);
303 }
304
305 //********matprocess***********************************
306 else if ((strcmp(name, matestr)) == 0 && gdml->HasAttr(node, "Z")) {
307 childtmp = gdml->GetChild(node);
308 // if ((strcmp(gdml->GetNodeName(childtmp), "fraction") == 0) || (strcmp(gdml->GetNodeName(childtmp), "D") ==
309 // 0)){
310 // Bool_t frac = kFALSE;
312 while (childtmp) {
313 // frac = strcmp(gdml->GetNodeName(childtmp),"fraction")==0;
314 atom = strcmp(gdml->GetNodeName(childtmp), "atom") == 0;
315 gdml->ShiftToNext(childtmp);
316 }
317 int z = (atom) ? 1 : 0;
318 node = MatProcess(gdml, node, attr, z);
319 } else if ((strcmp(name, matestr)) == 0 && !gdml->HasAttr(node, "Z")) {
320 int z = 0;
321 node = MatProcess(gdml, node, attr, z);
322 }
323
324 //*********************************************
325 else if ((strcmp(name, volustr)) == 0) {
326 node = VolProcess(gdml, node);
327 } else if ((strcmp(name, bboxstr)) == 0) {
328 node = Box(gdml, node, attr);
329 } else if ((strcmp(name, ellistr)) == 0) {
330 node = Ellipsoid(gdml, node, attr);
331 } else if ((strcmp(name, elcnstr)) == 0) {
332 node = ElCone(gdml, node, attr);
333 } else if ((strcmp(name, cutTstr)) == 0) {
334 node = CutTube(gdml, node, attr);
335 } else if ((strcmp(name, arb8str)) == 0) {
336 node = Arb8(gdml, node, attr);
337 } else if ((strcmp(name, tubestr)) == 0) {
338 node = Tube(gdml, node, attr);
339 } else if ((strcmp(name, conestr)) == 0) {
340 node = Cone(gdml, node, attr);
341 } else if ((strcmp(name, polystr)) == 0) {
342 node = Polycone(gdml, node, attr);
343 } else if ((strcmp(name, trapstr)) == 0) {
344 node = Trap(gdml, node, attr);
345 } else if ((strcmp(name, trdstr)) == 0) {
346 node = Trd(gdml, node, attr);
347 } else if ((strcmp(name, sphestr)) == 0) {
348 node = Sphere(gdml, node, attr);
349 } else if ((strcmp(name, xtrustr)) == 0) {
350 node = Xtru(gdml, node, attr);
351 } else if ((strcmp(name, twtrstr)) == 0) {
352 node = TwistTrap(gdml, node, attr);
353 } else if ((strcmp(name, hypestr)) == 0) {
354 node = Hype(gdml, node, attr);
355 } else if ((strcmp(name, orbstr)) == 0) {
356 node = Orb(gdml, node, attr);
357 } else if ((strcmp(name, parastr)) == 0) {
358 node = Para(gdml, node, attr);
359 } else if ((strcmp(name, torustr)) == 0) {
360 node = Torus(gdml, node, attr);
361 } else if ((strcmp(name, eltustr)) == 0) {
362 node = ElTube(gdml, node, attr);
363 } else if ((strcmp(name, hedrstr)) == 0) {
364 node = Polyhedra(gdml, node, attr);
365 } else if ((strcmp(name, tslstr)) == 0) {
366 node = Tessellated(gdml, node, attr);
367 } else if ((strcmp(name, parbstr)) == 0) {
368 node = Paraboloid(gdml, node, attr);
369 } else if ((strcmp(name, subtstr)) == 0) {
370 node = BooSolid(gdml, node, attr, 1);
371 } else if ((strcmp(name, intestr)) == 0) {
372 node = BooSolid(gdml, node, attr, 2);
373 } else if ((strcmp(name, uniostr)) == 0) {
374 node = BooSolid(gdml, node, attr, 3);
375 } else if ((strcmp(name, reflstr)) == 0) {
376 node = Reflection(gdml, node, attr);
377 } else if ((strcmp(name, assestr)) == 0) {
378 node = AssProcess(gdml, node);
379 } else if ((strcmp(name, usrstr)) == 0) {
380 node = UsrProcess(gdml, node);
381 // CHECK FOR TAGS NOT SUPPORTED
382 } else if (((strcmp(name, "gdml")) != 0) && ((strcmp(name, "define")) != 0) && ((strcmp(name, "element")) != 0) &&
383 ((strcmp(name, "materials")) != 0) && ((strcmp(name, "solids")) != 0) &&
384 ((strcmp(name, "structure")) != 0) && ((strcmp(name, "zplane")) != 0) && ((strcmp(name, "first")) != 0) &&
385 ((strcmp(name, "second")) != 0) && ((strcmp(name, "twoDimVertex")) != 0) &&
386 ((strcmp(name, "firstposition")) != 0) && ((strcmp(name, "firstpositionref")) != 0) &&
387 ((strcmp(name, "firstrotation")) != 0) && ((strcmp(name, "firstrotationref")) != 0) &&
388 ((strcmp(name, "section")) != 0) && ((strcmp(name, "world")) != 0) && ((strcmp(name, "isotope")) != 0) &&
389 ((strcmp(name, "triangular")) != 0) && ((strcmp(name, "quadrangular")) != 0)) {
390 std::cout << "Error: Unsupported GDML Tag Used :" << name << ". Please Check Geometry/Schema." << std::endl;
391 }
392
393 // Check for Child node - if present call this funct. recursively until no more
394
395 XMLNodePointer_t child = gdml->GetChild(node);
396 while (child != 0) {
397 ParseGDML(gdml, child);
398 child = gdml->GetNext(child);
399 }
400
401 return fWorldName;
402}
403
404////////////////////////////////////////////////////////////////////////////////
405/// Takes a string containing a mathematical expression and returns the value of
406/// the expression
407
408double TGDMLParse::Evaluate(const char *evalline)
409{
410
411 return TFormula("TFormula", evalline).Eval(0);
412}
413
414////////////////////////////////////////////////////////////////////////////////
415/// When using the 'divide' process in the geometry this function
416/// sets the variable 'axis' depending on what is specified.
417
418Int_t TGDMLParse::SetAxis(const char *axisString)
419{
420 Int_t axis = 0;
421
422 if ((strcmp(axisString, "kXAxis")) == 0) {
423 axis = 1;
424 } else if ((strcmp(axisString, "kYAxis")) == 0) {
425 axis = 2;
426 } else if ((strcmp(axisString, "kZAxis")) == 0) {
427 axis = 3;
428 } else if ((strcmp(axisString, "kRho")) == 0) {
429 axis = 1;
430 } else if ((strcmp(axisString, "kPhi")) == 0) {
431 axis = 2;
432 }
433
434 return axis;
435}
436
437////////////////////////////////////////////////////////////////////////////////
438/// This function looks thru a string for the chars '0x' next to
439/// each other, when it finds this, it calls another function to strip
440/// the hex address. It does this recursively until the end of the
441/// string is reached, returning a string without any hex addresses.
442
443const char *TGDMLParse::NameShort(const char *name)
444{
445 static TString stripped;
446 stripped = name;
447 Int_t index = stripped.Index("0x");
448 if (index >= 0)
449 stripped = stripped(0, index);
450 return stripped.Data();
451}
452
453////////////////////////////////////////////////////////////////////////////////
454/// In the define section of the GDML file, constants can be declared.
455/// when the constant keyword is found, this function is called, and the
456/// name and value of the constant is stored in the "fformvec" vector as
457/// a TFormula class, representing a constant function
458
460{
461 TString name = "";
462 TString value = "";
463 TString tempattr;
464
465 while (attr != 0) {
466 tempattr = gdml->GetAttrName(attr);
467 tempattr.ToLower();
468
469 if (tempattr == "name") {
470 name = gdml->GetAttrValue(attr);
471 }
472 if (tempattr == "value") {
473 value = gdml->GetAttrValue(attr);
474 }
475 attr = gdml->GetNextAttr(attr);
476 }
477
478 // if ((strcmp(fCurrentFile, fStartFile)) != 0) {
479 // name = TString::Format("%s_%s", name.Data(), fCurrentFile);
480 //}
481
482 Double_t val = Value(value);
483 fconsts[name.Data()] = val;
484 gGeoManager->AddProperty(name.Data(), val);
485
486 return node;
487}
488
489////////////////////////////////////////////////////////////////////////////////
490/// Define constant expressions used.
492{
493 auto def_units = gGeoManager->GetDefaultUnits();
494
495 // Units used in TGeo. Note that they are based on cm/degree/GeV and they are different from Geant4
497 fconsts["millimeter"] = (def_units == TGeoManager::kRootUnits) ? TGeoUnit::mm : TGeant4Unit::mm;
499 fconsts["centimeter"] = (def_units == TGeoManager::kRootUnits) ? TGeoUnit::cm : TGeant4Unit::cm;
501 fconsts["meter"] = (def_units == TGeoManager::kRootUnits) ? TGeoUnit::m : TGeant4Unit::m;
503 fconsts["kilometer"] = (def_units == TGeoManager::kRootUnits) ? TGeoUnit::km : TGeant4Unit::km;
504 fconsts["rad"] = TGeoUnit::rad;
505 fconsts["radian"] = TGeoUnit::rad;
506 fconsts["deg"] = TGeoUnit::deg;
507 fconsts["degree"] = TGeoUnit::deg;
508 fconsts["pi"] = TGeoUnit::pi;
509 fconsts["twopi"] = TGeoUnit::twopi;
510 fconsts["avogadro"] = TMath::Na();
526}
527
528////////////////////////////////////////////////////////////////////////////////
529/// In the define section of the GDML file, quantities can be declared.
530/// These are treated the same as constants, but the unit has to be multiplied
531
533{
534 TString name = "";
535 TString value = "";
536 TString unit = "1.0";
537 TString tempattr;
538
539 while (attr != 0) {
540 tempattr = gdml->GetAttrName(attr);
541 tempattr.ToLower();
542
543 if (tempattr == "name") {
544 name = gdml->GetAttrValue(attr);
545 }
546 if (tempattr == "value") {
547 value = gdml->GetAttrValue(attr);
548 }
549 if (tempattr == "unit") {
550 unit = gdml->GetAttrValue(attr);
551 }
552 attr = gdml->GetNextAttr(attr);
553 }
554
555 fconsts[name.Data()] = GetScaleVal(unit) * Value(value);
556
557 return node;
558}
559
560////////////////////////////////////////////////////////////////////////////////
561/// In the define section of the GDML file, matrices
562/// These are referenced by other GDML tags, such as optical surfaces
564{
565 TString name = "";
566 Int_t coldim = 1;
567 std::string values;
568 TString tempattr;
569
570 while (attr != 0) {
571 tempattr = gdml->GetAttrName(attr);
572 tempattr.ToLower();
573
574 if (tempattr == "name") {
575 name = gdml->GetAttrValue(attr);
576 }
577 if (tempattr == "coldim") {
578 coldim = (Int_t)Value(gdml->GetAttrValue(attr));
579 }
580 if (tempattr == "values") {
581 values = gdml->GetAttrValue(attr);
582 }
583 attr = gdml->GetNextAttr(attr);
584 }
585
586 // Parse the values and create the matrix
587 std::stringstream valueStream(values);
588 std::vector<Double_t> valueList;
589 while (!valueStream.eof()) {
590 std::string matrixValue;
591 valueStream >> matrixValue;
592 // protect against trailing '\n' and other white spaces
593 if (matrixValue.empty())
594 continue;
595 valueList.push_back(Value(matrixValue.c_str()));
596 }
597
598 // Const Properties in GDML are matrices with size 1 not constants
599 // This gives some ambiguity, but what can one do?
600 if ( coldim == 1 && valueList.size() == 1 ) {
601 gGeoManager->AddProperty(name, valueList[0]);
602 }
603 else {
604 TGDMLMatrix *matrix = new TGDMLMatrix(name, valueList.size() / coldim, coldim);
605 matrix->SetMatrixAsString(values.c_str());
606 for (size_t i = 0; i < valueList.size(); ++i)
607 matrix->Set(i / coldim, i % coldim, valueList[i]);
608
609 gGeoManager->AddGDMLMatrix(matrix);
610 fmatrices[name.Data()] = matrix;
611 }
612 return node;
613}
614
615////////////////////////////////////////////////////////////////////////////////
616/// In the solids section of the GDML file, optical surfaces can be defined
617///
619{
620 TString name, propname, ref;
624 Double_t value = 0;
625 TString tempattr;
626
627 while (attr != 0) {
628 tempattr = gdml->GetAttrName(attr);
629 tempattr.ToLower();
630
631 if (tempattr == "name") {
632 name = gdml->GetAttrValue(attr);
633 }
634 if (tempattr == "model") {
636 }
637 if (tempattr == "finish") {
639 }
640 if (tempattr == "type") {
642 }
643 if (tempattr == "value") {
644 value = Value(gdml->GetAttrValue(attr));
645 }
646 attr = gdml->GetNextAttr(attr);
647 }
648
649 TGeoOpticalSurface *surf = new TGeoOpticalSurface(name, model, finish, type, value);
650
651 XMLNodePointer_t child = gdml->GetChild(node);
652 while (child != 0) {
653 attr = gdml->GetFirstAttr(child);
654 if ((strcmp(gdml->GetNodeName(child), "property")) == 0) {
655 while (attr != 0) {
656 tempattr = gdml->GetAttrName(attr);
657 tempattr.ToLower();
658 if (tempattr == "name") {
659 propname = gdml->GetAttrValue(attr);
660 } else if (tempattr == "ref") {
661 ref = gdml->GetAttrValue(attr);
662 TGDMLMatrix *matrix = fmatrices[ref.Data()];
663 if (!matrix)
664 Error("OpticalSurfaceProcess", "Reference matrix %s for optical surface %s not found", ref.Data(),
665 name.Data());
666 surf->AddProperty(propname, ref);
667 }
668 attr = gdml->GetNextAttr(attr);
669 }
670 } // loop on child attributes
671 child = gdml->GetNext(child);
672 } // loop on children
674 return child;
675}
676
677////////////////////////////////////////////////////////////////////////////////
678/// Throughout the GDML file, a unit can de specified. Whether it be
679/// angular or linear, values can be used as well as abbreviations such as
680/// 'mm' or 'deg'. This function is passed the specified unit and if it is
681/// found, replaces it with the appropriate value.
682
684{
685 TString retunit = "";
686
687 if (strcmp(unit, "mm") == 0) {
688 retunit = "0.1";
689 } else if (strcmp(unit, "millimeter") == 0 || strcmp(unit, "milimeter") == 0) {
690 retunit = "0.1";
691 } else if (strcmp(unit, "cm") == 0) {
692 retunit = "1.0";
693 } else if (strcmp(unit, "centimeter") == 0) {
694 retunit = "1.0";
695 } else if (strcmp(unit, "m") == 0) {
696 retunit = "100.0";
697 } else if (strcmp(unit, "meter") == 0) {
698 retunit = "100.0";
699 } else if (strcmp(unit, "km") == 0) {
700 retunit = "100000.0";
701 } else if (strcmp(unit, "kilometer") == 0) {
702 retunit = "100000.0";
703 } else if (strcmp(unit, "rad") == 0) {
704 retunit = TString::Format("%.12f", TMath::RadToDeg());
705 } else if (strcmp(unit, "radian") == 0) {
706 retunit = TString::Format("%.12f", TMath::RadToDeg());
707 } else if (strcmp(unit, "deg") == 0) {
708 retunit = "1.0";
709 } else if (strcmp(unit, "degree") == 0) {
710 retunit = "1.0";
711 } else if (strcmp(unit, "pi") == 0) {
712 retunit = "pi";
713 } else if (strcmp(unit, "avogadro") == 0) {
714 retunit = TString::Format("%.12g", TMath::Na());
715 } else {
716 Fatal("GetScale", "Unit <%s> not known", unit);
717 retunit = "0";
718 }
719 return retunit;
720}
721
722////////////////////////////////////////////////////////////////////////////////
723/// Throughout the GDML file, a unit can de specified. Whether it be
724/// angular or linear, values can be used as well as abbreviations such as
725/// 'mm' or 'deg'. This function is passed the specified unit and if it is
726/// found, replaces it with the appropriate value.
727
729{
730 auto def_units = gGeoManager->GetDefaultUnits();
731 Double_t retunit = 0.;
732 TString unit(sunit);
733 unit.ToLower();
734
735 if ((unit == "mm") || (unit == "millimeter") || (unit == "milimeter")) {
736 retunit = (def_units == TGeoManager::kRootUnits) ? 0.1 : 1.0;
737 } else if ((unit == "cm") || (unit == "centimeter")) {
738 retunit = (def_units == TGeoManager::kRootUnits) ? 1.0 : 10.0;
739 } else if ((unit == "m") || (unit == "meter")) {
740 retunit = (def_units == TGeoManager::kRootUnits) ? 100.0 : 1e3;
741 } else if ((unit == "km") || (unit == "kilometer")) {
742 retunit = (def_units == TGeoManager::kRootUnits) ? 100000.0 : 1e6;
743 } else if ((unit == "rad") || (unit == "radian")) {
744 retunit = TMath::RadToDeg();
745 } else if ((unit == "deg") || (unit == "degree")) {
746 retunit = 1.0;
747 } else if ((unit == "ev") || (unit == "electronvolt")) {
748 retunit = (def_units == TGeoManager::kRootUnits) ? 0.000000001 : 1e-6;
749 } else if ((unit == "kev") || (unit == "kiloelectronvolt")) {
750 retunit = (def_units == TGeoManager::kRootUnits) ? 0.000001 : 1e-3;
751 } else if ((unit == "mev") || (unit == "megaelectronvolt")) {
752 retunit = (def_units == TGeoManager::kRootUnits) ? 0.001 : 1.0;
753 } else if ((unit == "gev") || (unit == "gigaelectronvolt")) {
754 retunit = (def_units == TGeoManager::kRootUnits) ? 1.0 : 1000.0;
755 } else if (unit == "pi") {
756 retunit = TMath::Pi();
757 } else if (unit == "avogadro") {
758 retunit = TMath::Na();
759 } else {
760 Fatal("GetScaleVal", "Unit <%s> not known", sunit);
761 retunit = 0;
762 }
763 return retunit;
764}
765
766////////////////////////////////////////////////////////////////////////////////
767/// Convert number in string format to double value.
768
769Double_t TGDMLParse::Value(const char *svalue) const
770{
771 char *end;
772 double val = strtod(svalue, &end);
773
774 // ignore white spaces.
775 while (*end != 0 && isspace(*end))
776 ++end;
777
778 // Successfully parsed all the characters up to the ending NULL, so svalue
779 // was a simple number.
780 if (*end == 0)
781 return val;
782
783 // Otherwise we'll use TFormula to evaluate the string, having first found
784 // all the GDML variable names in it and marked them with [] so that
785 // TFormula will recognize them as parameters.
786
787 std::string expanded;
788 expanded.reserve(strlen(svalue) * 2);
789
790 // Be careful about locale so we always mean the same thing by
791 // "alphanumeric"
792 const std::locale &loc = std::locale::classic(); // "C" locale
793
794 // Walk through the string inserting '[' and ']' where necessary
795 const char *p = svalue;
796 while (*p) {
797 // Find a site for a '['. Just before the first alphabetic character
798 for (; *p != 0; ++p) {
799 if (std::isalpha(*p, loc) || *p == '_') {
800 const char *pe = p + 1;
801 // Now look for the position of the following ']'. Straight before the
802 // first non-alphanumeric character
803 for (; *pe != 0; ++pe) {
804 if (!isalnum(*pe, loc) && *pe != '_') {
805 if (*pe == '(') {
806 // The string represents a function, so no brackets needed: copy chars and advance
807 for (; p < pe; ++p)
808 expanded += *p;
809 break;
810 } else {
811 expanded += '[';
812 for (; p < pe; ++p)
813 expanded += *p;
814 expanded += ']';
815 break;
816 }
817 }
818 }
819 if (*pe == 0) {
820 expanded += '[';
821 for (; p < pe; ++p)
822 expanded += *p;
823 expanded += ']';
824 }
825 }
826 expanded += *p;
827 }
828 } // end loop over svalue
829
830 TFormula f("TFormula", expanded.c_str());
831
832 // Tell the TFormula about every parameter we know about
833 for (auto &it : fconsts)
834 f.SetParameter(it.first.c_str(), it.second);
835
836 val = f.Eval(0);
837
838 if (std::isnan(val) || std::isinf(val)) {
839 Fatal("Value", "Got bad value %lf from string '%s'", val, svalue);
840 }
841
842 return val;
843}
844
845////////////////////////////////////////////////////////////////////////////////
846/// In the define section of the GDML file, positions can be declared.
847/// when the position keyword is found, this function is called, and the
848/// name and values of the position are converted into type TGeoPosition
849/// and stored in fposmap map using the name as its key. This function
850/// can also be called when declaring solids.
851
853{
854 TString lunit = fDefault_lunit.c_str();
855 bool unitless_l = true;
856
857 TString xpos = "0";
858 TString ypos = "0";
859 TString zpos = "0";
860 TString name = "0";
861 TString tempattr;
862
863 while (attr != 0) {
864
865 tempattr = gdml->GetAttrName(attr);
866 tempattr.ToLower();
867
868 if (tempattr == "name") {
869 name = gdml->GetAttrValue(attr);
870 } else if (tempattr == "x") {
871 xpos = gdml->GetAttrValue(attr);
872 } else if (tempattr == "y") {
873 ypos = gdml->GetAttrValue(attr);
874 } else if (tempattr == "z") {
875 zpos = gdml->GetAttrValue(attr);
876 } else if (tempattr == "unit") {
877 lunit = gdml->GetAttrValue(attr);
878 unitless_l = false;
879 }
880
881 attr = gdml->GetNextAttr(attr);
882 }
883
884 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
885 name = TString::Format("%s_%s", name.Data(), fCurrentFile);
886 }
887
888 Double_t retunit = GetScaleVal(lunit);
889 fNunitless += int(unitless_l);
890
891 Double_t xline = Value(xpos) * retunit;
892 Double_t yline = Value(ypos) * retunit;
893 Double_t zline = Value(zpos) * retunit;
894
895 TGeoTranslation *pos = new TGeoTranslation(xline, yline, zline);
896
897 fposmap[name.Data()] = pos;
898
899 return node;
900}
901
902////////////////////////////////////////////////////////////////////////////////
903/// In the define section of the GDML file, rotations can be declared.
904/// when the rotation keyword is found, this function is called, and the
905/// name and values of the rotation are converted into type TGeoRotation
906/// and stored in frotmap map using the name as its key. This function
907/// can also be called when declaring solids.
908
910{
911 TString aunit = fDefault_aunit.c_str();
912 bool unitless_l = true;
913 TString xpos = "0";
914 TString ypos = "0";
915 TString zpos = "0";
916 TString name = "";
917 TString tempattr;
918
919 while (attr != 0) {
920
921 tempattr = gdml->GetAttrName(attr);
922 tempattr.ToLower();
923
924 if (tempattr == "name") {
925 name = gdml->GetAttrValue(attr);
926 } else if (tempattr == "x") {
927 xpos = gdml->GetAttrValue(attr);
928 } else if (tempattr == "y") {
929 ypos = gdml->GetAttrValue(attr);
930 } else if (tempattr == "z") {
931 zpos = gdml->GetAttrValue(attr);
932 } else if (tempattr == "unit") {
933 aunit = gdml->GetAttrValue(attr);
934 unitless_l = false;
935 }
936
937 attr = gdml->GetNextAttr(attr);
938 }
939
940 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
941 name = TString::Format("%s_%s", name.Data(), fCurrentFile);
942 }
943
944 Double_t retunit = GetScaleVal(aunit);
945 fNunitless += int(unitless_l);
946
947 Double_t xline = Value(xpos) * retunit;
948 Double_t yline = Value(ypos) * retunit;
949 Double_t zline = Value(zpos) * retunit;
950
951 TGeoRotation *rot = new TGeoRotation();
952
953 rot->RotateZ(-zline);
954 rot->RotateY(-yline);
955 rot->RotateX(-xline);
956
957 frotmap[name.Data()] = rot;
958
959 return node;
960}
961
962////////////////////////////////////////////////////////////////////////////////
963/// In the define section of the GDML file, rotations can be declared.
964/// when the scale keyword is found, this function is called, and the
965/// name and values of the scale are converted into type TGeoScale
966/// and stored in fsclmap map using the name as its key. This function
967/// can also be called when declaring solids.
968
970{
971 TString xpos = "0";
972 TString ypos = "0";
973 TString zpos = "0";
974 TString name = "";
975 TString tempattr;
976
977 while (attr != 0) {
978
979 tempattr = gdml->GetAttrName(attr);
980 tempattr.ToLower();
981
982 if (tempattr == "name") {
983 name = gdml->GetAttrValue(attr);
984 } else if (tempattr == "x") {
985 xpos = gdml->GetAttrValue(attr);
986 } else if (tempattr == "y") {
987 ypos = gdml->GetAttrValue(attr);
988 } else if (tempattr == "z") {
989 zpos = gdml->GetAttrValue(attr);
990 }
991
992 attr = gdml->GetNextAttr(attr);
993 }
994
995 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
996 name = TString::Format("%s_%s", name.Data(), fCurrentFile);
997 }
998
999 TGeoScale *scl = new TGeoScale(Value(xpos), Value(ypos), Value(zpos));
1000
1001 fsclmap[name.Data()] = scl;
1002
1003 return node;
1004}
1005
1006////////////////////////////////////////////////////////////////////////////////
1007/// In the material section of the GDML file, an isotope may be declared.
1008/// when the isotope keyword is found, this function is called, and the
1009/// required parameters are taken and stored, these are then bound and
1010/// converted to type TGeoIsotope and stored in fisomap map using the name
1011/// as its key.
1012
1014{
1015 TString z = "0";
1016 TString name = "";
1017 TString n = "0";
1018 TString atom = "0";
1019 TString tempattr;
1020
1021 // obtain attributes for the element
1022
1023 XMLAttrPointer_t attr = gdml->GetFirstAttr(parentn);
1024
1025 while (attr != 0) {
1026
1027 tempattr = gdml->GetAttrName(attr);
1028 tempattr.ToLower();
1029
1030 if (tempattr == "name") {
1031 name = gdml->GetAttrValue(attr);
1032 } else if (tempattr == "z") {
1033 z = gdml->GetAttrValue(attr);
1034 } else if (tempattr == "n") {
1035 n = gdml->GetAttrValue(attr);
1036 }
1037
1038 attr = gdml->GetNextAttr(attr);
1039 }
1040
1041 // get the atom value for the element
1042
1043 attr = gdml->GetFirstAttr(node);
1044
1045 while (attr != 0) {
1046
1047 tempattr = gdml->GetAttrName(attr);
1048
1049 if (tempattr == "value") {
1050 atom = gdml->GetAttrValue(attr);
1051 }
1052
1053 attr = gdml->GetNextAttr(attr);
1054 }
1055
1056 TString local_name = name;
1057 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1058 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
1059 }
1060
1061 Int_t z2 = (Int_t)Value(z);
1062 Int_t n2 = (Int_t)Value(n);
1063 Double_t atom2 = Value(atom);
1064
1065 TGeoManager *mgr = gGeoManager;
1066 TString iso_name = NameShort(name);
1067 TGeoElementTable *tab = mgr->GetElementTable();
1068 TGeoIsotope *iso = tab->FindIsotope(iso_name);
1069 if (!iso) {
1070 iso = new TGeoIsotope(iso_name, z2, n2, atom2);
1071 } else if (gDebug >= 2) {
1072 Info("TGDMLParse", "Re-use existing isotope: %s", iso->GetName());
1073 }
1074 fisomap[local_name.Data()] = iso;
1075
1076 return node;
1077}
1078
1079////////////////////////////////////////////////////////////////////////////////
1080/// When the element keyword is found, this function is called, and the
1081/// name and values of the element are converted into type TGeoElement and
1082/// stored in felemap map using the name as its key.
1083
1085 Bool_t hasIsotopes, Bool_t hasIsotopesExtended)
1086
1087{
1088 TString z = "0";
1089 TString name, local_name;
1090 TString formula = "";
1091 TString atom = "0";
1092 TString tempattr;
1093 Int_t ncompo = 0;
1094 TGeoManager *mgr = gGeoManager;
1095 TGeoElementTable *tab = mgr->GetElementTable();
1096 typedef FracMap::iterator fractions;
1097 FracMap fracmap;
1098
1100
1101 // obtain attributes for the element
1102
1103 XMLAttrPointer_t attr = gdml->GetFirstAttr(node);
1104
1105 if (hasIsotopes) {
1106
1107 // Get the name of the element
1108 while (attr != 0) {
1109 tempattr = gdml->GetAttrName(attr);
1110 if (tempattr == "name") {
1111 name = gdml->GetAttrValue(attr);
1112 local_name = name;
1113 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1114 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
1115 }
1116 break;
1117 }
1118 attr = gdml->GetNextAttr(attr);
1119 }
1120 // Get component isotopes. Loop all children.
1121 child = gdml->GetChild(node);
1122 while (child != 0) {
1123
1124 // Check for fraction node name
1125 if ((strcmp(gdml->GetNodeName(child), "fraction")) == 0) {
1126 Double_t n = 0;
1127 TString ref = "";
1128 ncompo = ncompo + 1;
1129 attr = gdml->GetFirstAttr(child);
1130 while (attr != 0) {
1131 tempattr = gdml->GetAttrName(attr);
1132 tempattr.ToLower();
1133 if (tempattr == "n") {
1134 n = Value(gdml->GetAttrValue(attr));
1135 } else if (tempattr == "ref") {
1136 ref = gdml->GetAttrValue(attr);
1137 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1138 ref = TString::Format("%s_%s", ref.Data(), fCurrentFile);
1139 }
1140 }
1141 attr = gdml->GetNextAttr(attr);
1142 } // loop on child attributes
1143 fracmap[ref.Data()] = n;
1144 }
1145 child = gdml->GetNext(child);
1146 } // loop on children
1147 // Create TGeoElement - note: Object(name, title) corresponds to Element(formula, name)
1148 TGeoElement *ele = tab->FindElement(NameShort(name));
1149 // We cannot use elements with Z = 0, so we expect a user definition
1150 if (ele && ele->Z() == 0)
1151 ele = nullptr;
1152 if (!ele)
1153 ele = new TGeoElement(NameShort(name), NameShort(name), ncompo);
1154 for (fractions f = fracmap.begin(); f != fracmap.end(); ++f) {
1155 if (fisomap.find(f->first) != fisomap.end()) {
1156 ele->AddIsotope((TGeoIsotope *)fisomap[f->first], f->second);
1157 }
1158 }
1159 felemap[local_name.Data()] = ele;
1160 return child;
1161 } // hasisotopes end loop
1162
1163 //*************************
1164
1165 if (hasIsotopesExtended) {
1166
1167 while (attr != 0) {
1168 tempattr = gdml->GetAttrName(attr);
1169
1170 if (tempattr == "name") {
1171 name = gdml->GetAttrValue(attr);
1172 local_name = name;
1173 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1174 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
1175 }
1176 break;
1177 }
1178 attr = gdml->GetNextAttr(attr);
1179 }
1180 // Get component isotopes. Loop all children.
1181 child = gdml->GetChild(node);
1182 while (child != 0) {
1183
1184 // Check for fraction node name
1185 if ((strcmp(gdml->GetNodeName(child), "fraction")) == 0) {
1186 Double_t n = 0;
1187 TString ref = "";
1188 ncompo = ncompo + 1;
1189 attr = gdml->GetFirstAttr(child);
1190 while (attr != 0) {
1191 tempattr = gdml->GetAttrName(attr);
1192 tempattr.ToLower();
1193 if (tempattr == "n") {
1194 n = Value(gdml->GetAttrValue(attr));
1195 } else if (tempattr == "ref") {
1196 ref = gdml->GetAttrValue(attr);
1197 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1198 ref = TString::Format("%s_%s", ref.Data(), fCurrentFile);
1199 }
1200 }
1201 attr = gdml->GetNextAttr(attr);
1202 } // loop on child attributes
1203 fracmap[ref.Data()] = n;
1204 }
1205 child = gdml->GetNext(child);
1206 } // loop on children
1207 // Create TGeoElement - note: Object(name, title) corresponds to Element(formula, name)
1208 TGeoElement *ele = tab->FindElement(NameShort(name));
1209 // We cannot use elements with Z = 0, so we expect a user definition
1210 if (ele && ele->Z() == 0)
1211 ele = nullptr;
1212 if (!ele)
1213 ele = new TGeoElement(NameShort(name), NameShort(name), ncompo);
1214 for (fractions f = fracmap.begin(); f != fracmap.end(); ++f) {
1215 if (fisomap.find(f->first) != fisomap.end()) {
1216 ele->AddIsotope((TGeoIsotope *)fisomap[f->first], f->second);
1217 }
1218 }
1219 felemap[local_name.Data()] = ele;
1220 return child;
1221 } // hasisotopesExtended end loop
1222
1223 //***************************
1224
1225 attr = gdml->GetFirstAttr(parentn);
1226 while (attr != 0) {
1227
1228 tempattr = gdml->GetAttrName(attr);
1229 tempattr.ToLower();
1230
1231 if (tempattr == "name") {
1232 name = gdml->GetAttrValue(attr);
1233
1234 } else if (tempattr == "z") {
1235 z = gdml->GetAttrValue(attr);
1236 } else if (tempattr == "formula") {
1237 formula = gdml->GetAttrValue(attr);
1238 }
1239
1240 attr = gdml->GetNextAttr(attr);
1241 }
1242
1243 // get the atom value for the element
1244
1245 attr = gdml->GetFirstAttr(node);
1246
1247 while (attr != 0) {
1248
1249 tempattr = gdml->GetAttrName(attr);
1250 tempattr.ToLower();
1251
1252 if (tempattr == "value") {
1253 atom = gdml->GetAttrValue(attr);
1254 }
1255
1256 attr = gdml->GetNextAttr(attr);
1257 }
1258
1259 local_name = name;
1260 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1261 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
1262 }
1263
1264 Int_t z2 = (Int_t)Value(z);
1265 Double_t atom2 = Value(atom);
1266 TGeoElement *ele = tab->FindElement(formula);
1267 // We cannot use elements with Z = 0, so we expect a user definition
1268 if (ele && ele->Z() == 0)
1269 ele = nullptr;
1270
1271 if (!ele) {
1272 ele = new TGeoElement(formula, NameShort(name), z2, atom2);
1273 } else if (gDebug >= 2) {
1274 Info("TGDMLParse", "Re-use existing element: %s", ele->GetName());
1275 }
1276 felemap[local_name.Data()] = ele;
1277 return node;
1278}
1279
1280////////////////////////////////////////////////////////////////////////////////
1281/// In the materials section of the GDML file, materials can be declared.
1282/// when the material keyword is found, this function is called, and the
1283/// name and values of the material are converted into type TGeoMaterial
1284/// and stored in fmatmap map using the name as its key. Mixtures can also
1285/// be declared, and they are converted to TGeoMixture and stored in
1286/// fmixmap. These mixtures and materials are then all converted into one
1287/// common type - TGeoMedium. The map fmedmap is then built up of all the
1288/// mixtures and materials.
1289
1291{
1292 //! Map to hold fractions while being processed
1293 typedef FracMap::iterator fractions;
1294 // typedef FracMap::iterator i;
1295 FracMap fracmap;
1296
1297 TGeoManager *mgr = gGeoManager;
1298 TGeoElementTable *tab_ele = mgr->GetElementTable();
1299 TList properties, constproperties;
1300 properties.SetOwner();
1301 constproperties.SetOwner();
1302 // We have to assume the media are monotonic increasing starting with 1
1303 static int medid = mgr->GetListOfMedia()->GetSize() + 1;
1304 XMLNodePointer_t child = gdml->GetChild(node);
1305 TString tempattr = "";
1306 Int_t ncompo = 0, mixflag = 2;
1307 Double_t density = 0;
1308 TString name, local_name;
1309 TGeoMixture *mix = 0;
1310 TGeoMaterial *mat = 0;
1311 TString tempconst = "";
1312 TString matname;
1313 Bool_t composite = kFALSE;
1314
1315 if (z == 1) {
1316 Double_t a = 0;
1317 Double_t d = 0;
1318
1319 name = gdml->GetAttr(node, "name");
1320 local_name = name;
1321 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1322 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
1323 }
1324
1325 while (child != 0) {
1326 attr = gdml->GetFirstAttr(child);
1327
1328 if ((strcmp(gdml->GetNodeName(child), "property")) == 0) {
1329 TNamed *property = new TNamed();
1330 while (attr != 0) {
1331 tempattr = gdml->GetAttrName(attr);
1332 tempattr.ToLower();
1333
1334 if (tempattr == "name") {
1335 property->SetName(gdml->GetAttrValue(attr));
1336 } else if (tempattr == "ref") {
1337 property->SetTitle(gdml->GetAttrValue(attr));
1338 TGDMLMatrix *matrix = fmatrices[property->GetTitle()];
1339 if (matrix)
1340 properties.Add(property);
1341 else {
1342 Bool_t error = 0;
1343 gGeoManager->GetProperty(property->GetTitle(), &error);
1344 if (error)
1345 Error("MatProcess", "Reference %s for material %s not found", property->GetTitle(),
1346 name.Data());
1347 else
1348 constproperties.Add(property);
1349 }
1350 }
1351 attr = gdml->GetNextAttr(attr);
1352 }
1353 }
1354
1355 if ((strcmp(gdml->GetNodeName(child), "atom")) == 0) {
1356 while (attr != 0) {
1357 tempattr = gdml->GetAttrName(attr);
1358 tempattr.ToLower();
1359
1360 if (tempattr == "value") {
1361 a = Value(gdml->GetAttrValue(attr));
1362 }
1363 attr = gdml->GetNextAttr(attr);
1364 }
1365 }
1366
1367 if ((strcmp(gdml->GetNodeName(child), "D")) == 0) {
1368 while (attr != 0) {
1369 tempattr = gdml->GetAttrName(attr);
1370 tempattr.ToLower();
1371
1372 if (tempattr == "value") {
1373 d = Value(gdml->GetAttrValue(attr));
1374 }
1375 attr = gdml->GetNextAttr(attr);
1376 }
1377 }
1378 child = gdml->GetNext(child);
1379 }
1380 // still in the is Z else...but not in the while..
1381 // CHECK FOR CONSTANTS
1382 tempconst = gdml->GetAttr(node, "Z");
1383
1384 Double_t valZ = Value(tempconst);
1385
1386 TString tmpname = name;
1387 // deal with special case - Z of vacuum is always 0
1388 tmpname.ToLower();
1389 if (tmpname == "vacuum") {
1390 valZ = 0;
1391 }
1392 TString mat_name = NameShort(name);
1393 mat = mgr->GetMaterial(mat_name);
1394 if (!mat) {
1395 mat = new TGeoMaterial(mat_name, a, valZ, d);
1396 } else {
1397 Info("TGDMLParse", "Re-use existing material: %s", mat->GetName());
1398 }
1399 if (properties.GetSize()) {
1401 TIter next(&properties);
1402 while ((property = (TNamed *)next()))
1403 mat->AddProperty(property->GetName(), property->GetTitle());
1404 }
1405 if (constproperties.GetSize()) {
1407 TIter next(&constproperties);
1408 while ((property = (TNamed *)next()))
1409 mat->AddConstProperty(property->GetName(), property->GetTitle());
1410 }
1411 mixflag = 0;
1412 // Note: Object(name, title) corresponds to Element(formula, name)
1413 TGeoElement *mat_ele = tab_ele->FindElement(mat_name);
1414 // We cannot use elements with Z = 0, so we expect a user definition
1415 if (mat_ele && mat_ele->Z() == 0)
1416 mat_ele = nullptr;
1417
1418 if (!mat_ele) {
1419 mat_ele = new TGeoElement(mat_name, mat_name, atoi(tempconst), a);
1420 } else if (gDebug >= 2) {
1421 Info("TGDMLParse", "Re-use existing material-element: %s", mat_ele->GetName());
1422 }
1423 felemap[local_name.Data()] = mat_ele;
1424 }
1425
1426 else if (z == 0) {
1427 while (child != 0) {
1428 attr = gdml->GetFirstAttr(child);
1429
1430 if ((strcmp(gdml->GetNodeName(child), "property")) == 0) {
1431 TNamed *property = new TNamed();
1432 while (attr != 0) {
1433 tempattr = gdml->GetAttrName(attr);
1434 tempattr.ToLower();
1435
1436 if (tempattr == "name") {
1437 property->SetName(gdml->GetAttrValue(attr));
1438 } else if (tempattr == "ref") {
1439 property->SetTitle(gdml->GetAttrValue(attr));
1440 TGDMLMatrix *matrix = fmatrices[property->GetTitle()];
1441 if (matrix)
1442 properties.Add(property);
1443 else {
1444 Bool_t error = 0;
1445 gGeoManager->GetProperty(property->GetTitle(), &error);
1446 if (error)
1447 Error("MatProcess", "Reference %s for material %s not found", property->GetTitle(),
1448 name.Data());
1449 else
1450 constproperties.Add(property);
1451 }
1452 }
1453 attr = gdml->GetNextAttr(attr);
1454 }
1455 }
1456 if ((strcmp(gdml->GetNodeName(child), "fraction")) == 0) {
1457 Double_t n = 0;
1458 TString ref = "";
1459 ncompo = ncompo + 1;
1460
1461 while (attr != 0) {
1462 tempattr = gdml->GetAttrName(attr);
1463 tempattr.ToLower();
1464
1465 if (tempattr == "n") {
1466 n = Value(gdml->GetAttrValue(attr));
1467 } else if (tempattr == "ref") {
1468 ref = gdml->GetAttrValue(attr);
1469 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1470 ref = TString::Format("%s_%s", ref.Data(), fCurrentFile);
1471 }
1472 }
1473 attr = gdml->GetNextAttr(attr);
1474 }
1475 fracmap[ref.Data()] = n;
1476 }
1477
1478 else if ((strcmp(gdml->GetNodeName(child), "composite")) == 0) {
1479 composite = kTRUE;
1480 Double_t n = 0;
1481 TString ref = "";
1482 ncompo = ncompo + 1;
1483
1484 while (attr != 0) {
1485 tempattr = gdml->GetAttrName(attr);
1486 tempattr.ToLower();
1487 if (tempattr == "n") {
1488 n = Value(gdml->GetAttrValue(attr));
1489 } else if (tempattr == "ref") {
1490 ref = gdml->GetAttrValue(attr);
1491 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1492 ref = TString::Format("%s_%s", ref.Data(), fCurrentFile);
1493 }
1494 }
1495 attr = gdml->GetNextAttr(attr);
1496 }
1497 fracmap[ref.Data()] = n;
1498 } else if ((strcmp(gdml->GetNodeName(child), "D")) == 0) {
1499 while (attr != 0) {
1500 tempattr = gdml->GetAttrName(attr);
1501 tempattr.ToLower();
1502
1503 if (tempattr == "value") {
1504 density = Value(gdml->GetAttrValue(attr));
1505 }
1506 attr = gdml->GetNextAttr(attr);
1507 }
1508 }
1509 child = gdml->GetNext(child);
1510 }
1511 // still in the not Z else...but not in the while..
1512
1513 name = gdml->GetAttr(node, "name");
1514 local_name = name;
1515 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1516 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
1517 }
1518 // mix = new TGeoMixture(NameShort(name), 0 /*ncompo*/, density);
1519 mixflag = 1;
1520 TString mat_name = NameShort(name);
1521 mat = mgr->GetMaterial(mat_name);
1522 if (!mat) {
1523 mix = new TGeoMixture(mat_name, ncompo, density);
1524 } else if (mat->IsMixture()) {
1525 mix = (TGeoMixture *)mat;
1526 if (gDebug >= 2)
1527 Info("TGDMLParse", "Re-use existing material-mixture: %s", mix->GetName());
1528 } else {
1529 Fatal("TGDMLParse", "WARNING! Inconsistent material definitions between GDML and TGeoManager");
1530 return child;
1531 }
1532 if (properties.GetSize()) {
1534 TIter next(&properties);
1535 while ((property = (TNamed *)next()))
1536 mix->AddProperty(property->GetName(), property->GetTitle());
1537 }
1538 if (constproperties.GetSize()) {
1540 TIter next(&constproperties);
1541 while ((property = (TNamed *)next()))
1542 mix->AddConstProperty(property->GetName(), property->GetTitle());
1543 }
1544 Int_t natoms;
1545 Double_t weight;
1546
1547 for (fractions f = fracmap.begin(); f != fracmap.end(); ++f) {
1548 matname = f->first;
1549 matname = NameShort(matname);
1550
1552
1553 if (mattmp || (felemap.find(f->first) != felemap.end())) {
1554 if (composite) {
1555 natoms = (Int_t)f->second;
1556
1557 mix->AddElement(felemap[f->first], natoms);
1558
1559 }
1560
1561 else {
1562 weight = f->second;
1563 if (mattmp) {
1564 mix->AddElement(mattmp, weight);
1565 } else {
1566 mix->AddElement(felemap[f->first], weight);
1567 }
1568 }
1569 }
1570 }
1571 } // end of not Z else
1572
1573 medid = medid + 1;
1574
1575 TGeoMedium *med = mgr->GetMedium(NameShort(name));
1576 if (!med) {
1577 if (mixflag == 1) {
1578 fmixmap[local_name.Data()] = mix;
1579 med = new TGeoMedium(NameShort(name), medid, mix);
1580 } else if (mixflag == 0) {
1581 fmatmap[local_name.Data()] = mat;
1582 med = new TGeoMedium(NameShort(name), medid, mat);
1583 }
1584 } else if (gDebug >= 2) {
1585 Info("TGDMLParse", "Re-use existing medium: %s", med->GetName());
1586 }
1587 fmedmap[local_name.Data()] = med;
1588
1589 return child;
1590}
1591
1592////////////////////////////////////////////////////////////////////////////////
1593/// In the structure section of the GDML file, skin surfaces can be declared.
1594
1596{
1597 TString name, surfname, volname;
1598 TString tempattr;
1599
1600 while (attr != 0) {
1601 tempattr = gdml->GetAttrName(attr);
1602 tempattr.ToLower();
1603
1604 if (tempattr == "name") {
1605 name = gdml->GetAttrValue(attr);
1606 }
1607 if (tempattr == "surfaceproperty") {
1608 surfname = gdml->GetAttrValue(attr);
1609 }
1610 attr = gdml->GetNextAttr(attr);
1611 }
1612
1613 XMLNodePointer_t child = gdml->GetChild(node);
1614 while (child != 0) {
1615 attr = gdml->GetFirstAttr(child);
1616 if ((strcmp(gdml->GetNodeName(child), "volumeref")) == 0) {
1617 while (attr != 0) {
1618 tempattr = gdml->GetAttrName(attr);
1619 tempattr.ToLower();
1620 if (tempattr == "ref") {
1621 volname = gdml->GetAttrValue(attr);
1622 }
1623 attr = gdml->GetNextAttr(attr);
1624 }
1625 } // loop on child attributes
1626 child = gdml->GetNext(child);
1627 } // loop on children
1629 if (!surf)
1630 Fatal("SkinSurfaceProcess", "Skin surface %s: referenced optical surface %s not defined", name.Data(),
1631 surfname.Data());
1632 TGeoVolume *vol = GetVolume(volname.Data());
1633 TGeoSkinSurface *skin = new TGeoSkinSurface(name, surfname, surf, vol);
1635 return child;
1636}
1637
1638////////////////////////////////////////////////////////////////////////////////
1639/// In the structure section of the GDML file, border surfaces can be declared.
1640
1642{
1643 TString name, surfname, nodename[2];
1644 TString tempattr;
1645
1646 while (attr != 0) {
1647 tempattr = gdml->GetAttrName(attr);
1648 tempattr.ToLower();
1649
1650 if (tempattr == "name") {
1651 name = gdml->GetAttrValue(attr);
1652 }
1653 if (tempattr == "surfaceproperty") {
1654 surfname = gdml->GetAttrValue(attr);
1655 }
1656 attr = gdml->GetNextAttr(attr);
1657 }
1658
1659 XMLNodePointer_t child = gdml->GetChild(node);
1660 Int_t inode = 0;
1661 while (child != 0) {
1662 attr = gdml->GetFirstAttr(child);
1663 if ((strcmp(gdml->GetNodeName(child), "physvolref")) == 0) {
1664 while (attr != 0) {
1665 tempattr = gdml->GetAttrName(attr);
1666 tempattr.ToLower();
1667 if (tempattr == "ref") {
1668 nodename[inode++] = gdml->GetAttrValue(attr);
1669 }
1670 attr = gdml->GetNextAttr(attr);
1671 }
1672 } // loop on child attributes
1673 child = gdml->GetNext(child);
1674 } // loop on children
1675 if (inode != 2)
1676 Fatal("BorderSurfaceProcess", "Border surface %s not referencing two nodes", name.Data());
1678 if (!surf)
1679 Fatal("BorderSurfaceProcess", "Border surface %s: referenced optical surface %s not defined", name.Data(),
1680 surfname.Data());
1681 TGeoNode *node1 = fpvolmap[nodename[0].Data()];
1682 TGeoNode *node2 = fpvolmap[nodename[1].Data()];
1683 if (!node1 || !node2)
1684 Fatal("BorderSurfaceProcess", "Border surface %s: not found nodes %s [%s] or %s [%s]", name.Data(),
1685 nodename[0].Data(), node1 ? "present" : "missing", nodename[1].Data(), node2 ? "present" : "missing");
1686
1687 TGeoBorderSurface *border = new TGeoBorderSurface(name, surfname, surf, node1, node2);
1689 return child;
1690}
1691
1693{
1694 // Get defined position by name, in local file scope.
1695 TGeoTranslation *pos = nullptr;
1696 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1697 // Search local file namespace first
1698 TString reftemp = TString::Format("%s_%s", name, fCurrentFile);
1699 if (fposmap.find(reftemp.Data()) != fposmap.end())
1700 pos = fposmap[reftemp.Data()];
1701 }
1702
1703 if (!pos && fposmap.find(name) != fposmap.end())
1704 pos = fposmap[name];
1705
1706 if (!pos)
1707 Error("GetPosition", "Position %s not defined", name);
1708 return pos;
1709}
1710
1712{
1713 // Get defined rotation by name.
1714 TGeoRotation *rot = nullptr;
1715 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1716 // Search local file namespace first
1717 TString reftemp = TString::Format("%s_%s", name, fCurrentFile);
1718 if (frotmap.find(reftemp.Data()) != frotmap.end())
1719 rot = frotmap[reftemp.Data()];
1720 }
1721
1722 if (!rot && frotmap.find(name) != frotmap.end())
1723 rot = frotmap[name];
1724
1725 if (!rot)
1726 Error("GetRotation", "Rotation %s not defined", name);
1727 return rot;
1728}
1729
1731{
1732 // Get defined scale by name.
1733 TGeoScale *scl = nullptr;
1734 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1735 // Search local file namespace first
1736 TString reftemp = TString::Format("%s_%s", name, fCurrentFile);
1737 if (fsclmap.find(reftemp.Data()) != fsclmap.end())
1738 scl = fsclmap[reftemp.Data()];
1739 }
1740
1741 if (!scl && fsclmap.find(name) != fsclmap.end())
1742 scl = fsclmap[name];
1743
1744 if (!scl)
1745 Error("GetScale", "Scale %s not defined", name);
1746 return scl;
1747}
1748
1750{
1751 // Get defined solid by name.
1752 TGeoShape *sol = nullptr;
1753 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1754 // Search local file namespace first
1755 TString reftemp = TString::Format("%s_%s", name, fCurrentFile);
1756 if (fsolmap.find(reftemp.Data()) != fsolmap.end())
1757 sol = fsolmap[reftemp.Data()];
1758 }
1759
1760 if (!sol && fsolmap.find(name) != fsolmap.end())
1761 sol = fsolmap[name];
1762
1763 if (!sol)
1764 Error("GetSolid", "Solid %s not defined", name);
1765 return sol;
1766}
1767
1769{
1770 // Get defined solid by name.
1771 TGeoVolume *vol = nullptr;
1772 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1773 // Search local file namespace first
1774 TString reftemp = TString::Format("%s_%s", name, fCurrentFile);
1775 if (fvolmap.find(reftemp.Data()) != fvolmap.end())
1776 vol = fvolmap[reftemp.Data()];
1777 }
1778
1779 if (!vol && fvolmap.find(name) != fvolmap.end())
1780 vol = fvolmap[name];
1781
1782 if (!vol)
1783 Error("GetVolume", "Volume %s not defined", name);
1784 return vol;
1785}
1786
1787////////////////////////////////////////////////////////////////////////////////
1788/// In the structure section of the GDML file, volumes can be declared.
1789/// when the volume keyword is found, this function is called, and the
1790/// name and values of the volume are converted into type TGeoVolume and
1791/// stored in fvolmap map using the name as its key. Volumes reference to
1792/// a solid declared higher up in the solids section of the GDML file.
1793/// Some volumes reference to other physical volumes to contain inside
1794/// that volume, declaring positions and rotations within that volume.
1795/// when each 'physvol' is declared, a matrix for its rotation and
1796/// translation is built and the 'physvol node' is added to the original
1797/// volume using TGeoVolume->AddNode.
1798/// volume division is also declared within the volume node, and once the
1799/// values for the division have been collected, using TGeoVolume->divide,
1800/// the division can be applied.
1801
1803{
1805 XMLNodePointer_t subchild;
1806 XMLNodePointer_t subsubchild;
1807
1808 XMLNodePointer_t child = gdml->GetChild(node);
1809 TString name;
1810 TString solidname = "";
1811 TString tempattr = "";
1812 TGeoShape *solid = 0;
1813 TGeoMedium *medium = 0;
1814 TGeoVolume *vol = 0;
1815 TGeoVolume *lv = 0;
1816 TGeoShape *reflex = 0;
1817 const Double_t *parentrot = 0;
1818 int yesrefl = 0;
1819 TString reftemp = "";
1820 TMap *auxmap = 0;
1821
1822 while (child != 0) {
1823 if ((strcmp(gdml->GetNodeName(child), "solidref")) == 0) {
1824
1825 reftemp = gdml->GetAttr(child, "ref");
1826 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1827 reftemp = TString::Format("%s_%s", reftemp.Data(), fCurrentFile);
1828 }
1829 if (fsolmap.find(reftemp.Data()) != fsolmap.end()) {
1830 solid = fsolmap[reftemp.Data()];
1831 } else if (freflectmap.find(reftemp.Data()) != freflectmap.end()) {
1832 solidname = reftemp;
1833 reflex = fsolmap[freflectmap[reftemp.Data()]];
1834 } else {
1835 printf("Solid: %s, Not Yet Defined!\n", reftemp.Data());
1836 }
1837 }
1838
1839 if ((strcmp(gdml->GetNodeName(child), "materialref")) == 0) {
1840 reftemp = gdml->GetAttr(child, "ref");
1841 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1842 reftemp = TString::Format("%s_%s", reftemp.Data(), fCurrentFile);
1843 }
1844 if (fmedmap.find(reftemp.Data()) != fmedmap.end()) {
1845 medium = fmedmap[reftemp.Data()];
1846 } else {
1847 printf("Medium: %s, Not Yet Defined!\n", gdml->GetAttr(child, "ref"));
1848 }
1849 }
1850
1851 child = gdml->GetNext(child);
1852 }
1853
1854 name = gdml->GetAttr(node, "name");
1855 TString local_name = name;
1856 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
1857 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
1858 }
1859
1860 if (reflex == 0) {
1861 vol = new TGeoVolume(NameShort(name), solid, medium);
1862 } else {
1863 vol = new TGeoVolume(NameShort(name), reflex, medium);
1864 freflvolmap[name.Data()] = solidname;
1865 TGDMLRefl *parentrefl = freflsolidmap[solidname.Data()];
1866 parentrot = parentrefl->GetMatrix()->GetRotationMatrix();
1867 yesrefl = 1;
1868 }
1869
1870 fvolmap[local_name.Data()] = vol;
1871
1872 // PHYSVOL - run through child nodes of VOLUME again..
1873
1874 child = gdml->GetChild(node);
1875
1876 while (child != 0) {
1877 if ((strcmp(gdml->GetNodeName(child), "physvol")) == 0) {
1878
1879 TString volref = "";
1880
1881 TGeoTranslation *pos = 0;
1882 TGeoRotation *rot = 0;
1883 TGeoScale *scl = 0;
1884 TString pnodename = gdml->GetAttr(child, "name");
1885 TString scopynum = gdml->GetAttr(child, "copynumber");
1886 Int_t copynum = (scopynum.IsNull()) ? 0 : (Int_t)Value(scopynum);
1887
1888 subchild = gdml->GetChild(child);
1889
1890 while (subchild != 0) {
1891 tempattr = gdml->GetNodeName(subchild);
1892 tempattr.ToLower();
1893
1894 if (tempattr == "volumeref") {
1895 reftemp = gdml->GetAttr(subchild, "ref");
1896 lv = GetVolume(reftemp.Data());
1897 volref = reftemp;
1898 } else if (tempattr == "file") {
1899 const char *filevol;
1900 const char *prevfile = fCurrentFile;
1901
1902 fCurrentFile = gdml->GetAttr(subchild, "name");
1903 filevol = gdml->GetAttr(subchild, "volname");
1904
1905 TXMLEngine *gdml2 = new TXMLEngine;
1906 gdml2->SetSkipComments(kTRUE);
1907 XMLDocPointer_t filedoc1 = gdml2->ParseFile(fCurrentFile);
1908 if (filedoc1 == 0) {
1909 Fatal("VolProcess", "Bad filename given %s", fCurrentFile);
1910 }
1911 // take access to main node
1912 XMLNodePointer_t mainnode2 = gdml2->DocGetRootElement(filedoc1);
1913 // increase depth counter + add DOM pointer
1914 fFILENO = fFILENO + 1;
1915 fFileEngine[fFILENO] = gdml2;
1916
1917 if (ffilemap.find(fCurrentFile) != ffilemap.end()) {
1918 volref = ffilemap[fCurrentFile];
1919 } else {
1920 volref = ParseGDML(gdml2, mainnode2);
1921 ffilemap[fCurrentFile] = volref;
1922 }
1923
1924 if (filevol) volref = filevol;
1925 lv = GetVolume(volref.Data());
1926
1927 fFILENO = fFILENO - 1;
1928 gdml = fFileEngine[fFILENO];
1929 fCurrentFile = prevfile;
1930
1931 // File tree complete - Release memory before exit
1932
1933 gdml->FreeDoc(filedoc1);
1934 delete gdml2;
1935 } else if (tempattr == "position") {
1936 attr = gdml->GetFirstAttr(subchild);
1937 PosProcess(gdml, subchild, attr);
1938 reftemp = gdml->GetAttr(subchild, "name");
1939 pos = GetPosition(reftemp.Data());
1940 } else if (tempattr == "positionref") {
1941 reftemp = gdml->GetAttr(subchild, "ref");
1942 pos = GetPosition(reftemp.Data());
1943 if (!pos)
1944 Fatal("VolProcess", "Physvol's position %s not found", reftemp.Data());
1945 } else if (tempattr == "rotation") {
1946 attr = gdml->GetFirstAttr(subchild);
1947 RotProcess(gdml, subchild, attr);
1948 reftemp = gdml->GetAttr(subchild, "name");
1949 rot = GetRotation(reftemp.Data());
1950 } else if (tempattr == "rotationref") {
1951 reftemp = gdml->GetAttr(subchild, "ref");
1952 rot = GetRotation(reftemp.Data());
1953 if (!rot)
1954 Fatal("VolProcess", "Physvol's rotation %s not found", reftemp.Data());
1955 } else if (tempattr == "scale") {
1956 attr = gdml->GetFirstAttr(subchild);
1957 SclProcess(gdml, subchild, attr);
1958 reftemp = gdml->GetAttr(subchild, "name");
1959 scl = GetScaleObj(reftemp.Data());
1960 } else if (tempattr == "scaleref") {
1961 reftemp = gdml->GetAttr(subchild, "ref");
1962 scl = GetScaleObj(reftemp.Data());
1963 if (!scl)
1964 Fatal("VolProcess", "Physvol's scale %s not found", reftemp.Data());
1965 }
1966
1967 subchild = gdml->GetNext(subchild);
1968 }
1969
1970 // ADD PHYSVOL TO GEOMETRY
1971 fVolID = fVolID + 1;
1972
1973 TGeoHMatrix *transform = new TGeoHMatrix();
1974
1975 if (pos != 0)
1976 transform->SetTranslation(pos->GetTranslation());
1977 if (rot != 0)
1978 transform->SetRotation(rot->GetRotationMatrix());
1979
1980 if (scl != 0) { // Scaling must be added to the rotation matrix!
1981
1982 Double_t scale3x3[9];
1983 memset(scale3x3, 0, 9 * sizeof(Double_t));
1984 const Double_t *diagonal = scl->GetScale();
1985
1986 scale3x3[0] = diagonal[0];
1987 scale3x3[4] = diagonal[1];
1988 scale3x3[8] = diagonal[2];
1989
1990 TGeoRotation scaleMatrix;
1991 scaleMatrix.SetMatrix(scale3x3);
1992 transform->Multiply(&scaleMatrix);
1993 }
1994
1995 // BEGIN: reflectedSolid. Remove lines between if reflectedSolid will be removed from GDML!!!
1996
1997 if (freflvolmap.find(volref.Data()) != freflvolmap.end()) {
1998 // if the volume is a reflected volume the matrix needs to be CHANGED
1999 TGDMLRefl *temprefl = freflsolidmap[freflvolmap[volref.Data()]];
2000 transform->Multiply(temprefl->GetMatrix());
2001 }
2002
2003 if (yesrefl == 1) {
2004 // reflection is done per solid so that we cancel it if exists in mother volume!!!
2005 TGeoRotation prot;
2006 prot.SetMatrix(parentrot);
2007 transform->MultiplyLeft(&prot);
2008 }
2009
2010 // END: reflectedSolid
2011
2012 vol->AddNode(lv, copynum, transform);
2013 TGeoNode *lastnode = (TGeoNode *)vol->GetNodes()->Last();
2014 if (!pnodename.IsNull())
2015 lastnode->SetName(pnodename);
2016 fpvolmap[lastnode->GetName()] = lastnode;
2017 } else if ((strcmp(gdml->GetNodeName(child), "divisionvol")) == 0) {
2018
2019 TString divVolref = "";
2020 Int_t axis = 0;
2021 TString number = "";
2022 TString width = "";
2023 TString offset = "";
2024 TString lunit = fDefault_lunit.c_str();
2025 bool unitless_l = true;
2026 reftemp = "";
2027 local_name = "";
2028
2029 attr = gdml->GetFirstAttr(child);
2030
2031 while (attr != 0) {
2032
2033 tempattr = gdml->GetAttrName(attr);
2034 tempattr.ToLower();
2035
2036 if (tempattr == "axis") {
2037 axis = SetAxis(gdml->GetAttrValue(attr));
2038 } else if (tempattr == "number") {
2039 number = gdml->GetAttrValue(attr);
2040 } else if (tempattr == "width") {
2041 width = gdml->GetAttrValue(attr);
2042 } else if (tempattr == "offset") {
2043 offset = gdml->GetAttrValue(attr);
2044 } else if (tempattr == "unit") {
2045 lunit = gdml->GetAttrValue(attr);
2046 unitless_l = false;
2047 }
2048
2049 attr = gdml->GetNextAttr(attr);
2050 }
2051
2052 subchild = gdml->GetChild(child);
2053
2054 while (subchild != 0) {
2055 tempattr = gdml->GetNodeName(subchild);
2056 tempattr.ToLower();
2057
2058 if (tempattr == "volumeref") {
2059 reftemp = gdml->GetAttr(subchild, "ref");
2060 local_name = reftemp;
2061 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
2062 local_name = TString::Format("%s_%s", reftemp.Data(), fCurrentFile);
2063 }
2064 divVolref = reftemp;
2065 }
2066
2067 subchild = gdml->GetNext(subchild);
2068 }
2069
2070 Double_t numberline = Value(number);
2071 Double_t retunit = GetScaleVal(lunit);
2072 fNunitless += int(unitless_l);
2073 Double_t step = Value(width) * retunit;
2074 Double_t offsetline = Value(offset) * retunit;
2075
2076 fVolID = fVolID + 1;
2077 Double_t xlo, xhi;
2078 vol->GetShape()->GetAxisRange(axis, xlo, xhi);
2079
2080 Int_t ndiv = (Int_t)numberline;
2081 Double_t start = xlo + offsetline;
2082
2083 Int_t numed = 0;
2084 TGeoVolume *old = GetVolume(reftemp);
2085 if (old) {
2086 // We need to recreate the content of the divided volume
2087 // medium id
2088 numed = old->GetMedium()->GetId();
2089 }
2090 TGeoVolume *divvol = vol->Divide(NameShort(reftemp), axis, ndiv, start, step, numed);
2091 if (!divvol) {
2092 Fatal("VolProcess", "Cannot divide volume %s", vol->GetName());
2093 return child;
2094 }
2095 if (old && old->GetNdaughters()) {
2096 divvol->ReplayCreation(old);
2097 }
2098 fvolmap[local_name.Data()] = divvol;
2099
2100 } // end of Division else if
2101
2102 else if ((strcmp(gdml->GetNodeName(child), "replicavol")) == 0) {
2103
2104 TString divVolref = "";
2105 Int_t axis = 0;
2106 TString number = "";
2107 TString width = "";
2108 TString offset = "";
2109 TString wunit = fDefault_lunit.c_str();
2110 TString ounit = fDefault_lunit.c_str();
2111 bool unitless_l = true;
2112 Double_t wvalue = 0;
2113 Double_t ovalue = 0;
2114 reftemp = "";
2115 local_name = "";
2116
2117 attr = gdml->GetFirstAttr(child);
2118
2119 while (attr != 0) {
2120
2121 tempattr = gdml->GetAttrName(attr);
2122 tempattr.ToLower();
2123
2124 if (tempattr == "number") {
2125 number = gdml->GetAttrValue(attr);
2126 }
2127 attr = gdml->GetNextAttr(attr);
2128 }
2129
2130 subchild = gdml->GetChild(child);
2131
2132 while (subchild != 0) {
2133 tempattr = gdml->GetNodeName(subchild);
2134 tempattr.ToLower();
2135
2136 if (tempattr == "volumeref") {
2137 reftemp = gdml->GetAttr(subchild, "ref");
2138 local_name = reftemp;
2139 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
2140 local_name = TString::Format("%s_%s", reftemp.Data(), fCurrentFile);
2141 }
2142 divVolref = reftemp;
2143 }
2144
2145 if (tempattr == "replicate_along_axis") {
2146 subsubchild = gdml->GetChild(subchild);
2147
2148 while (subsubchild != 0) {
2149 if ((strcmp(gdml->GetNodeName(subsubchild), "width")) == 0) {
2150 attr = gdml->GetFirstAttr(subsubchild);
2151 while (attr != 0) {
2152 tempattr = gdml->GetAttrName(attr);
2153 tempattr.ToLower();
2154 if (tempattr == "value") {
2155 wvalue = Value(gdml->GetAttrValue(attr));
2156 } else if (tempattr == "unit") {
2157 wunit = gdml->GetAttrValue(attr);
2158 unitless_l = false;
2159 }
2160
2161 attr = gdml->GetNextAttr(attr);
2162 }
2163 } else if ((strcmp(gdml->GetNodeName(subsubchild), "offset")) == 0) {
2164 attr = gdml->GetFirstAttr(subsubchild);
2165 while (attr != 0) {
2166 tempattr = gdml->GetAttrName(attr);
2167 tempattr.ToLower();
2168 if (tempattr == "value") {
2169 ovalue = Value(gdml->GetAttrValue(attr));
2170 } else if (tempattr == "unit") {
2171 ounit = gdml->GetAttrValue(attr);
2172 unitless_l = false;
2173 }
2174 attr = gdml->GetNextAttr(attr);
2175 }
2176 } else if ((strcmp(gdml->GetNodeName(subsubchild), "direction")) == 0) {
2177 attr = gdml->GetFirstAttr(subsubchild);
2178 while (attr != 0) {
2179 tempattr = gdml->GetAttrName(attr);
2180 tempattr.ToLower();
2181 if (tempattr == "x") {
2182 axis = 1;
2183 } else if (tempattr == "y") {
2184 axis = 2;
2185 } else if (tempattr == "z") {
2186 axis = 3;
2187 } else if (tempattr == "rho") {
2188 axis = 1;
2189 } else if (tempattr == "phi") {
2190 axis = 2;
2191 }
2192
2193 attr = gdml->GetNextAttr(attr);
2194 }
2195 }
2196
2197 subsubchild = gdml->GetNext(subsubchild);
2198 }
2199 }
2200
2201 subchild = gdml->GetNext(subchild);
2202 }
2203
2204 Double_t retwunit = GetScaleVal(wunit);
2205 Double_t retounit = GetScaleVal(ounit);
2206 fNunitless += int(unitless_l);
2207
2208 Double_t numberline = Value(number);
2209 Double_t widthline = wvalue * retwunit;
2210 Double_t offsetline = ovalue * retounit;
2211
2212 fVolID = fVolID + 1;
2213 Double_t xlo, xhi;
2214 vol->GetShape()->GetAxisRange(axis, xlo, xhi);
2215
2216 Int_t ndiv = (Int_t)numberline;
2217 Double_t start = xlo + offsetline;
2218
2219 Double_t step = widthline;
2220 Int_t numed = 0;
2221 TGeoVolume *old = GetVolume(reftemp);
2222 if (old) {
2223 // We need to recreate the content of the divided volume
2224 // medium id
2225 numed = old->GetMedium()->GetId();
2226 }
2227 TGeoVolume *divvol = vol->Divide(NameShort(reftemp), axis, ndiv, start, step, numed);
2228 if (!divvol) {
2229 Fatal("VolProcess", "Cannot divide volume %s", vol->GetName());
2230 return child;
2231 }
2232 if (old && old->GetNdaughters()) {
2233 divvol->ReplayCreation(old);
2234 }
2235 fvolmap[local_name.Data()] = divvol;
2236
2237 } // End of replicavol
2238 else if (strcmp(gdml->GetNodeName(child), "auxiliary") == 0) {
2239 TString auxType, auxUnit, auxValue;
2240 if (!auxmap) {
2241 // printf("Auxiliary values for volume %s\n",vol->GetName());
2242 auxmap = new TMap();
2243 vol->SetUserExtension(new TGeoRCExtension(auxmap));
2244 }
2245 attr = gdml->GetFirstAttr(child);
2246 while (attr) {
2247 if (!strcmp(gdml->GetAttrName(attr), "auxtype"))
2248 auxType = gdml->GetAttrValue(attr);
2249 else if (!strcmp(gdml->GetAttrName(attr), "auxvalue"))
2250 auxValue = gdml->GetAttrValue(attr);
2251 else if (!strcmp(gdml->GetAttrName(attr), "auxunit"))
2252 auxUnit = gdml->GetAttrValue(attr);
2253 attr = gdml->GetNextAttr(attr);
2254 }
2255 if (!auxUnit.IsNull())
2256 auxValue = TString::Format("%s*%s", auxValue.Data(), auxUnit.Data());
2257 auxmap->Add(new TObjString(auxType), new TObjString(auxValue));
2258 // printf(" %s: %s\n", auxType.Data(), auxValue.Data());
2259 }
2260
2261 child = gdml->GetNext(child);
2262 }
2263
2264 return child;
2265}
2266
2267////////////////////////////////////////////////////////////////////////////////
2268/// In the solid section of the GDML file, boolean solids can be
2269/// declared. when the subtraction, intersection or union keyword
2270/// is found, this function is called, and the values (rotation and
2271/// translation) of the solid are converted into type TGeoCompositeShape
2272/// and stored in fsolmap map using the name as its key.
2273///
2274/// - 1 = SUBTRACTION
2275/// - 2 = INTERSECTION
2276/// - 3 = UNION
2277
2279{
2280 TString reftemp = "";
2281 TString tempattr = "";
2282 XMLNodePointer_t child = gdml->GetChild(node);
2283
2284 TGeoShape *first = 0;
2285 TGeoShape *second = 0;
2286
2287 TGeoTranslation *firstPos = new TGeoTranslation(0, 0, 0);
2288 TGeoTranslation *secondPos = new TGeoTranslation(0, 0, 0);
2289
2290 TGeoRotation *firstRot = new TGeoRotation();
2291 TGeoRotation *secondRot = new TGeoRotation();
2292
2293 firstRot->RotateZ(0);
2294 firstRot->RotateY(0);
2295 firstRot->RotateX(0);
2296
2297 secondRot->RotateZ(0);
2298 secondRot->RotateY(0);
2299 secondRot->RotateX(0);
2300
2301 TString name = gdml->GetAttr(node, "name");
2302 TString local_name = name;
2303
2304 if ((strcmp(fCurrentFile, fStartFile)) != 0)
2305 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
2306
2307 while (child != 0) {
2308 tempattr = gdml->GetNodeName(child);
2309 tempattr.ToLower();
2310
2311 if (tempattr == "first") {
2312 reftemp = gdml->GetAttr(child, "ref");
2313 first = GetSolid(reftemp.Data());
2314 if (!first)
2315 Fatal("BooSolid", "First solid %s not found", reftemp.Data());
2316 } else if (tempattr == "second") {
2317 reftemp = gdml->GetAttr(child, "ref");
2318 second = GetSolid(reftemp.Data());
2319 if (!second)
2320 Fatal("BooSolid", "Second solid %s not found", reftemp.Data());
2321 } else if (tempattr == "position") {
2322 attr = gdml->GetFirstAttr(child);
2323 PosProcess(gdml, child, attr);
2324 reftemp = gdml->GetAttr(child, "name");
2325 secondPos = GetPosition(reftemp.Data());
2326 } else if (tempattr == "positionref") {
2327 reftemp = gdml->GetAttr(child, "ref");
2328 secondPos = GetPosition(reftemp.Data());
2329 if (!secondPos)
2330 Fatal("BooSolid", "Second position %s not found", reftemp.Data());
2331 } else if (tempattr == "rotation") {
2332 attr = gdml->GetFirstAttr(child);
2333 RotProcess(gdml, child, attr);
2334 reftemp = gdml->GetAttr(child, "name");
2335 secondRot = GetRotation(reftemp.Data());
2336 } else if (tempattr == "rotationref") {
2337 reftemp = gdml->GetAttr(child, "ref");
2338 secondRot = GetRotation(reftemp.Data());
2339 if (!secondRot)
2340 Fatal("BooSolid", "Second rotation %s not found", reftemp.Data());
2341 } else if (tempattr == "firstposition") {
2342 attr = gdml->GetFirstAttr(child);
2343 PosProcess(gdml, child, attr);
2344 reftemp = gdml->GetAttr(child, "name");
2345 firstPos = GetPosition(reftemp.Data());
2346 } else if (tempattr == "firstpositionref") {
2347 reftemp = gdml->GetAttr(child, "ref");
2348 firstPos = GetPosition(reftemp.Data());
2349 if (!firstPos)
2350 Fatal("BooSolid", "First position %s not found", reftemp.Data());
2351 } else if (tempattr == "firstrotation") {
2352 attr = gdml->GetFirstAttr(child);
2353 RotProcess(gdml, child, attr);
2354 reftemp = gdml->GetAttr(child, "name");
2355 firstRot = GetRotation(reftemp.Data());
2356 } else if (tempattr == "firstrotationref") {
2357 reftemp = gdml->GetAttr(child, "ref");
2358 firstRot = GetRotation(reftemp.Data());
2359 if (!firstRot)
2360 Fatal("BooSolid", "First rotation %s not found", reftemp.Data());
2361 }
2362 child = gdml->GetNext(child);
2363 }
2364
2365 TGeoMatrix *firstMatrix = new TGeoCombiTrans(*firstPos, firstRot->Inverse());
2366 TGeoMatrix *secondMatrix = new TGeoCombiTrans(*secondPos, secondRot->Inverse());
2367
2368 TGeoCompositeShape *boolean = 0;
2369 switch (num) {
2370 case 1:
2371 boolean = new TGeoCompositeShape(NameShort(name), new TGeoSubtraction(first, second, firstMatrix, secondMatrix));
2372 break; // SUBTRACTION
2373 case 2:
2374 boolean = new TGeoCompositeShape(NameShort(name), new TGeoIntersection(first, second, firstMatrix, secondMatrix));
2375 break; // INTERSECTION
2376 case 3:
2377 boolean = new TGeoCompositeShape(NameShort(name), new TGeoUnion(first, second, firstMatrix, secondMatrix));
2378 break; // UNION
2379 default: break;
2380 }
2381
2382 fsolmap[local_name.Data()] = boolean;
2383
2384 return child;
2385}
2386
2387////////////////////////////////////////////////////////////////////////////////
2388/// User data to be processed.
2389
2391{
2392 XMLNodePointer_t child = gdml->GetChild(node);
2393 TString nodename, auxtype, auxtypec, auxvalue, auxvaluec, auxunit, auxunitc;
2394 double value = 0.;
2395 TGeoRegion *region;
2396 while (child) {
2397 region = nullptr;
2398 nodename = gdml->GetNodeName(child);
2399 if (nodename == "auxiliary") {
2400 auxtype = gdml->GetAttr(child, "auxtype");
2401 auxvalue = gdml->GetAttr(child, "auxvalue");
2402 if (auxtype == "Region") {
2403 auxvalue = NameShort(auxvalue);
2404 region = new TGeoRegion(auxvalue);
2405 }
2406 }
2407 XMLNodePointer_t subchild = gdml->GetChild(child);
2408 while (subchild) {
2409 auxtypec = gdml->GetAttr(subchild, "auxtype");
2410 auxvaluec = gdml->GetAttr(subchild, "auxvalue");
2411 auxunitc = gdml->GetAttr(subchild, "auxunit");
2412 if (auxtypec == "volume") {
2413 auxvaluec = NameShort(auxvaluec);
2414 if (region)
2415 region->AddVolume(auxvaluec);
2416 }
2417 if (auxtypec.Contains("cut")) {
2418 value = Value(auxvaluec) * GetScaleVal(auxunitc);
2419 if (region)
2420 region->AddCut(auxtypec, value);
2421 }
2422 subchild = gdml->GetNext(subchild);
2423 }
2424 if (region) {
2425 gGeoManager->AddRegion(region);
2426 // region->Print();
2427 }
2428 child = gdml->GetNext(child);
2429 }
2430 return child;
2431}
2432
2433////////////////////////////////////////////////////////////////////////////////
2434/// In the structure section of the GDML file, assembly volumes can be
2435/// declared. when the assembly keyword is found, this function is called,
2436/// and the name is converted into type TGeoVolumeAssembly and
2437/// stored in fvolmap map using the name as its key. Some assembly volumes
2438/// reference to other physical volumes to contain inside that assembly,
2439/// declaring positions and rotations within that volume. When each 'physvol'
2440/// is declared, a matrix for its rotation and translation is built and the
2441/// 'physvol node' is added to the original assembly using TGeoVolume->AddNode.
2442
2444{
2445 TString name = gdml->GetAttr(node, "name");
2446 TString local_name = name;
2447 TString reftemp = "";
2448
2449 if ((strcmp(fCurrentFile, fStartFile)) != 0)
2450 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
2451
2453 XMLNodePointer_t subchild;
2454 XMLNodePointer_t child = gdml->GetChild(node);
2455 TString tempattr = "";
2456 TGeoVolume *lv = 0;
2457 TGeoTranslation *pos = 0;
2458 TGeoRotation *rot = 0;
2459 TGeoCombiTrans *matr;
2460
2462
2463 // PHYSVOL - run through child nodes of VOLUME again..
2464
2465 // child = gdml->GetChild(node);
2466
2467 while (child != 0) {
2468 if ((strcmp(gdml->GetNodeName(child), "physvol")) == 0) {
2469 TString pnodename = gdml->GetAttr(child, "name");
2470 TString scopynum = gdml->GetAttr(child, "copynumber");
2471 Int_t copynum = (scopynum.IsNull()) ? 0 : (Int_t)Value(scopynum);
2472
2473 subchild = gdml->GetChild(child);
2474 pos = new TGeoTranslation(0, 0, 0);
2475 rot = new TGeoRotation();
2476
2477 while (subchild != 0) {
2478 tempattr = gdml->GetNodeName(subchild);
2479 tempattr.ToLower();
2480
2481 if (tempattr == "volumeref") {
2482 reftemp = gdml->GetAttr(subchild, "ref");
2483 lv = GetVolume(reftemp.Data());
2484 } else if (tempattr == "positionref") {
2485 reftemp = gdml->GetAttr(subchild, "ref");
2486 pos = GetPosition(reftemp.Data());
2487 if (!pos)
2488 Fatal("AssProcess", "Position %s not found", reftemp.Data());
2489 } else if (tempattr == "position") {
2490 attr = gdml->GetFirstAttr(subchild);
2491 PosProcess(gdml, subchild, attr);
2492 reftemp = gdml->GetAttr(subchild, "name");
2493 pos = GetPosition(reftemp.Data());
2494 } else if (tempattr == "rotationref") {
2495 reftemp = gdml->GetAttr(subchild, "ref");
2496 rot = GetRotation(reftemp.Data());
2497 if (!rot)
2498 Fatal("AssProcess", "Rotation %s not found", reftemp.Data());
2499 } else if (tempattr == "rotation") {
2500 attr = gdml->GetFirstAttr(subchild);
2501 RotProcess(gdml, subchild, attr);
2502 reftemp = gdml->GetAttr(subchild, "name");
2503 rot = GetRotation(reftemp.Data());
2504 }
2505
2506 subchild = gdml->GetNext(subchild);
2507 }
2508
2509 // ADD PHYSVOL TO GEOMETRY
2510 fVolID = fVolID + 1;
2511 matr = new TGeoCombiTrans(*pos, *rot);
2512 assem->AddNode(lv, copynum, matr);
2513 TGeoNode *lastnode = (TGeoNode *)assem->GetNodes()->Last();
2514 if (!pnodename.IsNull())
2515 lastnode->SetName(pnodename);
2516 fpvolmap[lastnode->GetName()] = lastnode;
2517 }
2518 child = gdml->GetNext(child);
2519 }
2520
2521 fvolmap[local_name.Data()] = assem;
2522 return child;
2523}
2524
2525////////////////////////////////////////////////////////////////////////////////
2526/// In the setup section of the GDML file, the top volume need to be
2527/// declared. when the setup keyword is found, this function is called,
2528/// and the top volume ref is taken and 'world' is set
2529
2531{
2532 const char *name = gdml->GetAttr(node, "name");
2534 XMLNodePointer_t child = gdml->GetChild(node);
2535 TString reftemp = "";
2536
2537 while (child != 0) {
2538
2539 if ((strcmp(gdml->GetNodeName(child), "world") == 0)) {
2540 // const char* reftemp;
2541 // TString reftemp = "";
2542 reftemp = gdml->GetAttr(child, "ref");
2543 fWorld = GetVolume(reftemp.Data());
2544 fWorldName = reftemp.Data();
2545 }
2546 child = gdml->GetNext(child);
2547 }
2548 return node;
2549}
2550
2551////////////////////////////////////////////////////////////////////////////////
2552/// In the solids section of the GDML file, a box may be declared.
2553/// when the box keyword is found, this function is called, and the
2554/// dimensions required are taken and stored, these are then bound and
2555/// converted to type TGeoBBox and stored in fsolmap map using the name
2556/// as its key.
2557
2559{
2560 TString lunit = fDefault_lunit.c_str();
2561 bool unitless_l = true;
2562 TString xpos = "0";
2563 TString ypos = "0";
2564 TString zpos = "0";
2565 TString name = "";
2566 TString tempattr;
2567
2568 while (attr != 0) {
2569
2570 tempattr = gdml->GetAttrName(attr);
2571 tempattr.ToLower();
2572
2573 if (tempattr == "name") {
2574 name = gdml->GetAttrValue(attr);
2575 } else if (tempattr == "x") {
2576 xpos = gdml->GetAttrValue(attr);
2577 } else if (tempattr == "y") {
2578 ypos = gdml->GetAttrValue(attr);
2579 } else if (tempattr == "z") {
2580 zpos = gdml->GetAttrValue(attr);
2581 } else if (tempattr == "lunit") {
2582 lunit = gdml->GetAttrValue(attr);
2583 unitless_l = false;
2584 }
2585
2586 attr = gdml->GetNextAttr(attr);
2587 }
2588
2589 TString local_name = name;
2590 if ((strcmp(fCurrentFile, fStartFile)) != 0)
2591 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
2592
2593 Double_t retunit = GetScaleVal(lunit);
2594 fNunitless += int(unitless_l);
2595
2596 Double_t xline = 0.5 * Value(xpos) * retunit;
2597 Double_t yline = 0.5 * Value(ypos) * retunit;
2598 Double_t zline = 0.5 * Value(zpos) * retunit;
2599
2600 TGeoBBox *box = new TGeoBBox(NameShort(name), xline, yline, zline);
2601
2602 fsolmap[local_name.Data()] = box;
2603
2604 return node;
2605}
2606
2607////////////////////////////////////////////////////////////////////////////////
2608/// In the solids section of the GDML file, an ellipsoid may be declared.
2609/// Unfortunately, the ellipsoid is not supported under ROOT so,
2610/// when the ellipsoid keyword is found, this function is called
2611/// to convert it to a simple box with similar dimensions, and the
2612/// dimensions required are taken and stored, these are then bound and
2613/// converted to type TGeoBBox and stored in fsolmap map using the name
2614/// as its key.
2615
2617{
2618 TString lunit = fDefault_lunit.c_str();
2619 bool unitless_l = true;
2620 TString ax = "0";
2621 TString by = "0";
2622 TString cz = "0";
2623 // initialization to empty string
2624 TString zcut1 = "";
2625 TString zcut2 = "";
2626 TString name = "";
2627 TString tempattr;
2628
2629 while (attr != 0) {
2630
2631 tempattr = gdml->GetAttrName(attr);
2632 tempattr.ToLower();
2633
2634 if (tempattr == "name") {
2635 name = gdml->GetAttrValue(attr);
2636 } else if (tempattr == "ax") {
2637 ax = gdml->GetAttrValue(attr);
2638 } else if (tempattr == "by") {
2639 by = gdml->GetAttrValue(attr);
2640 } else if (tempattr == "cz") {
2641 cz = gdml->GetAttrValue(attr);
2642 } else if (tempattr == "zcut1") {
2643 zcut1 = gdml->GetAttrValue(attr);
2644 } else if (tempattr == "zcut2") {
2645 zcut2 = gdml->GetAttrValue(attr);
2646 } else if (tempattr == "lunit") {
2647 lunit = gdml->GetAttrValue(attr);
2648 unitless_l = false;
2649 }
2650
2651 attr = gdml->GetNextAttr(attr);
2652 }
2653
2654 TString local_name = name;
2655 if ((strcmp(fCurrentFile, fStartFile)) != 0)
2656 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
2657
2658 Double_t retunit = GetScaleVal(lunit);
2659 fNunitless += int(unitless_l);
2660
2661 Double_t dx = Value(ax) * retunit;
2662 Double_t dy = Value(by) * retunit;
2663 Double_t radius = Value(cz) * retunit;
2664 Double_t sx = dx / radius;
2665 Double_t sy = dy / radius;
2666 Double_t sz = 1.;
2667 Double_t z1, z2;
2668 // Initialization of cutting
2669 if (zcut1 == "") {
2670 z1 = -radius;
2671 } else {
2672 z1 = Value(zcut1) * retunit;
2673 }
2674 if (zcut2 == "") {
2675 z2 = radius;
2676 } else {
2677 z2 = Value(zcut2) * retunit;
2678 }
2679
2680 TGeoSphere *sph = new TGeoSphere(0, radius);
2681 TGeoScale *scl = new TGeoScale("", sx, sy, sz);
2682 TGeoScaledShape *shape = new TGeoScaledShape(NameShort(name), sph, scl);
2683
2684 Double_t origin[3] = {0., 0., 0.};
2685 origin[2] = 0.5 * (z1 + z2);
2686 Double_t dz = 0.5 * (z2 - z1);
2687 TGeoBBox *pCutBox = new TGeoBBox("cutBox", dx, dy, dz, origin);
2688 TGeoBoolNode *pBoolNode = new TGeoIntersection(shape, pCutBox, 0, 0);
2689 TGeoCompositeShape *cs = new TGeoCompositeShape(NameShort(name), pBoolNode);
2690 fsolmap[local_name.Data()] = cs;
2691
2692 return node;
2693}
2694
2695////////////////////////////////////////////////////////////////////////////////
2696/// In the solids section of the GDML file, an elliptical cone may be declared.
2697/// Unfortunately, the elliptical cone is not supported under ROOT so,
2698/// when the elcone keyword is found, this function is called
2699/// to convert it to a simple box with similar dimensions, and the
2700/// dimensions required are taken and stored, these are then bound and
2701/// converted to type TGeoBBox and stored in fsolmap map using the name
2702/// as its key.
2703
2705{
2706 TString lunit = fDefault_lunit.c_str();
2707 bool unitless_l = true;
2708 TString dx = "0";
2709 TString dy = "0";
2710 TString zmax = "0";
2711 TString zcut = "0";
2712 TString name = "";
2713 TString tempattr;
2714
2715 while (attr != 0) {
2716
2717 tempattr = gdml->GetAttrName(attr);
2718 tempattr.ToLower();
2719
2720 if (tempattr == "name") {
2721 name = gdml->GetAttrValue(attr);
2722 } else if (tempattr == "dx") {
2723 dx = gdml->GetAttrValue(attr);
2724 } else if (tempattr == "dy") {
2725 dy = gdml->GetAttrValue(attr);
2726 } else if (tempattr == "zmax") {
2727 zmax = gdml->GetAttrValue(attr);
2728 } else if (tempattr == "zcut") {
2729 zcut = gdml->GetAttrValue(attr);
2730 } else if (tempattr == "lunit") {
2731 lunit = gdml->GetAttrValue(attr);
2732 unitless_l = false;
2733 }
2734
2735 attr = gdml->GetNextAttr(attr);
2736 }
2737
2738 TString local_name = name;
2739 if ((strcmp(fCurrentFile, fStartFile)) != 0)
2740 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
2741
2742 // semiaxises of elliptical cone (elcone) are different then ellipsoid
2743
2744 Double_t retunit = GetScaleVal(lunit);
2745 fNunitless += int(unitless_l);
2746
2747 // dxline and dyline are without units because they are as a ration
2748 Double_t dxratio = Value(dx);
2749 Double_t dyratio = Value(dy);
2750 Double_t z = Value(zmax) * retunit;
2751 Double_t z1 = Value(zcut) * retunit;
2752
2753 if (z1 <= 0) {
2754 Info("ElCone", "ERROR! Parameter zcut = %.12g is not set properly, elcone will not be imported.", z1);
2755 return node;
2756 }
2757 if (z1 > z) {
2758 z1 = z;
2759 }
2760 Double_t rx1 = (z + z1) * dxratio;
2761 Double_t ry1 = (z + z1) * dyratio;
2762 Double_t rx2 = (z - z1) * dxratio;
2763 Double_t sx = 1.;
2764 Double_t sy = ry1 / rx1;
2765 Double_t sz = 1.;
2766
2767 TGeoCone *con = new TGeoCone(z1, 0, rx1, 0, rx2);
2768 TGeoScale *scl = new TGeoScale("", sx, sy, sz);
2769 TGeoScaledShape *shape = new TGeoScaledShape(NameShort(name), con, scl);
2770
2771 fsolmap[local_name.Data()] = shape;
2772
2773 return node;
2774}
2775
2776////////////////////////////////////////////////////////////////////////////////
2777/// In the solids section of the GDML file, a Paraboloid may be declared.
2778/// when the paraboloid keyword is found, this function is called, and the
2779/// dimensions required are taken and stored, these are then bound and
2780/// converted to type TGeoParaboloid and stored in fsolmap map using the name
2781/// as its key.
2782
2784{
2785 TString lunit = fDefault_lunit.c_str();
2786 bool unitless_l = true;
2787 TString rlopos = "0";
2788 TString rhipos = "0";
2789 TString dzpos = "0";
2790 TString name = "";
2791 TString tempattr;
2792
2793 while (attr != 0) {
2794
2795 tempattr = gdml->GetAttrName(attr);
2796 tempattr.ToLower();
2797
2798 if (tempattr == "name") {
2799 name = gdml->GetAttrValue(attr);
2800 } else if (tempattr == "rlo") {
2801 rlopos = gdml->GetAttrValue(attr);
2802 } else if (tempattr == "rhi") {
2803 rhipos = gdml->GetAttrValue(attr);
2804 } else if (tempattr == "dz") {
2805 dzpos = gdml->GetAttrValue(attr);
2806 } else if (tempattr == "lunit") {
2807 lunit = gdml->GetAttrValue(attr);
2808 unitless_l = false;
2809 }
2810
2811 attr = gdml->GetNextAttr(attr);
2812 }
2813
2814 TString local_name = name;
2815 if ((strcmp(fCurrentFile, fStartFile)) != 0)
2816 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
2817
2818 Double_t retunit = GetScaleVal(lunit);
2819 fNunitless += int(unitless_l);
2820
2821 Double_t rlo = Value(rlopos) * retunit;
2822 Double_t rhi = Value(rhipos) * retunit;
2823 Double_t dz = Value(dzpos) * retunit;
2824
2825 TGeoParaboloid *paraboloid = new TGeoParaboloid(NameShort(name), rlo, rhi, dz);
2826
2827 fsolmap[local_name.Data()] = paraboloid;
2828
2829 return node;
2830}
2831
2832////////////////////////////////////////////////////////////////////////////////
2833/// In the solids section of the GDML file, an Arb8 may be declared.
2834/// when the arb8 keyword is found, this function is called, and the
2835/// dimensions required are taken and stored, these are then bound and
2836/// converted to type TGeoArb8 and stored in fsolmap map using the name
2837/// as its key.
2838
2840{
2841 TString lunit = fDefault_lunit.c_str();
2842 bool unitless_l = true;
2843 TString v1xpos = "0";
2844 TString v1ypos = "0";
2845 TString v2xpos = "0";
2846 TString v2ypos = "0";
2847 TString v3xpos = "0";
2848 TString v3ypos = "0";
2849 TString v4xpos = "0";
2850 TString v4ypos = "0";
2851 TString v5xpos = "0";
2852 TString v5ypos = "0";
2853 TString v6xpos = "0";
2854 TString v6ypos = "0";
2855 TString v7xpos = "0";
2856 TString v7ypos = "0";
2857 TString v8xpos = "0";
2858 TString v8ypos = "0";
2859 TString dzpos = "0";
2860 TString name = "";
2861 TString tempattr;
2862
2863 while (attr != 0) {
2864
2865 tempattr = gdml->GetAttrName(attr);
2866 tempattr.ToLower();
2867
2868 if (tempattr == "name") {
2869 name = gdml->GetAttrValue(attr);
2870 } else if (tempattr == "v1x") {
2871 v1xpos = gdml->GetAttrValue(attr);
2872 } else if (tempattr == "v1y") {
2873 v1ypos = gdml->GetAttrValue(attr);
2874 } else if (tempattr == "v2x") {
2875 v2xpos = gdml->GetAttrValue(attr);
2876 } else if (tempattr == "v2y") {
2877 v2ypos = gdml->GetAttrValue(attr);
2878 } else if (tempattr == "v3x") {
2879 v3xpos = gdml->GetAttrValue(attr);
2880 } else if (tempattr == "v3y") {
2881 v3ypos = gdml->GetAttrValue(attr);
2882 } else if (tempattr == "v4x") {
2883 v4xpos = gdml->GetAttrValue(attr);
2884 } else if (tempattr == "v4y") {
2885 v4ypos = gdml->GetAttrValue(attr);
2886 } else if (tempattr == "v5x") {
2887 v5xpos = gdml->GetAttrValue(attr);
2888 } else if (tempattr == "v5y") {
2889 v5ypos = gdml->GetAttrValue(attr);
2890 } else if (tempattr == "v6x") {
2891 v6xpos = gdml->GetAttrValue(attr);
2892 } else if (tempattr == "v6y") {
2893 v6ypos = gdml->GetAttrValue(attr);
2894 } else if (tempattr == "v7x") {
2895 v7xpos = gdml->GetAttrValue(attr);
2896 } else if (tempattr == "v7y") {
2897 v7ypos = gdml->GetAttrValue(attr);
2898 } else if (tempattr == "v8x") {
2899 v8xpos = gdml->GetAttrValue(attr);
2900 } else if (tempattr == "v8y") {
2901 v8ypos = gdml->GetAttrValue(attr);
2902 } else if (tempattr == "dz") {
2903 dzpos = gdml->GetAttrValue(attr);
2904 } else if (tempattr == "lunit") {
2905 lunit = gdml->GetAttrValue(attr);
2906 unitless_l = false;
2907 }
2908
2909 attr = gdml->GetNextAttr(attr);
2910 }
2911
2912 TString local_name = name;
2913 if ((strcmp(fCurrentFile, fStartFile)) != 0)
2914 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
2915
2916 Double_t retunit = GetScaleVal(lunit);
2917 fNunitless += int(unitless_l);
2918
2919 Double_t v1x = Value(v1xpos) * retunit;
2920 Double_t v1y = Value(v1ypos) * retunit;
2921 Double_t v2x = Value(v2xpos) * retunit;
2922 Double_t v2y = Value(v2ypos) * retunit;
2923 Double_t v3x = Value(v3xpos) * retunit;
2924 Double_t v3y = Value(v3ypos) * retunit;
2925 Double_t v4x = Value(v4xpos) * retunit;
2926 Double_t v4y = Value(v4ypos) * retunit;
2927 Double_t v5x = Value(v5xpos) * retunit;
2928 Double_t v5y = Value(v5ypos) * retunit;
2929 Double_t v6x = Value(v6xpos) * retunit;
2930 Double_t v6y = Value(v6ypos) * retunit;
2931 Double_t v7x = Value(v7xpos) * retunit;
2932 Double_t v7y = Value(v7ypos) * retunit;
2933 Double_t v8x = Value(v8xpos) * retunit;
2934 Double_t v8y = Value(v8ypos) * retunit;
2935 Double_t dz = Value(dzpos) * retunit;
2936
2937 TGeoArb8 *arb8 = new TGeoArb8(NameShort(name), dz);
2938
2939 arb8->SetVertex(0, v1x, v1y);
2940 arb8->SetVertex(1, v2x, v2y);
2941 arb8->SetVertex(2, v3x, v3y);
2942 arb8->SetVertex(3, v4x, v4y);
2943 arb8->SetVertex(4, v5x, v5y);
2944 arb8->SetVertex(5, v6x, v6y);
2945 arb8->SetVertex(6, v7x, v7y);
2946 arb8->SetVertex(7, v8x, v8y);
2947
2948 fsolmap[local_name.Data()] = arb8;
2949
2950 return node;
2951}
2952
2953////////////////////////////////////////////////////////////////////////////////
2954/// In the solids section of the GDML file, a Tube may be declared.
2955/// when the tube keyword is found, this function is called, and the
2956/// dimensions required are taken and stored, these are then bound and
2957/// converted to type TGeoTubeSeg and stored in fsolmap map using the name
2958/// as its key.
2959
2961{
2962 TString lunit = fDefault_lunit.c_str();
2963 TString aunit = fDefault_aunit.c_str();
2964 bool unitless_l = true;
2965 bool unitless_a = true;
2966 TString rmin = "0";
2967 TString rmax = "0";
2968 TString z = "0";
2969 TString startphi = "0";
2970 TString deltaphi = "0";
2971 TString name = "";
2972 TString tempattr;
2973
2974 while (attr != 0) {
2975
2976 tempattr = gdml->GetAttrName(attr);
2977 tempattr.ToLower();
2978
2979 if (tempattr == "name") {
2980 name = gdml->GetAttrValue(attr);
2981 } else if (tempattr == "rmin") {
2982 rmin = gdml->GetAttrValue(attr);
2983 } else if (tempattr == "rmax") {
2984 rmax = gdml->GetAttrValue(attr);
2985 } else if (tempattr == "z") {
2986 z = gdml->GetAttrValue(attr);
2987 } else if (tempattr == "lunit") {
2988 lunit = gdml->GetAttrValue(attr);
2989 unitless_l = false;
2990 } else if (tempattr == "aunit") {
2991 aunit = gdml->GetAttrValue(attr);
2992 unitless_a = false;
2993 } else if (tempattr == "startphi") {
2994 startphi = gdml->GetAttrValue(attr);
2995 } else if (tempattr == "deltaphi") {
2996 deltaphi = gdml->GetAttrValue(attr);
2997 }
2998
2999 attr = gdml->GetNextAttr(attr);
3000 }
3001
3002 TString local_name = name;
3003 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3004 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3005
3006 Double_t retlunit = GetScaleVal(lunit);
3007 Double_t retaunit = GetScaleVal(aunit);
3008 fNunitless += int(unitless_l || unitless_a);
3009
3010 Double_t rminline = Value(rmin) * retlunit;
3011 Double_t rmaxline = Value(rmax) * retlunit;
3012 Double_t zline = Value(z) * retlunit;
3013 Double_t startphideg = Value(startphi) * retaunit;
3014 Double_t deltaphideg = Value(deltaphi) * retaunit;
3015 Double_t endphideg = startphideg + deltaphideg;
3016
3017 TGeoShape *tube = 0;
3018 if (deltaphideg < 360.)
3019 tube = new TGeoTubeSeg(NameShort(name), rminline, rmaxline, zline / 2, startphideg, endphideg);
3020 else
3021 tube = new TGeoTube(NameShort(name), rminline, rmaxline, zline / 2);
3022 fsolmap[local_name.Data()] = tube;
3023
3024 return node;
3025}
3026
3027////////////////////////////////////////////////////////////////////////////////
3028/// In the solids section of the GDML file, a Cut Tube may be declared.
3029/// when the cutTube keyword is found, this function is called, and the
3030/// dimensions required are taken and stored, these are then bound and
3031/// converted to type TGeoCtub and stored in fsolmap map using the name
3032/// as its key.
3033
3035{
3036 TString lunit = fDefault_lunit.c_str();
3037 TString aunit = fDefault_aunit.c_str();
3038 bool unitless_l = true;
3039 bool unitless_a = true;
3040 TString rmin = "0";
3041 TString rmax = "0";
3042 TString z = "0";
3043 TString startphi = "0";
3044 TString deltaphi = "0";
3045 TString lowX = "0";
3046 TString lowY = "0";
3047 TString lowZ = "0";
3048 TString highX = "0";
3049 TString highY = "0";
3050 TString highZ = "0";
3051 TString name = "";
3052 TString tempattr;
3053
3054 while (attr != 0) {
3055
3056 tempattr = gdml->GetAttrName(attr);
3057 tempattr.ToLower();
3058
3059 if (tempattr == "name") {
3060 name = gdml->GetAttrValue(attr);
3061 } else if (tempattr == "rmin") {
3062 rmin = gdml->GetAttrValue(attr);
3063 } else if (tempattr == "rmax") {
3064 rmax = gdml->GetAttrValue(attr);
3065 } else if (tempattr == "z") {
3066 z = gdml->GetAttrValue(attr);
3067 } else if (tempattr == "lunit") {
3068 lunit = gdml->GetAttrValue(attr);
3069 unitless_l = false;
3070 } else if (tempattr == "aunit") {
3071 aunit = gdml->GetAttrValue(attr);
3072 unitless_a = false;
3073 } else if (tempattr == "startphi") {
3074 startphi = gdml->GetAttrValue(attr);
3075 } else if (tempattr == "deltaphi") {
3076 deltaphi = gdml->GetAttrValue(attr);
3077 } else if (tempattr == "lowx") {
3078 lowX = gdml->GetAttrValue(attr);
3079 } else if (tempattr == "lowy") {
3080 lowY = gdml->GetAttrValue(attr);
3081 } else if (tempattr == "lowz") {
3082 lowZ = gdml->GetAttrValue(attr);
3083 } else if (tempattr == "highx") {
3084 highX = gdml->GetAttrValue(attr);
3085 } else if (tempattr == "highy") {
3086 highY = gdml->GetAttrValue(attr);
3087 } else if (tempattr == "highz") {
3088 highZ = gdml->GetAttrValue(attr);
3089 }
3090
3091 attr = gdml->GetNextAttr(attr);
3092 }
3093
3094 TString local_name = name;
3095 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3096 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3097
3098 Double_t retlunit = GetScaleVal(lunit);
3099 Double_t retaunit = GetScaleVal(aunit);
3100 fNunitless += int(unitless_l || unitless_a);
3101
3102 Double_t rminline = Value(rmin) * retlunit;
3103 Double_t rmaxline = Value(rmax) * retlunit;
3104 Double_t zline = Value(z) * retlunit;
3105 Double_t startphiline = Value(startphi) * retaunit;
3106 Double_t deltaphiline = Value(deltaphi) * retaunit + startphiline;
3107 Double_t lowXline = Value(lowX) * retlunit;
3108 Double_t lowYline = Value(lowY) * retlunit;
3109 Double_t lowZline = Value(lowZ) * retlunit;
3110 Double_t highXline = Value(highX) * retlunit;
3111 Double_t highYline = Value(highY) * retlunit;
3112 Double_t highZline = Value(highZ) * retlunit;
3113
3114 TGeoCtub *cuttube = new TGeoCtub(NameShort(name), rminline, rmaxline, zline / 2, startphiline, deltaphiline,
3115 lowXline, lowYline, lowZline, highXline, highYline, highZline);
3116
3117 fsolmap[local_name.Data()] = cuttube;
3118
3119 return node;
3120}
3121
3122////////////////////////////////////////////////////////////////////////////////
3123/// In the solids section of the GDML file, a cone may be declared.
3124/// when the cone keyword is found, this function is called, and the
3125/// dimensions required are taken and stored, these are then bound and
3126/// converted to type TGeoConSeg and stored in fsolmap map using the name
3127/// as its key.
3128
3130{
3131 TString lunit = fDefault_lunit.c_str();
3132 TString aunit = fDefault_aunit.c_str();
3133 bool unitless_l = true;
3134 bool unitless_a = true;
3135 TString rmin1 = "0";
3136 TString rmax1 = "0";
3137 TString rmin2 = "0";
3138 TString rmax2 = "0";
3139 TString z = "0";
3140 TString startphi = "0";
3141 TString deltaphi = "0";
3142 TString name = "";
3143 TString tempattr;
3144
3145 while (attr != 0) {
3146
3147 tempattr = gdml->GetAttrName(attr);
3148 tempattr.ToLower();
3149
3150 if (tempattr == "name") {
3151 name = gdml->GetAttrValue(attr);
3152 } else if (tempattr == "rmin1") {
3153 rmin1 = gdml->GetAttrValue(attr);
3154 } else if (tempattr == "rmax1") {
3155 rmax1 = gdml->GetAttrValue(attr);
3156 } else if (tempattr == "rmin2") {
3157 rmin2 = gdml->GetAttrValue(attr);
3158 } else if (tempattr == "rmax2") {
3159 rmax2 = gdml->GetAttrValue(attr);
3160 } else if (tempattr == "z") {
3161 z = gdml->GetAttrValue(attr);
3162 } else if (tempattr == "lunit") {
3163 lunit = gdml->GetAttrValue(attr);
3164 unitless_l = false;
3165 } else if (tempattr == "aunit") {
3166 aunit = gdml->GetAttrValue(attr);
3167 unitless_a = false;
3168 } else if (tempattr == "startphi") {
3169 startphi = gdml->GetAttrValue(attr);
3170 } else if (tempattr == "deltaphi") {
3171 deltaphi = gdml->GetAttrValue(attr);
3172 }
3173
3174 attr = gdml->GetNextAttr(attr);
3175 }
3176
3177 TString local_name = name;
3178 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3179 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3180
3181 Double_t retlunit = GetScaleVal(lunit);
3182 Double_t retaunit = GetScaleVal(aunit);
3183 fNunitless += int(unitless_l || unitless_a);
3184
3185 Double_t rmin1line = Value(rmin1) * retlunit;
3186 Double_t rmax1line = Value(rmax1) * retlunit;
3187 Double_t rmin2line = Value(rmin2) * retlunit;
3188 Double_t rmax2line = Value(rmax2) * retlunit;
3189 Double_t zline = Value(z) * retlunit;
3190 Double_t sphi = Value(startphi) * retaunit;
3191 Double_t dphi = Value(deltaphi) * retaunit;
3192 Double_t ephi = sphi + dphi;
3193
3194 TGeoShape *cone = 0;
3195 if (dphi < 360.)
3196 cone = new TGeoConeSeg(NameShort(name), zline / 2, rmin1line, rmax1line, rmin2line, rmax2line, sphi, ephi);
3197 else
3198 cone = new TGeoCone(NameShort(name), zline / 2, rmin1line, rmax1line, rmin2line, rmax2line);
3199
3200 fsolmap[local_name.Data()] = cone;
3201
3202 return node;
3203}
3204
3205////////////////////////////////////////////////////////////////////////////////
3206/// In the solids section of the GDML file, a Trap may be declared.
3207/// when the trap keyword is found, this function is called, and the
3208/// dimensions required are taken and stored, these are then bound and
3209/// converted to type TGeoTrap and stored in fsolmap map using the name
3210/// as its key.
3211
3213{
3214 TString lunit = fDefault_lunit.c_str();
3215 TString aunit = fDefault_aunit.c_str();
3216 bool unitless_l = true;
3217 bool unitless_a = true;
3218 TString x1 = "0";
3219 TString x2 = "0";
3220 TString x3 = "0";
3221 TString x4 = "0";
3222 TString y1 = "0";
3223 TString y2 = "0";
3224 TString z = "0";
3225 TString phi = "0";
3226 TString theta = "0";
3227 TString alpha1 = "0";
3228 TString alpha2 = "0";
3229 TString name = "";
3230 TString tempattr;
3231
3232 while (attr != 0) {
3233
3234 tempattr = gdml->GetAttrName(attr);
3235 tempattr.ToLower();
3236
3237 if (tempattr == "name") {
3238 name = gdml->GetAttrValue(attr);
3239 } else if (tempattr == "x1") {
3240 x1 = gdml->GetAttrValue(attr);
3241 } else if (tempattr == "x2") {
3242 x2 = gdml->GetAttrValue(attr);
3243 } else if (tempattr == "x3") {
3244 x3 = gdml->GetAttrValue(attr);
3245 } else if (tempattr == "x4") {
3246 x4 = gdml->GetAttrValue(attr);
3247 } else if (tempattr == "y1") {
3248 y1 = gdml->GetAttrValue(attr);
3249 } else if (tempattr == "y2") {
3250 y2 = gdml->GetAttrValue(attr);
3251 } else if (tempattr == "z") {
3252 z = gdml->GetAttrValue(attr);
3253 } else if (tempattr == "lunit") {
3254 lunit = gdml->GetAttrValue(attr);
3255 unitless_l = false;
3256 } else if (tempattr == "aunit") {
3257 aunit = gdml->GetAttrValue(attr);
3258 unitless_a = false;
3259 } else if (tempattr == "phi") {
3260 phi = gdml->GetAttrValue(attr);
3261 } else if (tempattr == "theta") {
3262 theta = gdml->GetAttrValue(attr);
3263 } else if (tempattr == "alpha1") {
3264 alpha1 = gdml->GetAttrValue(attr);
3265 } else if (tempattr == "alpha2") {
3266 alpha2 = gdml->GetAttrValue(attr);
3267 }
3268
3269 attr = gdml->GetNextAttr(attr);
3270 }
3271
3272 TString local_name = name;
3273 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3274 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3275
3276 Double_t retlunit = GetScaleVal(lunit);
3277 Double_t retaunit = GetScaleVal(aunit);
3278 fNunitless += int(unitless_l || unitless_a);
3279
3280 Double_t x1line = Value(x1) * retlunit;
3281 Double_t x2line = Value(x2) * retlunit;
3282 Double_t x3line = Value(x3) * retlunit;
3283 Double_t x4line = Value(x4) * retlunit;
3284 Double_t y1line = Value(y1) * retlunit;
3285 Double_t y2line = Value(y2) * retlunit;
3286 Double_t zline = Value(z) * retlunit;
3287 Double_t philine = Value(phi) * retaunit;
3288 Double_t thetaline = Value(theta) * retaunit;
3289 Double_t alpha1line = Value(alpha1) * retaunit;
3290 Double_t alpha2line = Value(alpha2) * retaunit;
3291
3292 TGeoTrap *trap = new TGeoTrap(NameShort(name), zline / 2, thetaline, philine, y1line / 2, x1line / 2, x2line / 2,
3293 alpha1line, y2line / 2, x3line / 2, x4line / 2, alpha2line);
3294
3295 fsolmap[local_name.Data()] = trap;
3296
3297 return node;
3298}
3299
3300////////////////////////////////////////////////////////////////////////////////
3301/// In the solids section of the GDML file, a Trd may be declared.
3302/// when the trd keyword is found, this function is called, and the
3303/// dimensions required are taken and stored, these are then bound and
3304/// converted to type TGeoTrd2 and stored in fsolmap map using the name
3305/// as its key.
3306
3308{
3309 TString lunit = fDefault_lunit.c_str();
3310 bool unitless_l = true;
3311 TString x1 = "0";
3312 TString x2 = "0";
3313 TString y1 = "0";
3314 TString y2 = "0";
3315 TString z = "0";
3316 TString name = "";
3317 TString tempattr;
3318
3319 while (attr != 0) {
3320
3321 tempattr = gdml->GetAttrName(attr);
3322 tempattr.ToLower();
3323
3324 if (tempattr == "name") {
3325 name = gdml->GetAttrValue(attr);
3326 } else if (tempattr == "x1") {
3327 x1 = gdml->GetAttrValue(attr);
3328 } else if (tempattr == "x2") {
3329 x2 = gdml->GetAttrValue(attr);
3330 } else if (tempattr == "y1") {
3331 y1 = gdml->GetAttrValue(attr);
3332 } else if (tempattr == "y2") {
3333 y2 = gdml->GetAttrValue(attr);
3334 } else if (tempattr == "z") {
3335 z = gdml->GetAttrValue(attr);
3336 } else if (tempattr == "lunit") {
3337 lunit = gdml->GetAttrValue(attr);
3338 unitless_l = false;
3339 }
3340
3341 attr = gdml->GetNextAttr(attr);
3342 }
3343
3344 TString local_name = name;
3345 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3346 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3347
3348 Double_t retlunit = GetScaleVal(lunit);
3349 fNunitless += int(unitless_l);
3350
3351 Double_t x1line = Value(x1) * retlunit;
3352 Double_t x2line = Value(x2) * retlunit;
3353 Double_t y1line = Value(y1) * retlunit;
3354 Double_t y2line = Value(y2) * retlunit;
3355 Double_t zline = Value(z) * retlunit;
3356
3357 TGeoTrd2 *trd = new TGeoTrd2(NameShort(name), x1line / 2, x2line / 2, y1line / 2, y2line / 2, zline / 2);
3358
3359 fsolmap[local_name.Data()] = trd;
3360
3361 return node;
3362}
3363
3364////////////////////////////////////////////////////////////////////////////////
3365/// In the solids section of the GDML file, a Polycone may be declared.
3366/// when the polycone keyword is found, this function is called, and the
3367/// dimensions required are taken and stored, these are then bound and
3368/// converted to type TGeoPCon and stored in fsolmap map using the name
3369/// as its key. Polycone has Zplanes, planes along the z axis specifying
3370/// the rmin, rmax dimensions at that point along z.
3371
3373{
3374 TString lunit = fDefault_lunit.c_str();
3375 TString aunit = fDefault_aunit.c_str();
3376 bool unitless_l = true;
3377 bool unitless_a = true;
3378 TString rmin = "0";
3379 TString rmax = "0";
3380 TString z = "0";
3381 TString startphi = "0";
3382 TString deltaphi = "0";
3383 TString name = "";
3384 TString tempattr;
3385
3386 while (attr != 0) {
3387
3388 tempattr = gdml->GetAttrName(attr);
3389 tempattr.ToLower();
3390
3391 if (tempattr == "name") {
3392 name = gdml->GetAttrValue(attr);
3393 } else if (tempattr == "lunit") {
3394 lunit = gdml->GetAttrValue(attr);
3395 unitless_l = false;
3396 } else if (tempattr == "aunit") {
3397 aunit = gdml->GetAttrValue(attr);
3398 unitless_a = false;
3399 } else if (tempattr == "startphi") {
3400 startphi = gdml->GetAttrValue(attr);
3401 } else if (tempattr == "deltaphi") {
3402 deltaphi = gdml->GetAttrValue(attr);
3403 }
3404 attr = gdml->GetNextAttr(attr);
3405 }
3406
3407 TString local_name = name;
3408 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3409 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3410
3411 Double_t retlunit = GetScaleVal(lunit);
3412 Double_t retaunit = GetScaleVal(aunit);
3413 fNunitless += int(unitless_l || unitless_a);
3414
3415 // START TO LOOK THRU CHILD (ZPLANE) NODES...
3416
3417 XMLNodePointer_t child = gdml->GetChild(node);
3418 int numplanes = 0;
3419
3420 while (child != 0) {
3421 numplanes = numplanes + 1;
3422 child = gdml->GetNext(child);
3423 }
3424 if (numplanes < 2) {
3425 Fatal("Polycone", "Found less than 2 planes for polycone %s", name.Data());
3426 return child;
3427 }
3428
3429 int cols;
3430 int i;
3431 cols = 3;
3432 double **table = new double *[numplanes];
3433 for (i = 0; i < numplanes; i++) {
3434 table[i] = new double[cols];
3435 }
3436
3437 child = gdml->GetChild(node);
3438 int planeno = 0;
3439
3440 while (child != 0) {
3441 if (strcmp(gdml->GetNodeName(child), "zplane") == 0) {
3442 // removed original dec
3443 Double_t rminline = 0;
3444 Double_t rmaxline = 0;
3445 Double_t zline = 0;
3446
3447 attr = gdml->GetFirstAttr(child);
3448
3449 while (attr != 0) {
3450 tempattr = gdml->GetAttrName(attr);
3451 tempattr.ToLower();
3452
3453 if (tempattr == "rmin") {
3454 rmin = gdml->GetAttrValue(attr);
3455 rminline = Value(rmin) * retlunit;
3456 table[planeno][0] = rminline;
3457 } else if (tempattr == "rmax") {
3458 rmax = gdml->GetAttrValue(attr);
3459 rmaxline = Value(rmax) * retlunit;
3460 table[planeno][1] = rmaxline;
3461 } else if (tempattr == "z") {
3462 z = gdml->GetAttrValue(attr);
3463 zline = Value(z) * retlunit;
3464 table[planeno][2] = zline;
3465 }
3466 attr = gdml->GetNextAttr(attr);
3467 }
3468 }
3469 planeno = planeno + 1;
3470 child = gdml->GetNext(child);
3471 }
3472
3473 Double_t startphiline = Value(startphi) * retaunit;
3474 Double_t deltaphiline = Value(deltaphi) * retaunit;
3475
3476 TGeoPcon *poly = new TGeoPcon(NameShort(name), startphiline, deltaphiline, numplanes);
3477 Int_t zno = 0;
3478
3479 for (int j = 0; j < numplanes; j++) {
3480 poly->DefineSection(zno, table[j][2], table[j][0], table[j][1]);
3481 zno = zno + 1;
3482 }
3483
3484 fsolmap[local_name.Data()] = poly;
3485 for (i = 0; i < numplanes; i++) {
3486 delete[] table[i];
3487 }
3488 delete[] table;
3489
3490 return node;
3491}
3492
3493////////////////////////////////////////////////////////////////////////////////
3494/// In the solids section of the GDML file, a Polyhedra may be declared.
3495/// when the polyhedra keyword is found, this function is called, and the
3496/// dimensions required are taken and stored, these are then bound and
3497/// converted to type TGeoPgon and stored in fsolmap map using the name
3498/// as its key. Polycone has Zplanes, planes along the z axis specifying
3499/// the rmin, rmax dimensions at that point along z.
3500
3502{
3503 TString lunit = fDefault_lunit.c_str();
3504 TString aunit = fDefault_aunit.c_str();
3505 bool unitless_l = true;
3506 bool unitless_a = true;
3507 TString rmin = "0";
3508 TString rmax = "0";
3509 TString z = "0";
3510 TString startphi = "0";
3511 TString deltaphi = "0";
3512 TString numsides = "1";
3513 TString name = "";
3514 TString tempattr;
3515
3516 while (attr != 0) {
3517
3518 tempattr = gdml->GetAttrName(attr);
3519 tempattr.ToLower();
3520
3521 if (tempattr == "name") {
3522 name = gdml->GetAttrValue(attr);
3523 } else if (tempattr == "lunit") {
3524 lunit = gdml->GetAttrValue(attr);
3525 unitless_l = false;
3526 } else if (tempattr == "aunit") {
3527 aunit = gdml->GetAttrValue(attr);
3528 unitless_a = false;
3529 } else if (tempattr == "startphi") {
3530 startphi = gdml->GetAttrValue(attr);
3531 } else if (tempattr == "deltaphi") {
3532 deltaphi = gdml->GetAttrValue(attr);
3533 } else if (tempattr == "numsides") {
3534 numsides = gdml->GetAttrValue(attr);
3535 }
3536
3537 attr = gdml->GetNextAttr(attr);
3538 }
3539
3540 TString local_name = name;
3541 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3542 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3543
3544 Double_t retlunit = GetScaleVal(lunit);
3545 Double_t retaunit = GetScaleVal(aunit);
3546 fNunitless += int(unitless_l || unitless_a);
3547
3548 // START TO LOOK THRU CHILD (ZPLANE) NODES...
3549
3550 XMLNodePointer_t child = gdml->GetChild(node);
3551 int numplanes = 0;
3552
3553 while (child != 0) {
3554 numplanes = numplanes + 1;
3555 child = gdml->GetNext(child);
3556 }
3557 if (numplanes < 2) {
3558 Fatal("Polyhedra", "Found less than 2 planes for polyhedra %s", name.Data());
3559 return child;
3560 }
3561
3562 int cols;
3563 int i;
3564 cols = 3;
3565 double **table = new double *[numplanes];
3566 for (i = 0; i < numplanes; i++) {
3567 table[i] = new double[cols];
3568 }
3569
3570 child = gdml->GetChild(node);
3571 int planeno = 0;
3572
3573 while (child != 0) {
3574 if (strcmp(gdml->GetNodeName(child), "zplane") == 0) {
3575
3576 Double_t rminline = 0;
3577 Double_t rmaxline = 0;
3578 Double_t zline = 0;
3579 attr = gdml->GetFirstAttr(child);
3580
3581 while (attr != 0) {
3582 tempattr = gdml->GetAttrName(attr);
3583 tempattr.ToLower();
3584
3585 if (tempattr == "rmin") {
3586 rmin = gdml->GetAttrValue(attr);
3587 rminline = Value(rmin) * retlunit;
3588 table[planeno][0] = rminline;
3589 } else if (tempattr == "rmax") {
3590 rmax = gdml->GetAttrValue(attr);
3591 rmaxline = Value(rmax) * retlunit;
3592 table[planeno][1] = rmaxline;
3593 } else if (tempattr == "z") {
3594 z = gdml->GetAttrValue(attr);
3595 zline = Value(z) * retlunit;
3596 table[planeno][2] = zline;
3597 }
3598
3599 attr = gdml->GetNextAttr(attr);
3600 }
3601 }
3602 planeno = planeno + 1;
3603 child = gdml->GetNext(child);
3604 }
3605
3606 Double_t startphiline = Value(startphi) * retaunit;
3607 Double_t deltaphiline = Value(deltaphi) * retaunit;
3608 Int_t numsidesline = (int)Value(numsides);
3609
3610 TGeoPgon *polyg = new TGeoPgon(NameShort(name), startphiline, deltaphiline, numsidesline, numplanes);
3611 Int_t zno = 0;
3612
3613 for (int j = 0; j < numplanes; j++) {
3614 polyg->DefineSection(zno, table[j][2], table[j][0], table[j][1]);
3615 zno = zno + 1;
3616 }
3617
3618 fsolmap[local_name.Data()] = polyg;
3619 for (i = 0; i < numplanes; i++) {
3620 delete[] table[i];
3621 }
3622 delete[] table;
3623
3624 return node;
3625}
3626
3627////////////////////////////////////////////////////////////////////////////////
3628/// In the solids section of the GDML file, a Sphere may be declared.
3629/// when the sphere keyword is found, this function is called, and the
3630/// dimensions required are taken and stored, these are then bound and
3631/// converted to type TGeoSphere and stored in fsolmap map using the name
3632/// as its key.
3633
3635{
3636 TString lunit = fDefault_lunit.c_str();
3637 TString aunit = fDefault_aunit.c_str();
3638 bool unitless_l = true;
3639 bool unitless_a = true;
3640 TString rmin = "0";
3641 TString rmax = "0";
3642 TString startphi = "0";
3643 TString deltaphi = "0";
3644 TString starttheta = "0";
3645 TString deltatheta = "0";
3646 TString name = "";
3647 TString tempattr;
3648
3649 while (attr != 0) {
3650 tempattr = gdml->GetAttrName(attr);
3651 tempattr.ToLower();
3652
3653 if (tempattr == "name") {
3654 name = gdml->GetAttrValue(attr);
3655 } else if (tempattr == "rmin") {
3656 rmin = gdml->GetAttrValue(attr);
3657 } else if (tempattr == "rmax") {
3658 rmax = gdml->GetAttrValue(attr);
3659 } else if (tempattr == "lunit") {
3660 lunit = gdml->GetAttrValue(attr);
3661 unitless_l = false;
3662 } else if (tempattr == "aunit") {
3663 aunit = gdml->GetAttrValue(attr);
3664 unitless_a = false;
3665 } else if (tempattr == "startphi") {
3666 startphi = gdml->GetAttrValue(attr);
3667 } else if (tempattr == "deltaphi") {
3668 deltaphi = gdml->GetAttrValue(attr);
3669 } else if (tempattr == "starttheta") {
3670 starttheta = gdml->GetAttrValue(attr);
3671 } else if (tempattr == "deltatheta") {
3672 deltatheta = gdml->GetAttrValue(attr);
3673 }
3674
3675 attr = gdml->GetNextAttr(attr);
3676 }
3677
3678 TString local_name = name;
3679 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3680 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3681
3682 Double_t retlunit = GetScaleVal(lunit);
3683 Double_t retaunit = GetScaleVal(aunit);
3684 fNunitless += int(unitless_l || unitless_a);
3685
3686 Double_t rminline = Value(rmin) * retlunit;
3687 Double_t rmaxline = Value(rmax) * retlunit;
3688 Double_t startphiline = Value(startphi) * retaunit;
3689 Double_t deltaphiline = startphiline + Value(deltaphi) * retaunit;
3690 Double_t startthetaline = Value(starttheta) * retaunit;
3691 Double_t deltathetaline = startthetaline + Value(deltatheta) * retaunit;
3692
3693 TGeoSphere *sphere =
3694 new TGeoSphere(NameShort(name), rminline, rmaxline, startthetaline, deltathetaline, startphiline, deltaphiline);
3695
3696 fsolmap[local_name.Data()] = sphere;
3697
3698 return node;
3699}
3700
3701////////////////////////////////////////////////////////////////////////////////
3702/// In the solids section of the GDML file, a Torus may be declared.
3703/// when the torus keyword is found, this function is called, and the
3704/// dimensions required are taken and stored, these are then bound and
3705/// converted to type TGeoTorus and stored in fsolmap map using the name
3706/// as its key.
3707
3709{
3710 TString lunit = fDefault_lunit.c_str();
3711 TString aunit = fDefault_aunit.c_str();
3712 bool unitless_l = true;
3713 bool unitless_a = true;
3714 TString rmin = "0";
3715 TString rmax = "0";
3716 TString rtor = "0";
3717 TString startphi = "0";
3718 TString deltaphi = "0";
3719 TString name = "";
3720 TString tempattr;
3721
3722 while (attr != 0) {
3723
3724 tempattr = gdml->GetAttrName(attr);
3725 tempattr.ToLower();
3726
3727 if (tempattr == "name") {
3728 name = gdml->GetAttrValue(attr);
3729 } else if (tempattr == "rmin") {
3730 rmin = gdml->GetAttrValue(attr);
3731 } else if (tempattr == "rmax") {
3732 rmax = gdml->GetAttrValue(attr);
3733 } else if (tempattr == "rtor") {
3734 rtor = gdml->GetAttrValue(attr);
3735 } else if (tempattr == "lunit") {
3736 lunit = gdml->GetAttrValue(attr);
3737 unitless_l = false;
3738 } else if (tempattr == "aunit") {
3739 aunit = gdml->GetAttrValue(attr);
3740 unitless_a = false;
3741 } else if (tempattr == "startphi") {
3742 startphi = gdml->GetAttrValue(attr);
3743 } else if (tempattr == "deltaphi") {
3744 deltaphi = gdml->GetAttrValue(attr);
3745 }
3746
3747 attr = gdml->GetNextAttr(attr);
3748 }
3749
3750 TString local_name = name;
3751 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3752 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3753
3754 Double_t retlunit = GetScaleVal(lunit);
3755 Double_t retaunit = GetScaleVal(aunit);
3756 fNunitless += int(unitless_l || unitless_a);
3757
3758 Double_t rminline = Value(rmin) * retlunit;
3759 Double_t rmaxline = Value(rmax) * retlunit;
3760 Double_t rtorline = Value(rtor) * retlunit;
3761 Double_t startphiline = Value(startphi) * retaunit;
3762 Double_t deltaphiline = Value(deltaphi) * retaunit;
3763
3764 TGeoTorus *torus = new TGeoTorus(NameShort(name), rtorline, rminline, rmaxline, startphiline, deltaphiline);
3765
3766 fsolmap[local_name.Data()] = torus;
3767
3768 return node;
3769}
3770
3771////////////////////////////////////////////////////////////////////////////////
3772/// In the solids section of the GDML file, a Hype may be declared.
3773/// when the hype keyword is found, this function is called, and the
3774/// dimensions required are taken and stored, these are then bound and
3775/// converted to type TGeoHype and stored in fsolmap map using the name
3776/// as its key.
3777
3779{
3780 TString lunit = fDefault_lunit.c_str();
3781 TString aunit = fDefault_aunit.c_str();
3782 bool unitless_l = true;
3783 bool unitless_a = true;
3784 TString rmin = "0";
3785 TString rmax = "0";
3786 TString z = "0";
3787 TString inst = "0";
3788 TString outst = "0";
3789 TString name = "";
3790 TString tempattr;
3791
3792 while (attr != 0) {
3793 tempattr = gdml->GetAttrName(attr);
3794 tempattr.ToLower();
3795
3796 if (tempattr == "name") {
3797 name = gdml->GetAttrValue(attr);
3798 } else if (tempattr == "rmin") {
3799 rmin = gdml->GetAttrValue(attr);
3800 } else if (tempattr == "rmax") {
3801 rmax = gdml->GetAttrValue(attr);
3802 } else if (tempattr == "z") {
3803 z = gdml->GetAttrValue(attr);
3804 } else if (tempattr == "lunit") {
3805 lunit = gdml->GetAttrValue(attr);
3806 unitless_l = false;
3807 } else if (tempattr == "aunit") {
3808 aunit = gdml->GetAttrValue(attr);
3809 unitless_a = false;
3810 } else if (tempattr == "inst") {
3811 inst = gdml->GetAttrValue(attr);
3812 } else if (tempattr == "outst") {
3813 outst = gdml->GetAttrValue(attr);
3814 }
3815
3816 attr = gdml->GetNextAttr(attr);
3817 }
3818
3819 TString local_name = name;
3820 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3821 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3822
3823 Double_t retlunit = GetScaleVal(lunit);
3824 Double_t retaunit = GetScaleVal(aunit);
3825 fNunitless += int(unitless_l || unitless_a);
3826
3827 Double_t rminline = Value(rmin) * retlunit;
3828 Double_t rmaxline = Value(rmax) * retlunit;
3829 Double_t zline = Value(z) * retlunit;
3830 Double_t instline = Value(inst) * retaunit;
3831 Double_t outstline = Value(outst) * retaunit;
3832
3833 TGeoHype *hype = new TGeoHype(NameShort(name), rminline, instline, rmaxline, outstline, zline / 2);
3834
3835 fsolmap[local_name.Data()] = hype;
3836
3837 return node;
3838}
3839
3840////////////////////////////////////////////////////////////////////////////////
3841/// In the solids section of the GDML file, a Para may be declared.
3842/// when the para keyword is found, this function is called, and the
3843/// dimensions required are taken and stored, these are then bound and
3844/// converted to type TGeoPara and stored in fsolmap map using the name
3845/// as its key.
3846
3848{
3849 TString lunit = fDefault_lunit.c_str();
3850 TString aunit = fDefault_aunit.c_str();
3851 bool unitless_l = true;
3852 bool unitless_a = true;
3853 TString x = "0";
3854 TString y = "0";
3855 TString z = "0";
3856 TString phi = "0";
3857 TString theta = "0";
3858 TString alpha = "0";
3859 TString name = "";
3860 TString tempattr;
3861
3862 while (attr != 0) {
3863
3864 tempattr = gdml->GetAttrName(attr);
3865 tempattr.ToLower();
3866
3867 if (tempattr == "name") {
3868 name = gdml->GetAttrValue(attr);
3869 } else if (tempattr == "x") {
3870 x = gdml->GetAttrValue(attr);
3871 } else if (tempattr == "y") {
3872 y = gdml->GetAttrValue(attr);
3873 } else if (tempattr == "z") {
3874 z = gdml->GetAttrValue(attr);
3875 } else if (tempattr == "lunit") {
3876 lunit = gdml->GetAttrValue(attr);
3877 unitless_l = false;
3878 } else if (tempattr == "aunit") {
3879 aunit = gdml->GetAttrValue(attr);
3880 unitless_a = false;
3881 } else if (tempattr == "phi") {
3882 phi = gdml->GetAttrValue(attr);
3883 } else if (tempattr == "theta") {
3884 theta = gdml->GetAttrValue(attr);
3885 } else if (tempattr == "alpha") {
3886 alpha = gdml->GetAttrValue(attr);
3887 }
3888
3889 attr = gdml->GetNextAttr(attr);
3890 }
3891
3892 TString local_name = name;
3893 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3894 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3895
3896 Double_t retlunit = GetScaleVal(lunit);
3897 Double_t retaunit = GetScaleVal(aunit);
3898 fNunitless += int(unitless_l || unitless_a);
3899
3900 Double_t xline = Value(x) * retlunit;
3901 Double_t yline = Value(y) * retlunit;
3902 Double_t zline = Value(z) * retlunit;
3903 Double_t philine = Value(phi) * retaunit;
3904 Double_t alphaline = Value(alpha) * retaunit;
3905 Double_t thetaline = Value(theta) * retaunit;
3906
3907 TGeoPara *para = new TGeoPara(NameShort(name), xline / 2, yline / 2, zline / 2, alphaline, thetaline, philine);
3908
3909 fsolmap[local_name.Data()] = para;
3910
3911 return node;
3912}
3913
3914////////////////////////////////////////////////////////////////////////////////
3915/// In the solids section of the GDML file, a TwistTrap may be declared.
3916/// when the twistedtrap keyword is found, this function is called, and the
3917/// dimensions required are taken and stored, these are then bound and
3918/// converted to type TGeoGTra and stored in fsolmap map using the name
3919/// as its key.
3920
3922{
3923 TString lunit = fDefault_lunit.c_str();
3924 TString aunit = fDefault_aunit.c_str();
3925 bool unitless_l = true;
3926 bool unitless_a = true;
3927 TString x1 = "0";
3928 TString x2 = "0";
3929 TString x3 = "0";
3930 TString x4 = "0";
3931 TString y1 = "0";
3932 TString y2 = "0";
3933 TString z = "0";
3934 TString phi = "0";
3935 TString theta = "0";
3936 TString alpha1 = "0";
3937 TString alpha2 = "0";
3938 TString twist = "0";
3939 TString name = "";
3940 TString tempattr;
3941
3942 while (attr != 0) {
3943
3944 tempattr = gdml->GetAttrName(attr);
3945 tempattr.ToLower();
3946
3947 if (tempattr == "name") {
3948 name = gdml->GetAttrValue(attr);
3949 } else if (tempattr == "x1") {
3950 x1 = gdml->GetAttrValue(attr);
3951 } else if (tempattr == "x2") {
3952 x2 = gdml->GetAttrValue(attr);
3953 } else if (tempattr == "x3") {
3954 x3 = gdml->GetAttrValue(attr);
3955 } else if (tempattr == "x4") {
3956 x4 = gdml->GetAttrValue(attr);
3957 } else if (tempattr == "y1") {
3958 y1 = gdml->GetAttrValue(attr);
3959 } else if (tempattr == "y2") {
3960 y2 = gdml->GetAttrValue(attr);
3961 } else if (tempattr == "z") {
3962 z = gdml->GetAttrValue(attr);
3963 } else if (tempattr == "lunit") {
3964 lunit = gdml->GetAttrValue(attr);
3965 unitless_l = false;
3966 } else if (tempattr == "aunit") {
3967 aunit = gdml->GetAttrValue(attr);
3968 unitless_a = false;
3969 } else if (tempattr == "phi") {
3970 phi = gdml->GetAttrValue(attr);
3971 } else if (tempattr == "theta") {
3972 theta = gdml->GetAttrValue(attr);
3973 } else if (tempattr == "alph") { // gdml schema knows only alph attribute
3974 alpha1 = gdml->GetAttrValue(attr);
3975 alpha2 = alpha1;
3976 //} else if (tempattr == "alpha2") {
3977 // alpha2 = gdml->GetAttrValue(attr);
3978 } else if (tempattr == "phitwist") {
3979 twist = gdml->GetAttrValue(attr);
3980 }
3981
3982 attr = gdml->GetNextAttr(attr);
3983 }
3984
3985 TString local_name = name;
3986 if ((strcmp(fCurrentFile, fStartFile)) != 0)
3987 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
3988
3989 Double_t retlunit = GetScaleVal(lunit);
3990 Double_t retaunit = GetScaleVal(aunit);
3991 fNunitless += int(unitless_l || unitless_a);
3992
3993 Double_t x1line = Value(x1) * retlunit;
3994 Double_t x2line = Value(x2) * retlunit;
3995 Double_t x3line = Value(x3) * retlunit;
3996 Double_t x4line = Value(x4) * retlunit;
3997 Double_t y1line = Value(y1) * retlunit;
3998 Double_t y2line = Value(y2) * retlunit;
3999 Double_t zline = Value(z) * retlunit;
4000 Double_t philine = Value(phi) * retaunit;
4001 Double_t thetaline = Value(theta) * retaunit;
4002 Double_t alpha1line = Value(alpha1) * retaunit;
4003 Double_t alpha2line = Value(alpha2) * retaunit;
4004 Double_t twistline = Value(twist) * retaunit;
4005
4006 TGeoGtra *twtrap = new TGeoGtra(NameShort(name), zline / 2, thetaline, philine, twistline, y1line / 2, x1line / 2,
4007 x2line / 2, alpha1line, y2line / 2, x3line / 2, x4line / 2, alpha2line);
4008
4009 fsolmap[local_name.Data()] = twtrap;
4010
4011 return node;
4012}
4013
4014////////////////////////////////////////////////////////////////////////////////
4015/// In the solids section of the GDML file, a ElTube may be declared.
4016/// when the eltube keyword is found, this function is called, and the
4017/// dimensions required are taken and stored, these are then bound and
4018/// converted to type TGeoEltu and stored in fsolmap map using the name
4019/// as its key.
4020
4022{
4023 TString lunit = fDefault_lunit.c_str();
4024 bool unitless_l = true;
4025 TString xpos = "0";
4026 TString ypos = "0";
4027 TString zpos = "0";
4028 TString name = "";
4029 TString tempattr;
4030
4031 while (attr != 0) {
4032
4033 tempattr = gdml->GetAttrName(attr);
4034 tempattr.ToLower();
4035
4036 if (tempattr == "name") {
4037 name = gdml->GetAttrValue(attr);
4038 } else if (tempattr == "dx") {
4039 xpos = gdml->GetAttrValue(attr);
4040 } else if (tempattr == "dy") {
4041 ypos = gdml->GetAttrValue(attr);
4042 } else if (tempattr == "dz") {
4043 zpos = gdml->GetAttrValue(attr);
4044 } else if (tempattr == "lunit") {
4045 lunit = gdml->GetAttrValue(attr);
4046 unitless_l = false;
4047 }
4048
4049 attr = gdml->GetNextAttr(attr);
4050 }
4051
4052 TString local_name = name;
4053 if ((strcmp(fCurrentFile, fStartFile)) != 0)
4054 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
4055
4056 Double_t retunit = GetScaleVal(lunit);
4057 fNunitless += int(unitless_l);
4058
4059 Double_t xline = Value(xpos) * retunit;
4060 Double_t yline = Value(ypos) * retunit;
4061 Double_t zline = Value(zpos) * retunit;
4062
4063 TGeoEltu *eltu = new TGeoEltu(NameShort(name), xline, yline, zline);
4064
4065 fsolmap[local_name.Data()] = eltu;
4066
4067 return node;
4068}
4069////////////////////////////////////////////////////////////////////////////////
4070/// In the solids section of the GDML file, an Orb may be declared.
4071/// when the orb keyword is found, this function is called, and the
4072/// dimensions required are taken and stored, these are then bound and
4073/// converted to type TGeoSphere and stored in fsolmap map using the name
4074/// as its key.
4075
4077{
4078 TString lunit = fDefault_lunit.c_str();
4079 bool unitless_l = true;
4080 TString r = "0";
4081 TString name = "";
4082 TString tempattr;
4083
4084 while (attr != 0) {
4085
4086 tempattr = gdml->GetAttrName(attr);
4087 tempattr.ToLower();
4088
4089 if (tempattr == "name") {
4090 name = gdml->GetAttrValue(attr);
4091 } else if (tempattr == "r") {
4092 r = gdml->GetAttrValue(attr);
4093 } else if (tempattr == "lunit") {
4094 lunit = gdml->GetAttrValue(attr);
4095 unitless_l = false;
4096 }
4097
4098 attr = gdml->GetNextAttr(attr);
4099 }
4100
4101 TString local_name = name;
4102 if ((strcmp(fCurrentFile, fStartFile)) != 0)
4103 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
4104
4105 Double_t retunit = GetScaleVal(lunit);
4106 fNunitless += int(unitless_l);
4107
4108 Double_t rline = Value(r) * retunit;
4109
4110 TGeoSphere *orb = new TGeoSphere(NameShort(name), 0, rline, 0, 180, 0, 360);
4111
4112 fsolmap[local_name.Data()] = orb;
4113
4114 return node;
4115}
4116
4117////////////////////////////////////////////////////////////////////////////////
4118/// In the solids section of the GDML file, an Xtru may be declared.
4119/// when the xtru keyword is found, this function is called, and the
4120/// dimensions required are taken and stored, these are then bound and
4121/// converted to type TGeoXtru and stored in fsolmap map using the name
4122/// as its key. The xtru has child nodes of either 'twoDimVertex'or
4123/// 'section'. These two nodes define the real structure of the shape.
4124/// The twoDimVertex's define the x,y sizes of a vertice. The section links
4125/// the vertice to a position within the xtru.
4126
4128{
4129 TString lunit = fDefault_lunit.c_str();
4130 bool unitless_l = true;
4131 TString x = "0";
4132 TString y = "0";
4133 TString zorder = "0";
4134 TString zpos = "0";
4135 TString xoff = "0";
4136 TString yoff = "0";
4137 TString scale = "0";
4138 TString name = "";
4139 TString tempattr;
4140
4141 while (attr != 0) {
4142
4143 tempattr = gdml->GetAttrName(attr);
4144 tempattr.ToLower();
4145
4146 if (tempattr == "name") {
4147 name = gdml->GetAttrValue(attr);
4148 } else if (tempattr == "lunit") {
4149 lunit = gdml->GetAttrValue(attr);
4150 unitless_l = false;
4151 }
4152
4153 attr = gdml->GetNextAttr(attr);
4154 }
4155
4156 TString local_name = name;
4157 if ((strcmp(fCurrentFile, fStartFile)) != 0)
4158 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
4159
4160 Double_t retlunit = GetScaleVal(lunit);
4161 fNunitless += int(unitless_l);
4162
4163 // START TO LOOK THRU CHILD NODES...
4164
4165 XMLNodePointer_t child = gdml->GetChild(node);
4166 int nosects = 0;
4167 int noverts = 0;
4168
4169 while (child != 0) {
4170 tempattr = gdml->GetNodeName(child);
4171
4172 if (tempattr == "twoDimVertex") {
4173 noverts = noverts + 1;
4174 } else if (tempattr == "section") {
4175 nosects = nosects + 1;
4176 }
4177
4178 child = gdml->GetNext(child);
4179 }
4180
4181 if (nosects < 2 || noverts < 3) {
4182 Fatal("Xtru", "Invalid number of sections/vertices found forxtru %s", name.Data());
4183 return child;
4184 }
4185
4186 // Build the dynamic arrays..
4187 int cols;
4188 int i;
4189 double *vertx = new double[noverts];
4190 double *verty = new double[noverts];
4191 cols = 5;
4192 double **section = new double *[nosects];
4193 for (i = 0; i < nosects; i++) {
4194 section[i] = new double[cols];
4195 }
4196
4197 child = gdml->GetChild(node);
4198 int sect = 0;
4199 int vert = 0;
4200
4201 while (child != 0) {
4202 if (strcmp(gdml->GetNodeName(child), "twoDimVertex") == 0) {
4203 Double_t xline = 0;
4204 Double_t yline = 0;
4205
4206 attr = gdml->GetFirstAttr(child);
4207
4208 while (attr != 0) {
4209 tempattr = gdml->GetAttrName(attr);
4210
4211 if (tempattr == "x") {
4212 x = gdml->GetAttrValue(attr);
4213 xline = Value(x) * retlunit;
4214 vertx[vert] = xline;
4215 } else if (tempattr == "y") {
4216 y = gdml->GetAttrValue(attr);
4217 yline = Value(y) * retlunit;
4218 verty[vert] = yline;
4219 }
4220
4221 attr = gdml->GetNextAttr(attr);
4222 }
4223
4224 vert = vert + 1;
4225 }
4226
4227 else if (strcmp(gdml->GetNodeName(child), "section") == 0) {
4228
4229 Double_t zposline = 0;
4230 Double_t xoffline = 0;
4231 Double_t yoffline = 0;
4232
4233 attr = gdml->GetFirstAttr(child);
4234
4235 while (attr != 0) {
4236 tempattr = gdml->GetAttrName(attr);
4237
4238 if (tempattr == "zOrder") {
4239 zorder = gdml->GetAttrValue(attr);
4240 section[sect][0] = Value(zorder);
4241 } else if (tempattr == "zPosition") {
4242 zpos = gdml->GetAttrValue(attr);
4243 zposline = Value(zpos) * retlunit;
4244 section[sect][1] = zposline;
4245 } else if (tempattr == "xOffset") {
4246 xoff = gdml->GetAttrValue(attr);
4247 xoffline = Value(xoff) * retlunit;
4248 section[sect][2] = xoffline;
4249 } else if (tempattr == "yOffset") {
4250 yoff = gdml->GetAttrValue(attr);
4251 yoffline = Value(yoff) * retlunit;
4252 section[sect][3] = yoffline;
4253 } else if (tempattr == "scalingFactor") {
4254 scale = gdml->GetAttrValue(attr);
4255 section[sect][4] = Value(scale);
4256 }
4257
4258 attr = gdml->GetNextAttr(attr);
4259 }
4260
4261 sect = sect + 1;
4262 }
4263 child = gdml->GetNext(child);
4264 }
4265
4266 TGeoXtru *xtru = new TGeoXtru(nosects);
4267 xtru->SetName(NameShort(name));
4268 xtru->DefinePolygon(vert, vertx, verty);
4269
4270 for (int j = 0; j < sect; j++) {
4271 xtru->DefineSection((int)section[j][0], section[j][1], section[j][2], section[j][3], section[j][4]);
4272 }
4273
4274 fsolmap[local_name.Data()] = xtru;
4275 delete[] vertx;
4276 delete[] verty;
4277 for (i = 0; i < nosects; i++) {
4278 delete[] section[i];
4279 }
4280 delete[] section;
4281 return node;
4282}
4283
4284////////////////////////////////////////////////////////////////////////////////
4285/// In the solids section of the GDML file, a tessellated shape may be declared.
4286/// When the tessellated keyword is found, this function is called, and the
4287/// triangular/quadrangular facets are read, creating the corresponding
4288/// TGeoTessellated object stored in fsolmap map using the name
4289/// as its key.
4290
4292{
4293 TString name, vname, type;
4294 TString tempattr;
4295
4296 while (attr != nullptr) {
4297 tempattr = gdml->GetAttrName(attr);
4298 tempattr.ToLower();
4299 if (tempattr == "name") {
4300 name = gdml->GetAttrValue(attr);
4301 }
4302 attr = gdml->GetNextAttr(attr);
4303 }
4304
4305 TString local_name = name;
4306 if ((strcmp(fCurrentFile, fStartFile)) != 0)
4307 local_name = TString::Format("%s_%s", name.Data(), fCurrentFile);
4308
4309 auto tsl = new TGeoTessellated(NameShort(name));
4310 TGeoTranslation *pos = nullptr;
4311 Tessellated::Vertex_t vertices[4];
4312
4313 auto SetVertex = [&](int i, TGeoTranslation *trans) {
4314 if (trans == nullptr)
4315 return;
4316 const double *tr = trans->GetTranslation();
4317 vertices[i].Set(tr[0], tr[1], tr[2]);
4318 };
4319
4320 auto AddTriangularFacet = [&](bool relative) {
4321 if (relative) {
4322 vertices[2] += vertices[0] + vertices[1];
4323 vertices[1] += vertices[0];
4324 }
4325 tsl->AddFacet(vertices[0], vertices[1], vertices[2]);
4326 };
4327
4328 auto AddQuadrangularFacet = [&](bool relative) {
4329 if (relative) {
4330 vertices[3] += vertices[0] + vertices[1] + vertices[2];
4331 vertices[2] += vertices[0] + vertices[1];
4332 vertices[1] += vertices[0];
4333 }
4334 tsl->AddFacet(vertices[0], vertices[1], vertices[2], vertices[3]);
4335 };
4336
4337 // Get facet attributes
4338 XMLNodePointer_t child = gdml->GetChild(node);
4339 while (child != nullptr) {
4340 tempattr = gdml->GetNodeName(child);
4341 tempattr.ToLower();
4342 if (tempattr == "triangular") {
4343 attr = gdml->GetFirstAttr(child);
4344 bool relative = false;
4345
4346 while (attr != nullptr) {
4347 tempattr = gdml->GetAttrName(attr);
4348
4349 if (tempattr == "vertex1") {
4350 vname = gdml->GetAttrValue(attr);
4351 pos = GetPosition(vname.Data());
4352 if (!pos)
4353 Fatal("Tessellated", "Vertex %s not defined", vname.Data());
4354 SetVertex(0, pos);
4355 }
4356
4357 else if (tempattr == "vertex2") {
4358 vname = gdml->GetAttrValue(attr);
4359 pos = GetPosition(vname.Data());
4360 if (!pos)
4361 Fatal("Tessellated", "Vertex %s not defined", vname.Data());
4362 SetVertex(1, pos);
4363 }
4364
4365 else if (tempattr == "vertex3") {
4366 vname = gdml->GetAttrValue(attr);
4367 pos = GetPosition(vname.Data());
4368 if (!pos)
4369 Fatal("Tessellated", "Vertex %s not defined", vname.Data());
4370 SetVertex(2, pos);
4371 }
4372
4373 else if (tempattr == "type") {
4374 type = gdml->GetAttrValue(attr);
4375 type.ToLower();
4376 relative = (type == "relative") ? true : false;
4377 }
4378
4379 attr = gdml->GetNextAttr(attr);
4380 }
4381 AddTriangularFacet(relative);
4382 }
4383
4384 else if (tempattr == "quadrangular") {
4385 attr = gdml->GetFirstAttr(child);
4386 bool relative = false;
4387
4388 while (attr != nullptr) {
4389 tempattr = gdml->GetAttrName(attr);
4390
4391 if (tempattr == "vertex1") {
4392 vname = gdml->GetAttrValue(attr);
4393 pos = GetPosition(vname.Data());
4394 if (!pos)
4395 Fatal("Tessellated", "Vertex %s not defined", vname.Data());
4396 SetVertex(0, pos);
4397 }
4398
4399 else if (tempattr == "vertex2") {
4400 vname = gdml->GetAttrValue(attr);
4401 pos = GetPosition(vname.Data());
4402 if (!pos)
4403 Fatal("Tessellated", "Vertex %s not defined", vname.Data());
4404 SetVertex(1, pos);
4405 }
4406
4407 else if (tempattr == "vertex3") {
4408 vname = gdml->GetAttrValue(attr);
4409 pos = GetPosition(vname.Data());
4410 if (!pos)
4411 Fatal("Tessellated", "Vertex %s not defined", vname.Data());
4412 SetVertex(2, pos);
4413 }
4414
4415 else if (tempattr == "vertex4") {
4416 vname = gdml->GetAttrValue(attr);
4417 pos = GetPosition(vname.Data());
4418 if (!pos)
4419 Fatal("Tessellated", "Vertex %s not defined", vname.Data());
4420 SetVertex(3, pos);
4421 }
4422
4423 else if (tempattr == "type") {
4424 type = gdml->GetAttrValue(attr);
4425 type.ToLower();
4426 relative = (type == "relative") ? true : false;
4427 }
4428
4429 attr = gdml->GetNextAttr(attr);
4430 }
4431 AddQuadrangularFacet(relative);
4432 }
4433 child = gdml->GetNext(child);
4434 }
4435 tsl->CloseShape(false);
4436
4437 fsolmap[local_name.Data()] = tsl;
4438
4439 return node;
4440}
4441
4442////////////////////////////////////////////////////////////////////////////////
4443/// In the solids section of the GDML file, a Reflected Solid may be
4444/// declared when the ReflectedSolid keyword is found, this function
4445/// is called. The rotation, position and scale for the reflection are
4446/// applied to a matrix that is then stored in the class object
4447/// TGDMLRefl. This is then stored in the map freflsolidmap, with
4448/// the reflection name as a reference. also the name of the solid to
4449/// be reflected is stored in a map called freflectmap with the reflection
4450/// name as a reference.
4451
4453{
4454 std::cout << "WARNING! The reflectedSolid is obsolete! Use scale transformation instead!" << std::endl;
4455
4456 TString sx = "0";
4457 TString sy = "0";
4458 TString sz = "0";
4459 TString rx = "0";
4460 TString ry = "0";
4461 TString rz = "0";
4462 TString dx = "0";
4463 TString dy = "0";
4464 TString dz = "0";
4465 TString name = "0";
4466 TString solid = "0";
4467 TString tempattr;
4468
4469 while (attr != 0) {
4470
4471 tempattr = gdml->GetAttrName(attr);
4472 tempattr.ToLower();
4473
4474 if (tempattr == "name") {
4475 name = gdml->GetAttrValue(attr);
4476 } else if (tempattr == "sx") {
4477 sx = gdml->GetAttrValue(attr);
4478 } else if (tempattr == "sy") {
4479 sy = gdml->GetAttrValue(attr);
4480 } else if (tempattr == "sz") {
4481 sz = gdml->GetAttrValue(attr);
4482 } else if (tempattr == "rx") {
4483 rx = gdml->GetAttrValue(attr);
4484 } else if (tempattr == "ry") {
4485 ry = gdml->GetAttrValue(attr);
4486 } else if (tempattr == "rz") {
4487 rz = gdml->GetAttrValue(attr);
4488 } else if (tempattr == "dx") {
4489 dx = gdml->GetAttrValue(attr);
4490 } else if (tempattr == "dy") {
4491 dy = gdml->GetAttrValue(attr);
4492 } else if (tempattr == "dz") {
4493 dz = gdml->GetAttrValue(attr);
4494 } else if (tempattr == "solid") {
4495 solid = gdml->GetAttrValue(attr);
4496 }
4497 attr = gdml->GetNextAttr(attr);
4498 }
4499
4500 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
4501 name = TString::Format("%s_%s", name.Data(), fCurrentFile);
4502 }
4503 if ((strcmp(fCurrentFile, fStartFile)) != 0) {
4504 solid = TString::Format("%s_%s", solid.Data(), fCurrentFile);
4505 }
4506
4507 TGeoRotation *rot = new TGeoRotation();
4508 rot->RotateZ(-(Value(rz)));
4509 rot->RotateY(-(Value(ry)));
4510 rot->RotateX(-(Value(rx)));
4511
4512 if (atoi(sx) == -1) {
4513 rot->ReflectX(kTRUE);
4514 }
4515 if (atoi(sy) == -1) {
4516 rot->ReflectY(kTRUE);
4517 }
4518 if (atoi(sz) == -1) {
4519 rot->ReflectZ(kTRUE);
4520 }
4521
4522 TGeoCombiTrans *relf_matx = new TGeoCombiTrans(Value(dx), Value(dy), Value(dz), rot);
4523
4524 TGDMLRefl *reflsol = new TGDMLRefl(NameShort(name), solid, relf_matx);
4525 freflsolidmap[name.Data()] = reflsol;
4526 freflectmap[name.Data()] = solid;
4527
4528 return node;
4529}
4530
4531/** \class TGDMLRefl
4532\ingroup Geometry_gdml
4533
4534This class is a helper class for TGDMLParse. It assists in the
4535reflection process. This process takes a previously defined solid
4536and can reflect the matrix of it. This class stores the name of the
4537reflected solid, along with the name of the solid that is being
4538reflected, and finally the reflected solid's matrix. This is then
4539recalled when the volume is used in the structure part of the gdml
4540file.
4541
4542*/
4543
4545
4546////////////////////////////////////////////////////////////////////////////////
4547/// This constructor method stores the values brought in as params.
4548
4549TGDMLRefl::TGDMLRefl(const char *name, const char *solid, TGeoMatrix *matrix)
4550{
4551 fNameS = name;
4552 fSolid = solid;
4553 fMatrix = matrix;
4554}
4555
4556////////////////////////////////////////////////////////////////////////////////
4557/// This accessor method returns the matrix.
4558
4560{
4561 return fMatrix;
4562}
#define d(i)
Definition RSha256.hxx:102
#define f(i)
Definition RSha256.hxx:104
#define a(i)
Definition RSha256.hxx:99
#define e(i)
Definition RSha256.hxx:103
static const double x4[22]
static const double x3[11]
int Int_t
Definition RtypesCore.h:45
constexpr Bool_t kFALSE
Definition RtypesCore.h:101
constexpr Bool_t kTRUE
Definition RtypesCore.h:100
#define ClassImp(name)
Definition Rtypes.h:377
winID h TVirtualViewer3D TVirtualGLPainter p
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t atom
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char filename
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char Pixmap_t Pixmap_t PictureAttributes_t attr const char char ret_data h unsigned char height h offset
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t r
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t index
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t child
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void value
Option_t Option_t TPoint TPoint const char x2
Option_t Option_t TPoint TPoint const char x1
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void xpos
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t attr
Option_t Option_t TPoint TPoint const char y2
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void ypos
Option_t Option_t width
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char Pixmap_t Pixmap_t PictureAttributes_t attr const char char ret_data h unsigned char height h Atom_t Int_t ULong_t ULong_t unsigned char prop_list Atom_t Atom_t Atom_t Time_t type
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char Pixmap_t Pixmap_t PictureAttributes_t attr const char char ret_data h unsigned char height h Atom_t Int_t ULong_t ULong_t unsigned char prop_list Atom_t Atom_t Atom_t Time_t property
Option_t Option_t TPoint TPoint const char y1
char name[80]
Definition TGX11.cxx:110
R__EXTERN TGeoManager * gGeoManager
Int_t gDebug
Definition TROOT.cxx:585
void * XMLNodePointer_t
Definition TXMLEngine.h:17
void * XMLDocPointer_t
Definition TXMLEngine.h:20
void * XMLAttrPointer_t
Definition TXMLEngine.h:19
virtual void SetOwner(Bool_t enable=kTRUE)
Set whether this collection is the owner (enable==true) of its content.
virtual Int_t GetSize() const
Return the capacity of the collection, i.e.
The Formula class.
Definition TFormula.h:87
Double_t Eval(Double_t x) const
Sets first variable (e.g. x) and evaluate formula.
This class is used in the process of reading and writing the GDML "matrix" tag.
Definition TGDMLMatrix.h:34
void Set(size_t r, size_t c, Double_t a)
void SetMatrixAsString(const char *mat)
Definition TGDMLMatrix.h:46
This class contains the implementation of the GDML parser associated to all the supported GDML elemen...
Definition TGDMLParse.h:95
XMLNodePointer_t Ellipsoid(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, an ellipsoid may be declared.
double Evaluate(const char *evalline)
Takes a string containing a mathematical expression and returns the value of the expression.
TGeoVolume * GDMLReadFile(const char *filename="test.gdml")
Creates the new instance of the XMLEngine called 'gdml', using the filename >> then parses the file a...
XMLNodePointer_t Reflection(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Reflected Solid may be declared when the ReflectedSolid key...
XMLNodePointer_t TopProcess(TXMLEngine *gdml, XMLNodePointer_t node)
In the setup section of the GDML file, the top volume need to be declared.
TGeoVolume * GetVolume(const char *name)
TGeoScale * GetScaleObj(const char *name)
ReflSolidMap freflsolidmap
Map containing reflection names and the Solid name ir references to.
Definition TGDMLParse.h:219
const char * ParseGDML(TXMLEngine *gdml, XMLNodePointer_t node)
This function recursively moves thru the DOM tree of the GDML file.
XMLNodePointer_t SclProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the define section of the GDML file, rotations can be declared.
TGDMLParse()
Constructor.
XMLNodePointer_t BorderSurfaceProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the structure section of the GDML file, border surfaces can be declared.
XMLNodePointer_t Trd(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Trd may be declared.
const char * fCurrentFile
Definition TGDMLParse.h:105
TGeoRotation * GetRotation(const char *name)
void DefineConstants()
Define constant expressions used.
const char * NameShort(const char *name)
This function looks thru a string for the chars '0x' next to each other, when it finds this,...
XMLNodePointer_t Orb(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, an Orb may be declared.
FileMap ffilemap
Map containing reflected volume names and the solid ref for it.
Definition TGDMLParse.h:221
MatrixMap fmatrices
Map containing values of constants declared in the file.
Definition TGDMLParse.h:223
XMLNodePointer_t Hype(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Hype may be declared.
VolMap fvolmap
Map containing solid names and the TGeoShape for it.
Definition TGDMLParse.h:216
double GetScaleVal(const char *unit)
Throughout the GDML file, a unit can de specified.
std::string fDefault_lunit
Definition TGDMLParse.h:106
XMLNodePointer_t BooSolid(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr, int num)
In the solid section of the GDML file, boolean solids can be declared.
XMLNodePointer_t Para(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Para may be declared.
XMLNodePointer_t Arb8(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, an Arb8 may be declared.
RotMap frotmap
Map containing position names and the TGeoTranslation for it.
Definition TGDMLParse.h:208
XMLNodePointer_t PosProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the define section of the GDML file, positions can be declared.
ReflVolMap freflvolmap
Map containing reflection names and the TGDMLRefl for it - containing refl matrix.
Definition TGDMLParse.h:220
XMLNodePointer_t Sphere(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Sphere may be declared.
TString fWorldName
Definition TGDMLParse.h:98
ReflectionsMap freflectmap
Map containing placed volume names and the TGeoNode for it.
Definition TGDMLParse.h:218
XMLNodePointer_t Trap(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Trap may be declared.
TGeoVolume * fWorld
Definition TGDMLParse.h:99
std::map< std::string, double > FracMap
Definition TGDMLParse.h:204
XMLNodePointer_t EleProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLNodePointer_t parentn, Bool_t hasIsotopes, Bool_t hasIsotopesExtended)
When the element keyword is found, this function is called, and the name and values of the element ar...
XMLNodePointer_t Polyhedra(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Polyhedra may be declared.
XMLNodePointer_t Cone(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a cone may be declared.
XMLNodePointer_t ElCone(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, an elliptical cone may be declared.
MatMap fmatmap
Map containing element names and the TGeoElement for it.
Definition TGDMLParse.h:212
SclMap fsclmap
Map containing rotation names and the TGeoRotation for it.
Definition TGDMLParse.h:209
XMLNodePointer_t MatrixProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the define section of the GDML file, matrices These are referenced by other GDML tags,...
XMLNodePointer_t Tessellated(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a tessellated shape may be declared.
IsoMap fisomap
Map containing scale names and the TGeoScale for it.
Definition TGDMLParse.h:210
XMLNodePointer_t IsoProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLNodePointer_t parentn)
In the material section of the GDML file, an isotope may be declared.
PvolMap fpvolmap
Map containing volume names and the TGeoVolume for it.
Definition TGDMLParse.h:217
double Value(const char *svalue) const
Convert number in string format to double value.
TGeoTranslation * GetPosition(const char *name)
XMLNodePointer_t TwistTrap(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a TwistTrap may be declared.
MedMap fmedmap
Map containing material names and the TGeoMaterial for it.
Definition TGDMLParse.h:213
XMLNodePointer_t Paraboloid(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Paraboloid may be declared.
Int_t SetAxis(const char *axisString)
When using the 'divide' process in the geometry this function sets the variable 'axis' depending on w...
const char * fStartFile
Definition TGDMLParse.h:104
ConstMap fconsts
Map containing files parsed during entire parsing, with their world volume name.
Definition TGDMLParse.h:222
std::string fDefault_aunit
Definition TGDMLParse.h:107
XMLNodePointer_t QuantityProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the define section of the GDML file, quantities can be declared.
XMLNodePointer_t Polycone(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Polycone may be declared.
XMLNodePointer_t Box(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a box may be declared.
SolMap fsolmap
Map containing mixture names and the TGeoMixture for it.
Definition TGDMLParse.h:215
EleMap felemap
Map containing isotope names and the TGeoIsotope for it.
Definition TGDMLParse.h:211
XMLNodePointer_t Tube(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Tube may be declared.
TString GetScale(const char *unit)
Throughout the GDML file, a unit can de specified.
XMLNodePointer_t AssProcess(TXMLEngine *gdml, XMLNodePointer_t node)
In the structure section of the GDML file, assembly volumes can be declared.
PosMap fposmap
Definition TGDMLParse.h:207
TGeoShape * GetSolid(const char *name)
TXMLEngine * fFileEngine[20]
Definition TGDMLParse.h:103
XMLNodePointer_t RotProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the define section of the GDML file, rotations can be declared.
XMLNodePointer_t Torus(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Torus may be declared.
XMLNodePointer_t ConProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the define section of the GDML file, constants can be declared.
XMLNodePointer_t VolProcess(TXMLEngine *gdml, XMLNodePointer_t node)
In the structure section of the GDML file, volumes can be declared.
XMLNodePointer_t OpticalSurfaceProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, optical surfaces can be defined.
XMLNodePointer_t SkinSurfaceProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the structure section of the GDML file, skin surfaces can be declared.
XMLNodePointer_t ElTube(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a ElTube may be declared.
XMLNodePointer_t Xtru(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, an Xtru may be declared.
XMLNodePointer_t MatProcess(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr, int z)
In the materials section of the GDML file, materials can be declared.
XMLNodePointer_t CutTube(TXMLEngine *gdml, XMLNodePointer_t node, XMLAttrPointer_t attr)
In the solids section of the GDML file, a Cut Tube may be declared.
MixMap fmixmap
Map containing medium names and the TGeoMedium for it.
Definition TGDMLParse.h:214
XMLNodePointer_t UsrProcess(TXMLEngine *gdml, XMLNodePointer_t node)
User data to be processed.
This class is a helper class for TGDMLParse.
Definition TGDMLParse.h:30
const char * fNameS
Definition TGDMLParse.h:47
TGeoMatrix * fMatrix
solid name being reflected
Definition TGDMLParse.h:49
TGeoMatrix * GetMatrix()
This accessor method returns the matrix.
const char * fSolid
reflected solid name
Definition TGDMLParse.h:48
An arbitrary trapezoid with less than 8 vertices standing on two parallel planes perpendicular to Z a...
Definition TGeoArb8.h:18
virtual void SetVertex(Int_t vnum, Double_t x, Double_t y)
Set values for a given vertex.
Box class.
Definition TGeoBBox.h:18
Base class for Boolean operations between two shapes.
Class describing rotation + translation.
Definition TGeoMatrix.h:292
Composite shapes are Boolean combinations of two or more shape components.
A cone segment is a cone having a range in phi.
Definition TGeoCone.h:102
The cones are defined by 5 parameters:
Definition TGeoCone.h:18
The cut tubes constructor has the form:
Definition TGeoTube.h:172
Table of elements.
TGeoIsotope * FindIsotope(const char *name) const
Find existing isotope by name. Not optimized for a big number of isotopes.
TGeoElement * FindElement(const char *name) const
Search an element by symbol or full name Exact matching.
Base class for chemical elements.
Definition TGeoElement.h:37
Int_t Z() const
Definition TGeoElement.h:73
void AddIsotope(TGeoIsotope *isotope, Double_t relativeAbundance)
Add an isotope for this element. All isotopes have to be isotopes of the same element.
An elliptical tube is defined by the two semi-axes A and B.
Definition TGeoEltu.h:18
A twisted trapezoid.
Definition TGeoArb8.h:146
Matrix class used for computing global transformations Should NOT be used for node definition.
Definition TGeoMatrix.h:421
void SetRotation(const Double_t *matrix)
Definition TGeoMatrix.h:463
void MultiplyLeft(const TGeoMatrix *left)
multiply to the left with an other transformation if right is identity matrix, just return
void Multiply(const TGeoMatrix *right)
multiply to the right with an other transformation if right is identity matrix, just return
void SetTranslation(const Double_t *vect)
Definition TGeoMatrix.h:462
A hyperboloid is represented as a solid limited by two planes perpendicular to the Z axis (top and bo...
Definition TGeoHype.h:18
The manager class for any TGeo geometry.
Definition TGeoManager.h:45
void AddSkinSurface(TGeoSkinSurface *surf)
Add skin surface;.
static EDefaultUnits GetDefaultUnits()
TList * GetListOfMedia() const
TGeoElementTable * GetElementTable()
Returns material table. Creates it if not existing.
void AddGDMLMatrix(TGDMLMatrix *mat)
Add GDML matrix;.
void AddBorderSurface(TGeoBorderSurface *surf)
Add border surface;.
void AddOpticalSurface(TGeoOpticalSurface *optsurf)
Add optical surface;.
TGeoMedium * GetMedium(const char *medium) const
Search for a named tracking medium. All trailing blanks stripped.
Double_t GetProperty(const char *name, Bool_t *error=nullptr) const
Get a user-defined property.
TGeoOpticalSurface * GetOpticalSurface(const char *name) const
Get optical surface with a given name;.
Bool_t AddProperty(const char *property, Double_t value)
Add a user-defined property. Returns true if added, false if existing.
TGeoMaterial * GetMaterial(const char *matname) const
Search for a named material. All trailing blanks stripped.
Int_t AddRegion(TGeoRegion *region)
Add a new region of volumes.
TList * GetListOfMaterials() const
Base class describing materials.
virtual Bool_t IsMixture() const
bool AddConstProperty(const char *property, const char *ref)
bool AddProperty(const char *property, const char *ref)
Geometrical transformation package.
Definition TGeoMatrix.h:41
virtual const Double_t * GetRotationMatrix() const =0
Media are used to store properties related to tracking and which are useful only when using geometry ...
Definition TGeoMedium.h:24
Int_t GetId() const
Definition TGeoMedium.h:48
Mixtures of elements.
void AddElement(Double_t a, Double_t z, Double_t weight)
add an element to the mixture using fraction by weight Check if the element is already defined
A node represent a volume positioned inside another.They store links to both volumes and to the TGeoM...
Definition TGeoNode.h:41
This is a wrapper class to G4OpticalSurface.
static ESurfaceType StringToType(const char *type)
bool AddProperty(const char *property, const char *ref)
static ESurfaceFinish StringToFinish(const char *finish)
static ESurfaceModel StringToModel(const char *model)
Parallelepiped class.
Definition TGeoPara.h:18
A paraboloid is defined by the revolution surface generated by a parabola and is bounded by two plane...
A polycone is represented by a sequence of tubes/cones, glued together at defined Z planes.
Definition TGeoPcon.h:18
virtual void DefineSection(Int_t snum, Double_t z, Double_t rmin, Double_t rmax)
Defines z position of a section plane, rmin and rmax at this z.
Definition TGeoPcon.cxx:615
Polygons are defined in the same way as polycones, the difference being just that the segments betwee...
Definition TGeoPgon.h:21
Reference counted extension which has a pointer to and owns a user defined TObject.
Regions are groups of volumes having a common set of user tracking cuts.
Definition TGeoRegion.h:36
void AddCut(const char *name, Double_t cut)
Add cut to the region.
void AddVolume(TGeoVolume *vol)
Definition TGeoRegion.h:49
Class describing rotations.
Definition TGeoMatrix.h:175
virtual void RotateY(Double_t angle)
Rotate about Y axis of the master frame with angle expressed in degrees.
virtual void ReflectX(Bool_t leftside, Bool_t rotonly=kFALSE)
Multiply by a reflection respect to YZ.
virtual void ReflectZ(Bool_t leftside, Bool_t rotonly=kFALSE)
Multiply by a reflection respect to XY.
virtual const Double_t * GetRotationMatrix() const
Definition TGeoMatrix.h:230
void SetMatrix(const Double_t *rot)
Definition TGeoMatrix.h:225
virtual void ReflectY(Bool_t leftside, Bool_t rotonly=kFALSE)
Multiply by a reflection respect to ZX.
virtual void RotateX(Double_t angle)
Rotate about X axis of the master frame with angle expressed in degrees.
TGeoHMatrix Inverse() const
Return a temporary inverse of this.
virtual void RotateZ(Double_t angle)
Rotate about Z axis of the master frame with angle expressed in degrees.
Class describing scale transformations.
Definition TGeoMatrix.h:245
virtual const Double_t * GetScale() const
Definition TGeoMatrix.h:279
A shape scaled by a TGeoScale transformation.
Base abstract class for all shapes.
Definition TGeoShape.h:26
virtual Double_t GetAxisRange(Int_t iaxis, Double_t &xlo, Double_t &xhi) const =0
TGeoSphere are not just balls having internal and external radii, but sectors of a sphere having defi...
Definition TGeoSphere.h:18
Tessellated solid class.
The torus is defined by its axial radius, its inner and outer radius.
Definition TGeoTorus.h:18
Class describing translations.
Definition TGeoMatrix.h:122
virtual const Double_t * GetTranslation() const
Definition TGeoMatrix.h:160
A general trapezoid.
Definition TGeoArb8.h:92
A trapezoid with only X varying with Z.
Definition TGeoTrd2.h:18
A tube segment is a tube having a range in phi.
Definition TGeoTube.h:92
Cylindrical tube class.
Definition TGeoTube.h:18
Volume assemblies.
Definition TGeoVolume.h:305
virtual TGeoNode * AddNode(TGeoVolume *vol, Int_t copy_no, TGeoMatrix *mat=nullptr, Option_t *option="")
Add a component to the assembly.
TGeoVolume, TGeoVolumeMulti, TGeoVolumeAssembly are the volume classes.
Definition TGeoVolume.h:49
void SetUserExtension(TGeoExtension *ext)
Connect user-defined extension to the volume.
TGeoMedium * GetMedium() const
Definition TGeoVolume.h:174
void ReplayCreation(const TGeoVolume *other)
Recreate the content of the other volume without pointer copying.
virtual TGeoNode * AddNode(TGeoVolume *vol, Int_t copy_no, TGeoMatrix *mat=nullptr, Option_t *option="")
Add a TGeoNode to the list of nodes.
Int_t GetNdaughters() const
Definition TGeoVolume.h:351
TObjArray * GetNodes()
Definition TGeoVolume.h:168
TGeoShape * GetShape() const
Definition TGeoVolume.h:189
virtual TGeoVolume * Divide(const char *divname, Int_t iaxis, Int_t ndiv, Double_t start, Double_t step, Int_t numed=0, Option_t *option="")
Division a la G3.
A TGeoXtru shape is represented by the extrusion of an arbitrary polygon with fixed outline between s...
Definition TGeoXtru.h:23
Bool_t DefinePolygon(Int_t nvert, const Double_t *xv, const Double_t *yv)
Creates the polygon representing the blueprint of any Xtru section.
Definition TGeoXtru.cxx:691
virtual void DefineSection(Int_t snum, Double_t z, Double_t x0=0., Double_t y0=0., Double_t scale=1.)
defines z position of a section plane, rmin and rmax at this z.
Definition TGeoXtru.cxx:724
A doubly linked list.
Definition TList.h:38
TObject * FindObject(const char *name) const override
Find an object in this list using its name.
Definition TList.cxx:578
void Add(TObject *obj) override
Definition TList.h:81
TMap implements an associative array of (key,value) pairs using a THashTable for efficient retrieval ...
Definition TMap.h:40
void Add(TObject *obj) override
This function may not be used (but we need to provide it since it is a pure virtual in TCollection).
Definition TMap.cxx:54
The TNamed class is the base class for all named ROOT classes.
Definition TNamed.h:29
const char * GetName() const override
Returns name of object.
Definition TNamed.h:47
virtual void SetName(const char *name)
Set the name of the TNamed.
Definition TNamed.cxx:140
TObject * Last() const override
Return the object in the last filled slot. Returns 0 if no entries.
Collectable string class.
Definition TObjString.h:28
virtual void Warning(const char *method, const char *msgfmt,...) const
Issue warning message.
Definition TObject.cxx:956
virtual void Error(const char *method, const char *msgfmt,...) const
Issue error message.
Definition TObject.cxx:970
virtual void Fatal(const char *method, const char *msgfmt,...) const
Issue fatal error message.
Definition TObject.cxx:998
virtual void Info(const char *method, const char *msgfmt,...) const
Issue info message.
Definition TObject.cxx:944
Basic string class.
Definition TString.h:139
void ToLower()
Change string to lower-case.
Definition TString.cxx:1170
const char * Data() const
Definition TString.h:380
Bool_t IsNull() const
Definition TString.h:418
static TString Format(const char *fmt,...)
Static method which formats a string using a printf style format descriptor and return a TString.
Definition TString.cxx:2356
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
Definition TString.h:636
Ssiz_t Index(const char *pat, Ssiz_t i=0, ECaseCompare cmp=kExact) const
Definition TString.h:651
XMLNodePointer_t GetChild(XMLNodePointer_t xmlnode, Bool_t realnode=kTRUE)
returns first child of xmlnode
void FreeDoc(XMLDocPointer_t xmldoc)
frees allocated document data and deletes document itself
XMLNodePointer_t DocGetRootElement(XMLDocPointer_t xmldoc)
returns root node of document
Bool_t HasAttr(XMLNodePointer_t xmlnode, const char *name)
checks if node has attribute of specified name
XMLAttrPointer_t GetNextAttr(XMLAttrPointer_t xmlattr)
return next attribute in the list
const char * GetAttrName(XMLAttrPointer_t xmlattr)
return name of the attribute
XMLAttrPointer_t GetFirstAttr(XMLNodePointer_t xmlnode)
return first attribute in the list, namespace (if exists) will be skipped
const char * GetNodeName(XMLNodePointer_t xmlnode)
returns name of xmlnode
const char * GetAttr(XMLNodePointer_t xmlnode, const char *name)
returns value of attribute for xmlnode
XMLDocPointer_t ParseFile(const char *filename, Int_t maxbuf=100000)
Parses content of file and tries to produce xml structures.
void SetSkipComments(Bool_t on=kTRUE)
Definition TXMLEngine.h:48
const char * GetAttrValue(XMLAttrPointer_t xmlattr)
return value of attribute
XMLNodePointer_t GetNext(XMLNodePointer_t xmlnode, Bool_t realnode=kTRUE)
return next to xmlnode node if realnode==kTRUE, any special nodes in between will be skipped
void ShiftToNext(XMLNodePointer_t &xmlnode, Bool_t realnode=kTRUE)
shifts specified node to next if realnode==kTRUE, any special nodes in between will be skipped
XMLNodePointer_t GetParent(XMLNodePointer_t xmlnode)
returns parent of xmlnode
void box(Int_t pat, Double_t x1, Double_t y1, Double_t x2, Double_t y2)
Definition fillpatterns.C:1
TCanvas * fractions()
Definition fractions.C:1
Double_t y[n]
Definition legend1.C:17
Double_t x[n]
Definition legend1.C:17
const Int_t n
Definition legend1.C:16
static constexpr double GeV
static constexpr double us
static constexpr double s
static constexpr double mm
static constexpr double g
static constexpr double km
static constexpr double keV
static constexpr double ns
static constexpr double m
static constexpr double cm
static constexpr double ms
static constexpr double kg
static constexpr double mg
static constexpr double eV
static constexpr double MeV
static constexpr double mg
static constexpr double us
static constexpr double ms
static constexpr double s
static constexpr double mm
static constexpr double MeV
static constexpr double pi
static constexpr double keV
static constexpr double GeV
static constexpr double twopi
static constexpr double rad
static constexpr double kg
static constexpr double cm
static constexpr double m
static constexpr double ns
static constexpr double deg
static constexpr double eV
static constexpr double g
static constexpr double km
constexpr Double_t Pi()
Definition TMath.h:37
constexpr Double_t Na()
Avogadro constant (Avogadro's Number) in .
Definition TMath.h:284
constexpr Double_t RadToDeg()
Conversion from radian to degree: .
Definition TMath.h:72
Typedefs used by the geometry group.
Definition first.py:1
void Set(double const &a, double const &b, double const &c)
Definition TGeoVector3.h:81
TLine lv
Definition textalign.C:5