GeoModel - GeoModelCore
GeoPhysVol.cxx
1 /*
2  Copyright (C) 2002-2017 CERN for the benefit of the ATLAS collaboration
3 */
4 
5 #include "GeoModelKernel/GeoPhysVol.h"
6 #include "GeoModelKernel/GeoNodeAction.h"
7 #include "GeoModelKernel/GeoTransform.h"
8 #include "GeoModelKernel/GeoCountVolAction.h"
9 #include "GeoModelKernel/GeoCountVolAndSTAction.h"
10 #include "GeoModelKernel/GeoAccessVolumeAction.h"
11 
12 #include <algorithm>
13 
14 
15 GeoPhysVol::GeoPhysVol(const GeoLogVol* LogVol)
16  : GeoVPhysVol(LogVol)
17 {
18 }
19 
20 GeoPhysVol::~GeoPhysVol()
21 {
22  std::lock_guard<std::mutex> lk(m_muxVec);
23  for(const GeoGraphNode* daughter : m_daughters) daughter->unref();
24 }
25 
26 void GeoPhysVol::add(GeoGraphNode* graphNode)
27 {
28  std::lock_guard<std::mutex> lk(m_muxVec);
29  m_daughters.push_back(graphNode);
30  graphNode->ref();
31  graphNode->dockTo(this);
32 }
33 
34 unsigned int GeoPhysVol::getNChildVols() const
35 {
37  exec(&cv);
38  return cv.getCount ();
39 }
40 
41 PVConstLink GeoPhysVol::getChildVol(unsigned int index) const
42 {
43  GeoAccessVolumeAction av(index,nullptr);
44  exec(&av);
45  return av.getVolume();
46 }
47 
48 GeoTrf::Transform3D GeoPhysVol::getXToChildVol(unsigned int index
49  ,const GeoVAlignmentStore* store) const
50 {
51  GeoAccessVolumeAction av(index,store);
52  exec(&av);
53  return av.getTransform();
54 }
55 
56 GeoTrf::Transform3D GeoPhysVol::getDefXToChildVol(unsigned int index
57  ,const GeoVAlignmentStore* store) const
58 {
59  GeoAccessVolumeAction av(index,store);
60  exec(&av);
61  return av.getDefTransform();
62 }
63 
64 void GeoPhysVol::exec(GeoNodeAction *action) const
65 {
66  //
67  // Put this node on the head of the path:
68  //
69  action->getPath()->push(this);
70  if(action->getDepthLimit().isValid()
71  && action->getPath()->getLength() - 1 > action->getDepthLimit()) {
72  action->getPath ()->pop ();
73  return;
74  }
75  //
76  // Perform the action on this node:
77  //
78  action->handlePhysVol(this);
79  if(action->shouldTerminate()) {
80  action->getPath()->pop();
81  return;
82  }
83  //
84  // Pass this on to the children.
85  //
86  if(action->getDepthLimit().isValid()
87  && action->getPath()->getLength() > action->getDepthLimit()) {
88  }
89  else {
90  // FIXME: m_daughters access is now protected in other methods, but having the lock here makes a deadlock
91  // std::lock_guard<std::mutex> lk(m_muxVec);
92  // TODO: Think more thouroughly about thread-safe of this class...!!
93  for(size_t c = 0; c < m_daughters.size (); c++) {
94  m_daughters[c]->exec(action);
95  if(action->shouldTerminate()) {
96  action->getPath()->pop();
97  return;
98  }
99  }
100  }
101  //
102  // Take this node back off the head of the path:
103  //
104  action->getPath()->pop();
105 }
106 
107 std::string GeoPhysVol::getNameOfChildVol(unsigned int i) const
108 {
109  GeoAccessVolumeAction av(i,nullptr);
110  exec(&av);
111  return av.getName();
112 }
113 
115 {
116  GeoAccessVolumeAction av(i,nullptr);
117  exec(&av);
118  return av.getId();
119 }
120 
121 unsigned int GeoPhysVol::getNChildVolAndST() const
122 {
124  exec(&cv);
125  return cv.getCount();
126 }
127 
128 GeoTrf::Transform3D GeoPhysVol::getX(const GeoVAlignmentStore* store) const {
129  //
130  // Check we are not shared:
131  //
132  if (isShared()) throw std::runtime_error("Transform requested from shared volume");
133  GeoTrf::Transform3D xform(GeoTrf::Transform3D::Identity());
134  //
135  // Get the address of the first graph node, from the parent:
136  //
137  const GeoGraphNode * const * fence = getParent()->getChildNode(0);
138  const GeoGraphNode * const * node1 = getParent()->findChildNode(this);
139 
140  for(const GeoGraphNode * const * current = node1 - 1; current>=fence; current--) {
141 
142  // If this happens, we are done, compute & return--------------------//
143  // //
144  if(dynamic_cast<const GeoVPhysVol *>(*current)) break; //
145  //-------------------------------------------------------------------//
146 
147  // If this happens, we are done, compute & return--------------------//
148  // //
149  if(dynamic_cast<const GeoSerialTransformer *>(*current)) break; //
150  //-------------------------------------------------------------------//
151 
152  const GeoTransform *xf = dynamic_cast<const GeoTransform *> (*current);
153 
154  //-------------------------------------------------------------------//
155  // If this happens, accumulate into transform //
156  if (xf) xform = xf->getTransform(store)*xform; //
157  //-------------------------------------------------------------------//
158  }
159  return xform;
160 }
161 
162 GeoTrf::Transform3D GeoPhysVol::getDefX(const GeoVAlignmentStore* store) const {
163  //
164  // Check we are not shared:
165  //
166  if (isShared()) throw std::runtime_error("Transform requested from shared volume");
167  GeoTrf::Transform3D xform(GeoTrf::Transform3D::Identity());
168  //
169  // Get the address of the first graph node, from the parent:
170  //
171  const GeoGraphNode * const * fence = getParent()->getChildNode(0);
172  const GeoGraphNode * const * node1 = getParent()->findChildNode(this);
173 
174  for(const GeoGraphNode * const * current = node1 - 1; current>=fence; current--) {
175 
176  // If this happens, we are done, compute & return--------------------//
177  // //
178  if (dynamic_cast<const GeoVPhysVol *>(*current)) break; //
179  //-------------------------------------------------------------------//
180 
181  // If this happens, we are done, compute & return--------------------//
182  // //
183  if (dynamic_cast<const GeoSerialTransformer *>(*current)) break; //
184  //-------------------------------------------------------------------//
185 
186  const GeoTransform *xf = dynamic_cast<const GeoTransform *> (*current);
187 
188  //-------------------------------------------------------------------//
189  // If this happens, accumulate into transform //
190  if (xf) xform = xf->getDefTransform(store)*xform; //
191  //-------------------------------------------------------------------//
192  }
193  return xform;
194 }
195 
196 unsigned int GeoPhysVol::getNChildNodes() const
197 {
198  std::lock_guard<std::mutex> lk(m_muxVec);
199  return m_daughters.size();
200 }
201 
202 const GeoGraphNode * const * GeoPhysVol::getChildNode(unsigned int i) const
203 {
204  std::lock_guard<std::mutex> lk(m_muxVec);
205  return &(m_daughters[i]);
206 }
207 
208 const GeoGraphNode * const * GeoPhysVol::findChildNode(const GeoGraphNode * n) const
209 {
210  std::lock_guard<std::mutex> lk(m_muxVec);
211  std::vector<const GeoGraphNode *>::const_iterator i = std::find(m_daughters.begin(),m_daughters.end(),n);
212  if (i==m_daughters.end()) {
213  return nullptr;
214  }
215  else {
216  return &*i;
217  }
218 }
An action to count the number of physical volumes and Serial Transformers.
virtual void exec(GeoNodeAction *action) const override final
Executes a GeoNodeAction.
Definition: GeoPhysVol.cxx:64
virtual GeoTrf::Transform3D getTransform(const GeoVAlignmentStore *store=nullptr) const
Gets the total transformation.
A Logical Volume, or agglomeration of shape and material. The logical volume increases the reference ...
Definition: GeoLogVol.h:20
Abstract base class for GeoModel alignment stores The interface allows to store/retrieve transformati...
virtual GeoTrf::Transform3D getDefXToChildVol(unsigned int index, const GeoVAlignmentStore *store=nullptr) const override final
Returns the default transform to the ith volume.
Definition: GeoPhysVol.cxx:56
PVConstLink getVolume() const
Returns the selected physical volume or nullptr if not found.
virtual PVConstLink getChildVol(unsigned int index) const override final
Returns the ith child volume.
Definition: GeoPhysVol.cxx:41
const std::string & getName() const
Returns the name of the volume. From nametag or serial denominator.
virtual unsigned int getNChildVolAndST() const override final
Returns the number of child physical volumes and Serial Transformers.
Definition: GeoPhysVol.cxx:121
Query< int > getId() const
Returns the id of the volume. From the identifier.
virtual unsigned int getNChildVols() const override final
Returns the number of child physical volumes.
Definition: GeoPhysVol.cxx:34
virtual std::string getNameOfChildVol(unsigned int i) const override final
Returns the name of the child.
Definition: GeoPhysVol.cxx:107
virtual Query< int > getIdOfChildVol(unsigned int i) const override final
Returns the id of the child.
Definition: GeoPhysVol.cxx:114
const GeoTrf::Transform3D & getDefTransform() const
Returns the default ransformation to the volume.
This type of action sees the geometry graph in full detail, including each transformation and propert...
Definition: GeoNodeAction.h:30
const GeoTrf::Transform3D & getTransform() const
Returns the transformation to the volume.
Represents Nodes that can be assembled together to make a graph. Subclasses (for now): ...
Definition: GeoGraphNode.h:28
GeoTrf::Transform3D getDefTransform(const GeoVAlignmentStore *store=nullptr) const
Gets the default transformation (no alignment correction)
Accesses volumes, returning the ith volume and also its transformation relative to the parent...
A basic geometrical (Euclidean) transform. Can return a GeoTrf::Transform3D. Reference counted...
Definition: GeoTransform.h:22
virtual GeoTrf::Transform3D getXToChildVol(unsigned int index, const GeoVAlignmentStore *store=nullptr) const override final
Returns the transform to the ith volume.
Definition: GeoPhysVol.cxx:48