ECCE @ EIC Software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
G4Navigator.hh
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file G4Navigator.hh
1 //
2 // ********************************************************************
3 // * License and Disclaimer *
4 // * *
5 // * The Geant4 software is copyright of the Copyright Holders of *
6 // * the Geant4 Collaboration. It is provided under the terms and *
7 // * conditions of the Geant4 Software License, included in the file *
8 // * LICENSE and available at http://cern.ch/geant4/license . These *
9 // * include a list of copyright holders. *
10 // * *
11 // * Neither the authors of this software system, nor their employing *
12 // * institutes,nor the agencies providing financial support for this *
13 // * work make any representation or warranty, express or implied, *
14 // * regarding this software system or assume any liability for its *
15 // * use. Please see the license in the file LICENSE and URL above *
16 // * for the full disclaimer and the limitation of liability. *
17 // * *
18 // * This code implementation is the result of the scientific and *
19 // * technical work of the GEANT4 collaboration. *
20 // * By using, copying, modifying or distributing the software (or *
21 // * any work based on the software) you agree to acknowledge its *
22 // * use in resulting scientific publications, and indicate your *
23 // * acceptance of all terms of the Geant4 Software license. *
24 // ********************************************************************
25 //
26 // class G4Navigator
27 //
28 // Class description:
29 //
30 // A class for use by the tracking management, able to obtain/calculate
31 // dynamic tracking time information such as the distance to the next volume,
32 // or to find the physical volume containing a given point in the world
33 // reference system. The navigator maintains a transformation history and
34 // other information to optimise the tracking time performance.
35 
36 // - Created. Paul Kent, Jul 95/96
37 // - Made Navigator Abstract G. Cosmo, Nov 2003
38 // - Added check mode G. Cosmo, Mar 2004
39 // - Zero step protections J.A. / G.C., Nov 2004
40 // *********************************************************************
41 
42 #ifndef G4NAVIGATOR_HH
43 #define G4NAVIGATOR_HH
44 
45 #include "geomdefs.hh"
46 
47 #include "G4ThreeVector.hh"
48 #include "G4AffineTransform.hh"
49 #include "G4RotationMatrix.hh"
50 
51 #include "G4LogicalVolume.hh" // Used in inline methods
52 #include "G4GRSVolume.hh" // " "
53 #include "G4GRSSolid.hh" // " "
54 #include "G4TouchableHandle.hh" // " "
56 
57 #include "G4NavigationHistory.hh"
58 #include "G4NormalNavigation.hh"
59 #include "G4VoxelNavigation.hh"
61 #include "G4ReplicaNavigation.hh"
62 #include "G4RegularNavigation.hh"
63 #include "G4VExternalNavigation.hh"
64 
65 #include <iostream>
66 
67 class G4VPhysicalVolume;
68 
70 {
71  public: // with description
72 
73  friend std::ostream& operator << (std::ostream &os, const G4Navigator &n);
74 
75  G4Navigator();
76  // Constructor - initialisers and setup.
77 
78  G4Navigator(const G4Navigator&) = delete;
79  G4Navigator& operator=(const G4Navigator&) = delete;
80  // Copy constructor & assignment operator not allowed.
81 
82  virtual ~G4Navigator();
83  // Destructor. No actions.
84 
85  virtual G4double ComputeStep(const G4ThreeVector& pGlobalPoint,
86  const G4ThreeVector& pDirection,
87  const G4double pCurrentProposedStepLength,
88  G4double& pNewSafety);
89  // Calculate the distance to the next boundary intersected
90  // along the specified NORMALISED vector direction and
91  // from the specified point in the global coordinate
92  // system. LocateGlobalPointAndSetup or LocateGlobalPointWithinVolume
93  // must have been called with the same global point prior to this call.
94  // The isotropic distance to the nearest boundary is also
95  // calculated (usually an underestimate). The current
96  // proposed Step length is used to avoid intersection
97  // calculations: if it can be determined that the nearest
98  // boundary is >pCurrentProposedStepLength away, kInfinity
99  // is returned together with the computed isotropic safety
100  // distance. Geometry must be closed.
101 
102  G4double CheckNextStep(const G4ThreeVector& pGlobalPoint,
103  const G4ThreeVector& pDirection,
104  const G4double pCurrentProposedStepLength,
105  G4double& pNewSafety);
106  // Same as above, but do not disturb the state of the Navigator.
107 
108  virtual
110  const G4ThreeVector& direction,
111  const G4TouchableHistory& h);
112 
113  // Resets the geometrical hierarchy and search for the volumes deepest
114  // in the hierarchy containing the point in the global coordinate space.
115  // The direction is used to check if a volume is entered.
116  // The search begin is the geometrical hierarchy at the location of the
117  // last located point, or the endpoint of the previous Step if
118  // SetGeometricallyLimitedStep() has been called immediately before.
119  //
120  // Important Note: In order to call this the geometry MUST be closed.
121 
122  virtual
124  const G4ThreeVector* direction = nullptr,
125  const G4bool pRelativeSearch = true,
126  const G4bool ignoreDirection = true);
127  // Search the geometrical hierarchy for the volumes deepest in the hierarchy
128  // containing the point in the global coordinate space. Two main cases are:
129  // i) If pRelativeSearch=false it makes use of no previous/state
130  // information. Returns the physical volume containing the point,
131  // with all previous mothers correctly set up.
132  // ii) If pRelativeSearch is set to true, the search begin is the
133  // geometrical hierarchy at the location of the last located point,
134  // or the endpoint of the previous Step if SetGeometricallyLimitedStep()
135  // has been called immediately before.
136  // The direction is used (to check if a volume is entered) if either
137  // - the argument ignoreDirection is false, or
138  // - the Navigator has determined that it is on an edge shared by two or
139  // more volumes. (This is state information.)
140  //
141  // Important Note: In order to call this the geometry MUST be closed.
142 
143  virtual
145  // Notify the Navigator that a track has moved to the new Global point
146  // 'position', that is known to be within the current safety.
147  // No check is performed to ensure that it is within the volume.
148  // This method can be called instead of LocateGlobalPointAndSetup ONLY if
149  // the caller is certain that the new global point (position) is inside the
150  // same volume as the previous position. Usually this can be guaranteed
151  // only if the point is within safety.
152 
154  const G4ThreeVector& position,
155  const G4ThreeVector& direction,
156  G4TouchableHandle& oldTouchableToUpdate,
157  const G4bool RelativeSearch = true);
158  // First, search the geometrical hierarchy like the above method
159  // LocateGlobalPointAndSetup(). Then use the volume found and its
160  // navigation history to update the touchable.
161 
163  const G4ThreeVector& position,
164  const G4ThreeVector& direction,
165  G4VTouchable* touchableToUpdate,
166  const G4bool RelativeSearch = true);
167  // First, search the geometrical hierarchy like the above method
168  // LocateGlobalPointAndSetup(). Then use the volume found and its
169  // navigation history to update the touchable.
170 
172  const G4ThreeVector& position,
173  G4VTouchable* touchableToUpdate,
174  const G4bool RelativeSearch = true);
175  // Same as the method above but missing direction.
176 
177  inline void SetGeometricallyLimitedStep();
178  // Inform the navigator that the previous Step calculated
179  // by the geometry was taken in its entirety.
180 
181  virtual G4double ComputeSafety(const G4ThreeVector& globalpoint,
182  const G4double pProposedMaxLength = DBL_MAX,
183  const G4bool keepState = true);
184  // Calculate the isotropic distance to the nearest boundary from the
185  // specified point in the global coordinate system.
186  // The globalpoint utilised must be within the current volume.
187  // The value returned is usually an underestimate.
188  // The proposed maximum length is used to avoid volume safety
189  // calculations. The geometry must be closed.
190  // To ensure minimum side effects from the call, keepState
191  // must be true.
192 
194  const G4ThreeVector& pGlobalPoint,
195  const G4ThreeVector& pDirection,
196  const G4double CurrentProposedStepLength,
197  G4double* prDistance,
198  G4double* prNewSafety = nullptr) const;
199  // Trial method for checking potential displacement for MS
200  // Check new Globalpoint, to see whether it is in current volume
201  // (mother) and not in potential entering daughter.
202  // If in mother, check distance to boundary along pDirection.
203  // If in entering daughter, check distance back to boundary.
204  // NOTE:
205  // Can be called only after ComputeStep is called - before ReLocation
206  // Deals only with current volume (and potentially entered)
207 
208  inline G4VPhysicalVolume* GetWorldVolume() const;
209  // Return the current world (`topmost') volume.
210 
211  inline void SetWorldVolume(G4VPhysicalVolume* pWorld);
212  // Set the world (`topmost') volume. This must be positioned at
213  // origin (0,0,0) and unrotated.
214 
215  inline G4GRSVolume* CreateGRSVolume() const;
216  inline G4GRSSolid* CreateGRSSolid() const;
219  // `Touchable' creation methods: caller has deletion responsibility.
220 
222  // Returns a reference counted handle to a touchable history.
223 
226  G4bool* valid);
227  virtual G4ThreeVector GetGlobalExitNormal(const G4ThreeVector& point,
228  G4bool* valid);
229  // Return Exit Surface Normal and validity too.
230  // Can only be called if the Navigator's last Step has crossed a
231  // volume geometrical boundary.
232  // It returns the Normal to the surface pointing out of the volume that
233  // was left behind and/or into the volume that was entered.
234  // Convention:
235  // The *local* normal is in the coordinate system of the *final* volume.
236  // Restriction:
237  // Normals are not available for replica volumes (returns valid= false)
238  // These methods takes full care about how to calculate this normal,
239  // but if the surfaces are not convex it will return valid=false.
240 
241  inline G4int GetVerboseLevel() const;
242  inline void SetVerboseLevel(G4int level);
243  // Get/Set Verbose(ness) level.
244  // [if level>0 && G4VERBOSE, printout can occur]
245 
246  inline G4bool IsActive() const;
247  // Verify if the navigator is active.
248  inline void Activate(G4bool flag);
249  // Activate/inactivate the navigator.
250 
251  inline G4bool EnteredDaughterVolume() const;
252  // The purpose of this function is to inform the caller if the track is
253  // entering a daughter volume while exiting from the current volume.
254  // This method returns
255  // - True only in case 1) above, that is when the Step has caused
256  // the track to arrive at a boundary of a daughter.
257  // - False in cases 2), 3) and 4), i.e. in all other cases.
258  // This function is not guaranteed to work if SetGeometricallyLimitedStep()
259  // was not called when it should have been called.
260  inline G4bool ExitedMotherVolume() const;
261  // Verify if the step has exited the mother volume.
262 
263  inline void CheckMode(G4bool mode);
264  // Run navigation in "check-mode", therefore using additional
265  // verifications and more strict correctness conditions.
266  // Is effective only with G4VERBOSE set.
267  inline G4bool IsCheckModeActive() const;
268  inline void SetPushVerbosity(G4bool mode);
269  // Set/unset verbosity for pushed tracks (default is true).
270 
271  void PrintState() const;
272  // Print the internal state of the Navigator (for debugging).
273  // The level of detail is according to the verbosity.
274 
275  inline const G4AffineTransform& GetGlobalToLocalTransform() const;
276  inline const G4AffineTransform GetLocalToGlobalTransform() const;
277  // Obtain the transformations Global/Local (and inverse).
278  // Clients of these methods must copy the data if they need to keep it.
279 
281  G4int dReplicaNo,
282  EVolume dVolumeType );
283  // Obtain mother to daughter transformation
284 
285  inline void ResetStackAndState();
286  // Reset stack and minimum or navigator state machine necessary for reset
287  // as needed by LocalGlobalPointAndSetup.
288  // [Does not perform clears, resizes, or reset fLastLocatedPointLocal]
289 
290  inline G4int SeverityOfZeroStepping( G4int* noZeroSteps ) const;
291  // Report on severity of error and number of zero steps,
292  // in case Navigator is stuck and is returning zero steps.
293  // Values: 1 (small problem), 5 (correcting),
294  // 9 (ready to abandon), 10 (abandoned)
295 
297  // Return the local coordinate of the point in the reference system
298  // of its containing volume that was found by LocalGlobalPointAndSetup.
299  // The local coordinate of the last located track.
300 
301  inline G4ThreeVector NetTranslation() const;
302  inline G4RotationMatrix NetRotation() const;
303  // Compute+return the local->global translation/rotation of current volume.
304 
305  inline void EnableBestSafety( G4bool value = false );
306  // Enable best-possible evaluation of isotropic safety.
307 
309  inline void SetExternalNavigation(G4VExternalNavigation* externalNav);
310  // Accessor & modifier for custom external navigation.
311 
312  inline G4Navigator* Clone() const;
313  // Cloning feature for use in MT applications to clone
314  // navigator, including external sub-navigator.
315  // Client has responsibility for ownership of returned allocated pointer.
316 
317  protected: // with description
318 
319  void SetSavedState();
320  // ( fValidExitNormal, fExitNormal, fExiting, fEntering,
321  // fBlockedPhysicalVolume, fBlockedReplicaNo, fLastStepWasZero);
322  // Extended to include:
323  // ( fLastLocatedPointLocal, fLocatedOutsideWorld;
324  // fEnteredDaughter, fExitedMother
325  // fPreviousSftOrigin, sPreviousSafety) Safety Sphere.
326 
327  void RestoreSavedState();
328  // Copy aspects of the state, to enable a non-state changing
329  // call to ComputeStep().
330 
331  virtual void ResetState();
332  // Utility method to reset the navigator state machine.
333 
334  inline G4ThreeVector ComputeLocalPoint(const G4ThreeVector& rGlobPoint) const;
335  // Return position vector in local coordinate system, given a position
336  // vector in world coordinate system.
337 
338  inline G4ThreeVector ComputeLocalAxis(const G4ThreeVector& pVec) const;
339  // Return the local direction of the specified vector in the reference
340  // system of the volume that was found by LocalGlobalPointAndSetup.
341  // The Local Coordinates of point in world coordinate system.
342 
343  inline EVolume VolumeType(const G4VPhysicalVolume *pVol) const;
344  // Characterise `type' of volume - normal/replicated/parameterised.
345 
346  inline EVolume CharacteriseDaughters(const G4LogicalVolume *pLog) const;
347  // Characterise daughter of logical volume.
348 
349  inline G4int GetDaughtersRegularStructureId(const G4LogicalVolume *pLv) const;
350  // Get regular structure ID of first daughter
351 
352  virtual void SetupHierarchy();
353  // Renavigate & reset hierarchy described by current history
354  // o Reset volumes
355  // o Recompute transforms and/or solids of replicated/parameterised
356  // volumes.
357 
359  // Utility method to trigger overlaps check on a volume with reported
360  // overlaps ordered by relevance. Used in ComputeStep() when loopings
361  // with zero step are detected.
362 
363  private:
364 
365  void ComputeStepLog(const G4ThreeVector& pGlobalpoint,
366  G4double moveLenSq) const;
367  // Log and checks for steps larger than the tolerance
368 
369  protected: // without description
370 
372  // Cached tolerances.
373 
374  //
375  // BEGIN State information
376  //
377 
379  // Transformation and history of the current path
380  // through the geometrical hierarchy.
381 
383  // A memory of whether in this Step a daughter volume is entered
384  // (set in Compute & Locate).
385  // After Compute: it expects to enter a daughter
386  // After Locate: it has entered a daughter
387 
389  // A similar memory whether the Step exited current "mother" volume
390  // completely, not entering daughter.
391 
393  // Set true if last Step was limited by geometry.
394 
396  // Endpoint of last ComputeStep
397  // can be used for optimisation (e.g. when computing safety).
399  // Position of the end-point of the last call to ComputeStep
400  // in last Local coordinates.
401 
403  // Verbose(ness) level [if > 0, printout can occur].
404 
405  private:
406 
407  G4bool fActive = false;
408  // States if the navigator is activated or not.
409 
411  // Whether ComputeStep was called since the last call to a Locate method
412  // Uses: - distinguish parts of state which differ before/after calls
413  // to ComputeStep or one of the Locate methods;
414  // - avoid two consecutive calls to compute-step (illegal).
415 
417  // Entering/Exiting volumes blocking/setup
418  // o If exiting
419  // volume ptr & replica number (set & used by Locate..())
420  // used for blocking on redescent of geometry
421  // o If entering
422  // volume ptr & replica number (set by ComputeStep(),used by
423  // Locate..()) of volume for `automatic' entry
424 
427 
429  // Position of the last located point relative to its containing volume.
431  // Whether the last call to Locate methods left the world
432 
433  G4bool fValidExitNormal; // Set true if have leaving volume normal
434  G4ThreeVector fExitNormal; // Leaving volume normal, in the
435  // volume containing the exited
436  // volume's coordinate system
437  G4ThreeVector fGrandMotherExitNormal; // Leaving volume normal, in its
438  // own coordinate system
439  G4bool fChangedGrandMotherRefFrame; // Whether frame is changed
440 
441  G4ThreeVector fExitNormalGlobalFrame; // Leaving volume normal, in the
442  // global coordinate system
443  G4bool fCalculatedExitNormal; // Has it been computed since
444  // the last call to ComputeStep
445  // Covers both Global and GrandMother
446 
447  // Count zero steps - as one or two can occur due to changing momentum at
448  // a boundary or at an edge common between volumes
449  // - several are likely a problem in the geometry
450  // description or in the navigation
451  //
453  // Whether the last ComputeStep moved Zero. Used to check for edges.
454 
456  // Whether the Navigator has detected an edge
458  // Number of preceding moves that were Zero. Reset to 0 after finite step
460  // After this many failed/zero steps, act (push etc)
462  // After this many failed/zero steps, abandon track
463 
466  // Memory of last safety origin & value. Used in ComputeStep to ensure
467  // that origin of current Step is in the same volume as the point of the
468  // last relocation
469 
471  // Memory of the mother volume during previous step.
472  // Intended use: inform user in case of stuck track.
473 
474  //
475  // END State information
476  //
477 
478  // Save key state information (NOT the navigation history stack)
479  //
481  {
489 
490  // Potentially relevant
491  //
497  } fSaveState;
498 
499  // Tracking Invariants
500  //
502  // A link to the topmost physical volume in the detector.
503  // Must be positioned at the origin and unrotated.
504 
505  // Utility information
506  //
507  G4bool fCheck = false;
508  // Check-mode flag [if true, more strict checks are performed].
509  G4bool fPushed = false, fWarnPush = true;
510  // Push flags [if true, means a stuck particle has been pushed].
511 
512  // Helpers/Utility classes
513  //
521 };
522 
523 #include "G4Navigator.icc"
524 
525 #endif
526 
527 
528 // NOTES:
529 //
530 // The following methods provide detailed information when a Step has
531 // arrived at a geometrical boundary. They distinguish between the different
532 // causes that can result in the track leaving its current volume.
533 //
534 // Four cases are possible:
535 //
536 // 1) The particle has reached a boundary of a daughter of the current volume:
537 // (this could cause the relocation to enter the daughter itself
538 // or a potential granddaughter or further descendant)
539 //
540 // 2) The particle has reached a boundary of the current
541 // volume, exiting into a mother (regardless the level
542 // at which it is located in the tree):
543 //
544 // 3) The particle has reached a boundary of the current
545 // volume, exiting into a volume which is not in its
546 // parental hierarchy:
547 //
548 // 4) The particle is not on a boundary between volumes:
549 // the function returns an exception, and the caller is
550 // reccomended to compare the G4touchables associated
551 // to the preStepPoint and postStepPoint to handle this case.
552 //
553 // G4bool EnteredDaughterVolume()
554 // G4bool IsExitNormalValid()
555 // G4ThreeVector GetLocalExitNormal()
556 //
557 // The expected usefulness of these methods is to allow the caller to
558 // determine how to compute the surface normal at the volume boundary. The two
559 // possibilities are to obtain the normal from:
560 //
561 // i) the solid associated with the volume of the initial point of the Step.
562 // This is valid for cases 2 and 3.
563 // (Note that the initial point is generally the PreStepPoint of a Step).
564 // or
565 //
566 // ii) the solid of the final point, ie of the volume after the relocation.
567 // This is valid for case 1.
568 // (Note that the final point is generally the PreStepPoint of a Step).
569 //
570 // This way the caller can always get a valid normal, pointing outside
571 // the solid for which it is computed, that can be used at his own
572 // discretion.