GeoModel - GeoModelCore
GeoFullPhysVol.cxx
1 /*
2  Copyright (C) 2002-2017 CERN for the benefit of the ATLAS collaboration
3 */
4 
5 #include "GeoModelKernel/GeoFullPhysVol.h"
6 #include "GeoModelKernel/GeoTransform.h"
7 #include "GeoModelKernel/GeoNodeAction.h"
8 #include "GeoModelKernel/GeoCountVolAction.h"
9 #include "GeoModelKernel/GeoCountVolAndSTAction.h"
10 #include "GeoModelKernel/GeoAccessVolumeAction.h"
11 
12 #include <algorithm>
13 
14 GeoFullPhysVol::GeoFullPhysVol (const GeoLogVol* LogVol)
15  : GeoVFullPhysVol(LogVol)
16  , m_cloneOrigin(nullptr)
17 {
18 }
19 
20 GeoFullPhysVol::~GeoFullPhysVol()
21 {
22  for(const GeoGraphNode* daughter : m_daughters) daughter->unref();
23  if(m_cloneOrigin && m_cloneOrigin!=this) m_cloneOrigin->unref();
24 }
25 
27 {
28  if(m_cloneOrigin) throw std::runtime_error("Attempt to modify contents of a cloned FPV");
29 
30  m_daughters.push_back(graphNode);
31  graphNode->ref();
32  graphNode->dockTo(this);
33 }
34 
35 unsigned int GeoFullPhysVol::getNChildVols() const
36 {
38  exec(&cv);
39  return cv.getCount();
40 }
41 
42 PVConstLink GeoFullPhysVol::getChildVol(unsigned int index) const
43 {
44  GeoAccessVolumeAction av(index,nullptr);
45  exec(&av);
46  return av.getVolume();
47 }
48 
49 GeoTrf::Transform3D GeoFullPhysVol::getXToChildVol(unsigned int index, const GeoVAlignmentStore* store) const
50 {
51  GeoAccessVolumeAction av(index,store);
52  exec(&av);
53  return av.getTransform();
54 }
55 
56 GeoTrf::Transform3D GeoFullPhysVol::getDefXToChildVol(unsigned int index, const GeoVAlignmentStore* store) const
57 {
58  GeoAccessVolumeAction av(index,store);
59  exec(&av);
60  return av.getDefTransform();
61 }
62 
64 {
65  //
66  // Put this node on the head of the path: bb
67  //
68  action->getPath()->push(this);
69  if(action->getDepthLimit().isValid()
70  && action->getPath()->getLength()-1 > action->getDepthLimit()) {
71  action->getPath()->pop();
72  return;
73  }
74  //
75  // Perform the action on this node:
76  //
77  action->handleFullPhysVol(this);
78  if(action->shouldTerminate()) {
79  action->getPath()->pop();
80  return;
81  }
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  for(size_t c = 0; c<m_daughters.size(); c++) {
91  m_daughters[c]->exec(action);
92  if(action->shouldTerminate()) {
93  action->getPath()->pop();
94  return;
95  }
96  }
97  }
98 
99  //
100  // Take this node back off the head of the path:
101  //
102  action->getPath()->pop();
103 }
104 
105 std::string GeoFullPhysVol::getNameOfChildVol(unsigned int i) const
106 {
107  GeoAccessVolumeAction av(i,nullptr);
108  exec(&av);
109  return av.getName();
110 }
111 
113 {
114  GeoAccessVolumeAction av(i,nullptr);
115  exec(&av);
116  return av.getId ();
117 }
118 
120 {
122  exec(&cv);
123  return cv.getCount();
124 }
125 
134 {
135  GeoFullPhysVol* clone = new GeoFullPhysVol(this->getLogVol());
136  for(unsigned int ind = 0; ind < this->m_daughters.size(); ind++) {
137  GeoGraphNode* daughter =(GeoGraphNode*) m_daughters[ind];
138  clone->add(daughter);
139  }
140 
141  if(attached) {
142  if(this->m_cloneOrigin==0) {
143  this->m_cloneOrigin = this;
144  }
145  clone->m_cloneOrigin = this->m_cloneOrigin;
146  this->m_cloneOrigin->ref();
147  }
148 
149  return clone;
150 }
151 
152 const GeoFullPhysVol* GeoFullPhysVol::cloneOrigin() const
153 {
154  return m_cloneOrigin;
155 }
156 
161 {
162  for(size_t i=0; i<m_daughters.size(); i++)
163  m_daughters[i]->unref();
164  m_daughters.clear();
165 }
166 
167 GeoTrf::Transform3D GeoFullPhysVol::getX(const GeoVAlignmentStore* store) const {
168  //
169  // Check we are not shared:
170  //
171  if (isShared()) throw std::runtime_error("Transform requested from shared volume");
172  GeoTrf::Transform3D xform(GeoTrf::Transform3D::Identity());
173  //
174  // Get the address of the first graph node, from the parent:
175  //
176  const GeoGraphNode * const * fence = getParent()->getChildNode(0);
177  const GeoGraphNode * const * node1 = getParent()->findChildNode(this);
178 
179  for(const GeoGraphNode * const * current = node1 - 1; current>=fence; current--) {
180 
181  // If this happens, we are done, compute & return--------------------//
182  // //
183  if (dynamic_cast<const GeoVPhysVol *>(*current)) break; //
184  //-------------------------------------------------------------------//
185 
186  // If this happens, we are done, compute & return--------------------//
187  // //
188  if (dynamic_cast<const GeoSerialTransformer *>(*current)) break; //
189  //-------------------------------------------------------------------//
190 
191  const GeoTransform *xf = dynamic_cast<const GeoTransform *> (*current);
192 
193  //-------------------------------------------------------------------//
194  // If this happens, accumulate into transform //
195  if (xf) xform = xf->getTransform(store)*xform; //
196  //-------------------------------------------------------------------//
197  }
198  return xform;
199 }
200 
201 GeoTrf::Transform3D GeoFullPhysVol::getDefX(const GeoVAlignmentStore* store) const {
202  //
203  // Check we are not shared:
204  //
205  if (isShared()) throw std::runtime_error("Transform requested from shared volume");
206  GeoTrf::Transform3D xform(GeoTrf::Transform3D::Identity());
207  //
208  // Get the address of the first graph node, from the parent:
209  //
210  const GeoGraphNode * const * fence = getParent()->getChildNode(0);
211  const GeoGraphNode * const * node1 = getParent()->findChildNode(this);
212 
213  for(const GeoGraphNode * const * current = node1 - 1; current>=fence; current--) {
214 
215  // If this happens, we are done, compute & return--------------------//
216  // //
217  if (dynamic_cast<const GeoVPhysVol *>(*current)) break; //
218  //-------------------------------------------------------------------//
219 
220  // If this happens, we are done, compute & return--------------------//
221  // //
222  if (dynamic_cast<const GeoSerialTransformer *>(*current)) break; //
223  //-------------------------------------------------------------------//
224 
225  const GeoTransform *xf = dynamic_cast<const GeoTransform *> (*current);
226 
227  //-------------------------------------------------------------------//
228  // If this happens, accumulate into transform //
229  if (xf) xform = xf->getDefTransform(store)*xform; //
230  //-------------------------------------------------------------------//
231  }
232  return xform;
233 
234 }
235 
236 unsigned int GeoFullPhysVol::getNChildNodes() const
237 {
238  return m_daughters.size();
239 }
240 
241 const GeoGraphNode * const * GeoFullPhysVol::getChildNode(unsigned int i) const
242 {
243  return &(m_daughters[i]);
244 }
245 const GeoGraphNode * const * GeoFullPhysVol::findChildNode(const GeoGraphNode * n) const
246 {
247  std::vector<const GeoGraphNode *>::const_iterator i = std::find(m_daughters.begin(),m_daughters.end(),n);
248  if (i==m_daughters.end()) {
249  return nullptr;
250  }
251  else {
252  return &*i;
253  }
254 }
virtual GeoTrf::Transform3D getXToChildVol(unsigned int index, const GeoVAlignmentStore *store=nullptr) const override
Returns the transform to the ith volume.
An action to count the number of physical volumes and Serial Transformers.
GeoFullPhysVol * clone(bool attached=true)
virtual PVConstLink getChildVol(unsigned int index) const override
Returns the ith child volume.
virtual unsigned int getNChildVols() const override
Returns the number of child physical volumes.
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...
PVConstLink getVolume() const
Returns the selected physical volume or nullptr if not found.
This class represent a physical volume whose absolute default and aligned positions are known and hel...
virtual std::string getNameOfChildVol(unsigned int i) const override
Returns the name of the child.
const std::string & getName() const
Returns the name of the volume. From nametag or serial denominator.
virtual void exec(GeoNodeAction *action) const override final
Executes a GeoNodeAction.
Query< int > getId() const
Returns the id of the volume. From the identifier.
virtual unsigned int getNChildVolAndST() const override
Returns the number of child physical volumes and Serial Transformers.
virtual GeoTrf::Transform3D getDefXToChildVol(unsigned int index, const GeoVAlignmentStore *store=nullptr) const override
Returns the default transform to the ith volume.
virtual Query< int > getIdOfChildVol(unsigned int i) const override
Returns the id of the child.
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
virtual void exec(GeoNodeAction *action) const override
Executes a GeoNodeAction.
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)
void add(GeoGraphNode *graphNode)
Adds a Graph Node to the Geometry Graph.
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