Import Geant4 4.0.0 source tree
This commit is contained in:
@@ -0,0 +1,163 @@
|
||||
//
|
||||
// ********************************************************************
|
||||
// * DISCLAIMER *
|
||||
// * *
|
||||
// * The following disclaimer summarizes all the specific disclaimers *
|
||||
// * of contributors to this software. The specific disclaimers,which *
|
||||
// * govern, are listed with their locations in: *
|
||||
// * http://cern.ch/geant4/license *
|
||||
// * *
|
||||
// * Neither the authors of this software system, nor their employing *
|
||||
// * institutes,nor the agencies providing financial support for this *
|
||||
// * work make any representation or warranty, express or implied, *
|
||||
// * regarding this software system or assume any liability for its *
|
||||
// * use. *
|
||||
// * *
|
||||
// * This code implementation is the intellectual property of the *
|
||||
// * GEANT4 collaboration. *
|
||||
// * By copying, distributing or modifying the Program (or any work *
|
||||
// * based on the Program) you indicate your acceptance of this *
|
||||
// * statement, and all its terms. *
|
||||
// ********************************************************************
|
||||
//
|
||||
//
|
||||
// $Id: G4GeomTestErrorList.cc,v 1.1 2001/10/17 12:59:57 gcosmo Exp $
|
||||
// GEANT4 tag $Name: geant4-04-00 $
|
||||
//
|
||||
// --------------------------------------------------------------------
|
||||
// GEANT 4 class source file
|
||||
//
|
||||
// G4GeomTestErrorList
|
||||
//
|
||||
// Author: D.C.Williams, UCSC (davidw@scipp.ucsc.edu)
|
||||
|
||||
#include "G4GeomTestErrorList.hh"
|
||||
#include "G4VPhysicalVolume.hh"
|
||||
|
||||
//
|
||||
// Constructor
|
||||
//
|
||||
G4GeomTestErrorList::G4GeomTestErrorList( const G4VPhysicalVolume *theMother )
|
||||
: mother(theMother)
|
||||
{
|
||||
FindGlobalCoordinateSystem();
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Destructor
|
||||
//
|
||||
G4GeomTestErrorList::~G4GeomTestErrorList() {;}
|
||||
|
||||
|
||||
//
|
||||
// AddError
|
||||
//
|
||||
// Add a new Error point to our list, where the point
|
||||
// is given in the coordinate system of the mother
|
||||
//
|
||||
void G4GeomTestErrorList::AddError( const G4ThreeVector &s1,
|
||||
const G4ThreeVector &s2 )
|
||||
{
|
||||
segments.push_back( Segment(s1,s2) );
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Accessors
|
||||
//
|
||||
const G4VPhysicalVolume *G4GeomTestErrorList::GetMother() const
|
||||
{
|
||||
return mother;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Return number of segments
|
||||
//
|
||||
G4int G4GeomTestErrorList::NumError() const
|
||||
{
|
||||
return segments.size();
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// GetMotherPoints
|
||||
//
|
||||
// Return start and end points in the coordinate system
|
||||
// of the mother
|
||||
//
|
||||
void G4GeomTestErrorList::GetMotherPoints( G4int i,
|
||||
G4ThreeVector &s1,
|
||||
G4ThreeVector &s2 ) const
|
||||
{
|
||||
s1 = segments[i].GetS1();
|
||||
s2 = segments[i].GetS2();
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// GetGlobalPoints
|
||||
//
|
||||
// Return start and end points in the global coordinate system
|
||||
//
|
||||
void G4GeomTestErrorList::GetGlobalPoints( G4int i,
|
||||
G4ThreeVector &s1,
|
||||
G4ThreeVector &s2 ) const
|
||||
{
|
||||
s1 = globalTranslation + globalRotation*segments[i].GetS1();
|
||||
s2 = globalTranslation + globalRotation*segments[i].GetS2();
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// GetOneDaughtPoints
|
||||
//
|
||||
// Return start and end points in the coordinate system of
|
||||
// a daughter
|
||||
//
|
||||
void G4GeomTestErrorList::GetOneDaughtPoints( const G4VPhysicalVolume *daught,
|
||||
G4int i,
|
||||
G4ThreeVector &s1,
|
||||
G4ThreeVector &s2 ) const
|
||||
{
|
||||
const G4RotationMatrix *rotation = daught->GetFrameRotation();
|
||||
const G4ThreeVector &translation = daught->GetFrameTranslation();
|
||||
|
||||
if (rotation) {
|
||||
s1 = (*rotation)*(translation + segments[i].GetS1());
|
||||
s2 = (*rotation)*(translation + segments[i].GetS2());
|
||||
}
|
||||
else {
|
||||
s1 = translation + segments[i].GetS1();
|
||||
s2 = translation + segments[i].GetS2();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
//
|
||||
// FindGlobalCoordinateSystem
|
||||
//
|
||||
// Calculate translation to global coordinates
|
||||
//
|
||||
void G4GeomTestErrorList::FindGlobalCoordinateSystem()
|
||||
{
|
||||
globalTranslation = G4ThreeVector(0,0,0);
|
||||
globalRotation = G4RotationMatrix();
|
||||
|
||||
const G4VPhysicalVolume *vol = mother;
|
||||
|
||||
for(;;) {
|
||||
const G4VPhysicalVolume *parent = vol->GetMother();
|
||||
if (parent == 0) break;
|
||||
|
||||
const G4RotationMatrix &rotation = vol->GetObjectRotationValue();
|
||||
const G4ThreeVector &translation = vol->GetObjectTranslation();
|
||||
|
||||
globalTranslation = translation + rotation*globalTranslation;
|
||||
globalRotation = rotation*globalRotation;
|
||||
|
||||
vol = parent;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,137 @@
|
||||
//
|
||||
// ********************************************************************
|
||||
// * DISCLAIMER *
|
||||
// * *
|
||||
// * The following disclaimer summarizes all the specific disclaimers *
|
||||
// * of contributors to this software. The specific disclaimers,which *
|
||||
// * govern, are listed with their locations in: *
|
||||
// * http://cern.ch/geant4/license *
|
||||
// * *
|
||||
// * Neither the authors of this software system, nor their employing *
|
||||
// * institutes,nor the agencies providing financial support for this *
|
||||
// * work make any representation or warranty, express or implied, *
|
||||
// * regarding this software system or assume any liability for its *
|
||||
// * use. *
|
||||
// * *
|
||||
// * This code implementation is the intellectual property of the *
|
||||
// * GEANT4 collaboration. *
|
||||
// * By copying, distributing or modifying the Program (or any work *
|
||||
// * based on the Program) you indicate your acceptance of this *
|
||||
// * statement, and all its terms. *
|
||||
// ********************************************************************
|
||||
//
|
||||
//
|
||||
// $Id: G4GeomTestOverlapList.cc,v 1.1 2001/10/17 12:59:58 gcosmo Exp $
|
||||
// GEANT4 tag $Name: geant4-04-00 $
|
||||
//
|
||||
// --------------------------------------------------------------------
|
||||
// GEANT 4 class source file
|
||||
//
|
||||
// G4GeomTestOverlapList
|
||||
//
|
||||
// Author: D.C.Williams, UCSC (davidw@scipp.ucsc.edu)
|
||||
|
||||
#include "G4GeomTestOverlapList.hh"
|
||||
|
||||
#include "G4VPhysicalVolume.hh"
|
||||
#include "G4LogicalVolume.hh"
|
||||
|
||||
//
|
||||
// Constructor
|
||||
//
|
||||
G4GeomTestOverlapList::G4GeomTestOverlapList(
|
||||
const G4VPhysicalVolume *theMother,
|
||||
G4int theDaughter1,
|
||||
G4int theDaughter2 )
|
||||
: G4GeomTestErrorList(theMother),
|
||||
daughter1(theDaughter1),
|
||||
daughter2(theDaughter2)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Default constructor
|
||||
//
|
||||
G4GeomTestOverlapList::G4GeomTestOverlapList()
|
||||
: G4GeomTestErrorList(0),
|
||||
daughter1(0),
|
||||
daughter2(0)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Destructor
|
||||
//
|
||||
G4GeomTestOverlapList::~G4GeomTestOverlapList() {;}
|
||||
|
||||
|
||||
//
|
||||
// Comparison operators
|
||||
//
|
||||
G4bool
|
||||
G4GeomTestOverlapList::operator==( const G4GeomTestOverlapList &other ) const
|
||||
{
|
||||
return daughter1==other.daughter1 && daughter2==other.daughter2;
|
||||
}
|
||||
|
||||
G4bool
|
||||
G4GeomTestOverlapList::operator< ( const G4GeomTestOverlapList &other ) const
|
||||
{
|
||||
if (daughter1 > other.daughter1) return false;
|
||||
if (daughter1 < other.daughter1) return true;
|
||||
|
||||
return (daughter2 < other.daughter2);
|
||||
}
|
||||
|
||||
|
||||
|
||||
//
|
||||
// Accessors
|
||||
//
|
||||
const G4VPhysicalVolume *G4GeomTestOverlapList::GetDaughter1() const
|
||||
{
|
||||
return GetMother()->GetLogicalVolume()->GetDaughter(daughter1);
|
||||
}
|
||||
|
||||
const G4VPhysicalVolume *G4GeomTestOverlapList::GetDaughter2() const
|
||||
{
|
||||
return GetMother()->GetLogicalVolume()->GetDaughter(daughter2);
|
||||
}
|
||||
|
||||
G4int G4GeomTestOverlapList::GetDaughter1Index() const
|
||||
{
|
||||
return daughter1;
|
||||
}
|
||||
|
||||
G4int G4GeomTestOverlapList::GetDaughter2Index() const
|
||||
{
|
||||
return daughter2;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// GetDaught1Points
|
||||
//
|
||||
// Return start and end points in the coordinate system of
|
||||
// the first daughter
|
||||
//
|
||||
void G4GeomTestOverlapList::GetDaught1Points( G4int i,
|
||||
G4ThreeVector &s1,
|
||||
G4ThreeVector &s2 ) const
|
||||
{
|
||||
GetOneDaughtPoints( GetDaughter1(), i, s1, s2 );
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// GetDaught2Points
|
||||
//
|
||||
// Return start and end points in the coordinate system of
|
||||
// the second daughter
|
||||
//
|
||||
void G4GeomTestOverlapList::GetDaught2Points( G4int i,
|
||||
G4ThreeVector &s1,
|
||||
G4ThreeVector &s2 ) const
|
||||
{
|
||||
GetOneDaughtPoints( GetDaughter2(), i, s1, s2 );
|
||||
}
|
||||
@@ -0,0 +1,107 @@
|
||||
//
|
||||
// ********************************************************************
|
||||
// * DISCLAIMER *
|
||||
// * *
|
||||
// * The following disclaimer summarizes all the specific disclaimers *
|
||||
// * of contributors to this software. The specific disclaimers,which *
|
||||
// * govern, are listed with their locations in: *
|
||||
// * http://cern.ch/geant4/license *
|
||||
// * *
|
||||
// * Neither the authors of this software system, nor their employing *
|
||||
// * institutes,nor the agencies providing financial support for this *
|
||||
// * work make any representation or warranty, express or implied, *
|
||||
// * regarding this software system or assume any liability for its *
|
||||
// * use. *
|
||||
// * *
|
||||
// * This code implementation is the intellectual property of the *
|
||||
// * GEANT4 collaboration. *
|
||||
// * By copying, distributing or modifying the Program (or any work *
|
||||
// * based on the Program) you indicate your acceptance of this *
|
||||
// * statement, and all its terms. *
|
||||
// ********************************************************************
|
||||
//
|
||||
//
|
||||
// $Id: G4GeomTestOvershootList.cc,v 1.1 2001/10/17 12:59:58 gcosmo Exp $
|
||||
// GEANT4 tag $Name: geant4-04-00 $
|
||||
//
|
||||
// --------------------------------------------------------------------
|
||||
// GEANT 4 class source file
|
||||
//
|
||||
// G4GeomTestOvershootList
|
||||
//
|
||||
// Author: D.C.Williams, UCSC (davidw@scipp.ucsc.edu)
|
||||
|
||||
#include "G4GeomTestOvershootList.hh"
|
||||
|
||||
#include "G4VPhysicalVolume.hh"
|
||||
#include "G4LogicalVolume.hh"
|
||||
|
||||
//
|
||||
// Constructor
|
||||
//
|
||||
G4GeomTestOvershootList::G4GeomTestOvershootList(
|
||||
const G4VPhysicalVolume *theMother,
|
||||
G4int theDaughterIndex )
|
||||
: G4GeomTestErrorList(theMother),
|
||||
daughter(theDaughterIndex)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Default constructor
|
||||
//
|
||||
G4GeomTestOvershootList::G4GeomTestOvershootList()
|
||||
: G4GeomTestErrorList(0),
|
||||
daughter(0)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Destructor
|
||||
//
|
||||
G4GeomTestOvershootList::~G4GeomTestOvershootList() {;}
|
||||
|
||||
|
||||
//
|
||||
// Comparison operators
|
||||
//
|
||||
G4bool
|
||||
G4GeomTestOvershootList::operator==( const G4GeomTestOvershootList &other ) const
|
||||
{
|
||||
return daughter==other.daughter;
|
||||
}
|
||||
|
||||
G4bool
|
||||
G4GeomTestOvershootList::operator< ( const G4GeomTestOvershootList &other ) const
|
||||
{
|
||||
return (daughter < other.daughter);
|
||||
}
|
||||
|
||||
|
||||
|
||||
//
|
||||
// Accessors
|
||||
//
|
||||
const G4VPhysicalVolume *G4GeomTestOvershootList::GetDaughter() const
|
||||
{
|
||||
return GetMother()->GetLogicalVolume()->GetDaughter(daughter);
|
||||
}
|
||||
|
||||
G4int G4GeomTestOvershootList::GetDaughterIndex() const
|
||||
{
|
||||
return daughter;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// GetDaughtPoints
|
||||
//
|
||||
// Return start and end points in the coordinate system of
|
||||
// the daughter
|
||||
//
|
||||
void G4GeomTestOvershootList::GetDaughtPoints( G4int i,
|
||||
G4ThreeVector &s1,
|
||||
G4ThreeVector &s2 ) const
|
||||
{
|
||||
GetOneDaughtPoints( GetDaughter(), i, s1, s2 );
|
||||
}
|
||||
@@ -0,0 +1,123 @@
|
||||
//
|
||||
// ********************************************************************
|
||||
// * DISCLAIMER *
|
||||
// * *
|
||||
// * The following disclaimer summarizes all the specific disclaimers *
|
||||
// * of contributors to this software. The specific disclaimers,which *
|
||||
// * govern, are listed with their locations in: *
|
||||
// * http://cern.ch/geant4/license *
|
||||
// * *
|
||||
// * Neither the authors of this software system, nor their employing *
|
||||
// * institutes,nor the agencies providing financial support for this *
|
||||
// * work make any representation or warranty, express or implied, *
|
||||
// * regarding this software system or assume any liability for its *
|
||||
// * use. *
|
||||
// * *
|
||||
// * This code implementation is the intellectual property of the *
|
||||
// * GEANT4 collaboration. *
|
||||
// * By copying, distributing or modifying the Program (or any work *
|
||||
// * based on the Program) you indicate your acceptance of this *
|
||||
// * statement, and all its terms. *
|
||||
// ********************************************************************
|
||||
//
|
||||
//
|
||||
// $Id: G4GeomTestPoint.cc,v 1.1 2001/10/17 12:59:58 gcosmo Exp $
|
||||
// GEANT4 tag $Name: geant4-04-00 $
|
||||
//
|
||||
// --------------------------------------------------------------------
|
||||
// GEANT 4 class source file
|
||||
//
|
||||
// G4GeomTestPoint
|
||||
//
|
||||
// Author: D.C.Williams, UCSC (davidw@scipp.ucsc.edu)
|
||||
|
||||
#include "G4GeomTestPoint.hh"
|
||||
|
||||
|
||||
//
|
||||
// Default constructor
|
||||
//
|
||||
G4GeomTestPoint::G4GeomTestPoint()
|
||||
: p(0),
|
||||
s(0),
|
||||
entering(false)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Specific constructor
|
||||
//
|
||||
G4GeomTestPoint::G4GeomTestPoint( const G4ThreeVector &thePoint,
|
||||
G4double theS,
|
||||
G4bool isEntering )
|
||||
: p(thePoint),
|
||||
s(theS),
|
||||
entering(isEntering)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Copy constructor
|
||||
//
|
||||
G4GeomTestPoint::G4GeomTestPoint( const G4GeomTestPoint &other )
|
||||
: p(other.p),
|
||||
s(other.s),
|
||||
entering(other.entering)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Destructor
|
||||
//
|
||||
G4GeomTestPoint::~G4GeomTestPoint() {;}
|
||||
|
||||
|
||||
//
|
||||
// Equivalence operator
|
||||
//
|
||||
G4bool G4GeomTestPoint::operator==( const G4GeomTestPoint &other ) const
|
||||
{
|
||||
return s == other.s;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Order operators
|
||||
//
|
||||
G4bool G4GeomTestPoint::operator<( const G4GeomTestPoint &other ) const
|
||||
{
|
||||
return s < other.s;
|
||||
}
|
||||
|
||||
G4bool G4GeomTestPoint::operator<=( const G4GeomTestPoint &other ) const
|
||||
{
|
||||
return s <= other.s;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Return position
|
||||
//
|
||||
const G4ThreeVector &G4GeomTestPoint::GetPosition() const
|
||||
{
|
||||
return p;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Return distance
|
||||
//
|
||||
G4double G4GeomTestPoint::GetDistance() const
|
||||
{
|
||||
return s;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Return true if point was entering
|
||||
//
|
||||
G4bool G4GeomTestPoint::Entering() const
|
||||
{
|
||||
return entering;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,371 @@
|
||||
//
|
||||
// ********************************************************************
|
||||
// * DISCLAIMER *
|
||||
// * *
|
||||
// * The following disclaimer summarizes all the specific disclaimers *
|
||||
// * of contributors to this software. The specific disclaimers,which *
|
||||
// * govern, are listed with their locations in: *
|
||||
// * http://cern.ch/geant4/license *
|
||||
// * *
|
||||
// * Neither the authors of this software system, nor their employing *
|
||||
// * institutes,nor the agencies providing financial support for this *
|
||||
// * work make any representation or warranty, express or implied, *
|
||||
// * regarding this software system or assume any liability for its *
|
||||
// * use. *
|
||||
// * *
|
||||
// * This code implementation is the intellectual property of the *
|
||||
// * GEANT4 collaboration. *
|
||||
// * By copying, distributing or modifying the Program (or any work *
|
||||
// * based on the Program) you indicate your acceptance of this *
|
||||
// * statement, and all its terms. *
|
||||
// ********************************************************************
|
||||
//
|
||||
//
|
||||
// $Id: G4GeomTestSegment.cc,v 1.1 2001/10/17 12:59:59 gcosmo Exp $
|
||||
// GEANT4 tag $Name: geant4-04-00 $
|
||||
//
|
||||
// --------------------------------------------------------------------
|
||||
// GEANT 4 class source file
|
||||
//
|
||||
// G4GeomTestSegment
|
||||
//
|
||||
// Author: D.C.Williams, UCSC (davidw@scipp.ucsc.edu)
|
||||
|
||||
#include "G4GeomTestSegment.hh"
|
||||
|
||||
#include "G4VSolid.hh"
|
||||
#include "G4GeomTestLogger.hh"
|
||||
|
||||
//
|
||||
// Constructor
|
||||
//
|
||||
G4GeomTestSegment::G4GeomTestSegment( const G4VSolid *theSolid,
|
||||
const G4ThreeVector &theP,
|
||||
const G4ThreeVector &theV,
|
||||
G4GeomTestLogger *logger )
|
||||
: solid(theSolid),
|
||||
p0(theP),
|
||||
v(theV)
|
||||
{
|
||||
FindPoints(logger);
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Simple accessors
|
||||
//
|
||||
const G4VSolid * G4GeomTestSegment::GetSolid() const { return solid; }
|
||||
|
||||
const G4ThreeVector &G4GeomTestSegment::GetP() const { return p0; }
|
||||
|
||||
const G4ThreeVector &G4GeomTestSegment::GetV() const { return v; }
|
||||
|
||||
|
||||
//
|
||||
// Return number points
|
||||
//
|
||||
G4int G4GeomTestSegment::GetNumberPoints() const
|
||||
{
|
||||
return points.size();
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Return ith point
|
||||
//
|
||||
const G4GeomTestPoint &G4GeomTestSegment::GetPoint( G4int i ) const
|
||||
{
|
||||
return points[i];
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// FindPoints
|
||||
//
|
||||
// Do the dirty work
|
||||
//
|
||||
void G4GeomTestSegment::FindPoints( G4GeomTestLogger *logger )
|
||||
{
|
||||
FindSomePoints( logger, true );
|
||||
FindSomePoints( logger, false );
|
||||
|
||||
PatchInconsistencies( logger );
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// PatchInconsistencies
|
||||
//
|
||||
// Search for inconsistancies in the hit list and patch
|
||||
// them up, if possible
|
||||
//
|
||||
void G4GeomTestSegment::PatchInconsistencies( G4GeomTestLogger *logger )
|
||||
{
|
||||
if (points.size() == 0) return;
|
||||
|
||||
//
|
||||
// Sort
|
||||
//
|
||||
G4std::sort( points.begin(), points.end() );
|
||||
|
||||
//
|
||||
// Loop over entering/leaving pairs
|
||||
//
|
||||
G4std::vector<G4GeomTestPoint>::iterator curr = points.begin();
|
||||
do {
|
||||
G4std::vector<G4GeomTestPoint>::iterator next = curr + 1;
|
||||
|
||||
//
|
||||
// Is the next point close by?
|
||||
//
|
||||
while (next != points.end() &&
|
||||
next->GetDistance()-curr->GetDistance() < kCarTolerance) {
|
||||
//
|
||||
// Yup. If we have an entering/leaving pair, all is okay
|
||||
//
|
||||
if (next->Entering() != curr->Entering()) {
|
||||
curr = next + 1;
|
||||
next = curr + 1;
|
||||
break;
|
||||
}
|
||||
|
||||
//
|
||||
// Otherwise, they are duplicate, and just delete one
|
||||
//
|
||||
next = points.erase(next);
|
||||
curr = next - 1;
|
||||
}
|
||||
|
||||
if (curr == points.end()) break;
|
||||
|
||||
//
|
||||
// The next point should be entering...
|
||||
//
|
||||
if (!curr->Entering()) {
|
||||
//
|
||||
// Point is out of sequence:
|
||||
// Test solid just before this point
|
||||
//
|
||||
G4double s = curr->GetDistance();
|
||||
G4ThreeVector p = p0 + s*v;
|
||||
G4ThreeVector p1 = p - 10*kCarTolerance*v;
|
||||
|
||||
if (solid->Inside(p1) == kOutside) {
|
||||
//
|
||||
// We are missing an entrance point near the current
|
||||
// point. Add one.
|
||||
//
|
||||
curr = points.insert(curr, G4GeomTestPoint( p, s, true ) );
|
||||
++curr;
|
||||
break;
|
||||
}
|
||||
|
||||
//
|
||||
// Test solid just after last point
|
||||
//
|
||||
if (curr != points.begin()) {
|
||||
G4std::vector<G4GeomTestPoint>::iterator prev = curr - 1;
|
||||
|
||||
s = prev->GetDistance();
|
||||
p = p0 + s*v;
|
||||
p1 = p + 10*kCarTolerance*v;
|
||||
|
||||
if (solid->Inside(p1) == kOutside) {
|
||||
//
|
||||
// We are missing an entrance point near the previous
|
||||
// point. Add one.
|
||||
//
|
||||
curr = points.insert(curr, G4GeomTestPoint( p, s, true ) );
|
||||
++curr;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Oh oh. No solution. Delete the current point and complain.
|
||||
//
|
||||
logger->SolidProblem( solid, "Spurious exiting intersection point", p );
|
||||
curr = points.erase(curr);
|
||||
break;
|
||||
}
|
||||
|
||||
//
|
||||
// The following point should be leaving
|
||||
//
|
||||
if (next == points.end() || next->Entering() ) {
|
||||
//
|
||||
// But is missing. Check immediately after this point.
|
||||
//
|
||||
G4double s = curr->GetDistance();
|
||||
G4ThreeVector p = p0 + s*v;
|
||||
G4ThreeVector p1 = p + 10*kCarTolerance*v;
|
||||
|
||||
if (solid->Inside(p1) == kOutside) {
|
||||
//
|
||||
// We are missing an exit point near the current
|
||||
// point. Add one.
|
||||
//
|
||||
curr = points.insert(next, G4GeomTestPoint( p, s, false ) );
|
||||
break;
|
||||
}
|
||||
|
||||
if (next != points.end()) {
|
||||
//
|
||||
// Check just before next point
|
||||
//
|
||||
s = next->GetDistance();
|
||||
p = p0 + s*v;
|
||||
p1 = p - 10*kCarTolerance*v;
|
||||
if (solid->Inside(p1) == kOutside) {
|
||||
//
|
||||
// We are missing an exit point before the next
|
||||
// point. Add one.
|
||||
//
|
||||
curr = points.insert(next, G4GeomTestPoint( p, s, false ) );
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Oh oh. Hanging entering point. Delete and complain.
|
||||
//
|
||||
logger->SolidProblem( solid, "Spurious entering intersection point", p );
|
||||
curr = points.erase(curr);
|
||||
}
|
||||
|
||||
curr = next + 1;
|
||||
} while( curr != points.end() );
|
||||
|
||||
//
|
||||
// Double check
|
||||
//
|
||||
if (points.size()&1)
|
||||
logger->SolidProblem( solid,
|
||||
"Solid has odd number of intersection points", p0 );
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Find intersections either in front or behind the point
|
||||
//
|
||||
void G4GeomTestSegment::FindSomePoints( G4GeomTestLogger *logger,
|
||||
G4bool forward )
|
||||
{
|
||||
G4double sign = forward ? +1 : -1;
|
||||
|
||||
G4ThreeVector p(p0);
|
||||
G4ThreeVector vSearch(sign*v);
|
||||
G4double s(0);
|
||||
G4bool entering;
|
||||
|
||||
//
|
||||
// Look for nearest intersection point in the specified
|
||||
// direction and return if there isn't one
|
||||
//
|
||||
G4double dist;
|
||||
switch(solid->Inside(p)) {
|
||||
case kInside:
|
||||
dist = solid->DistanceToOut(p,vSearch);
|
||||
if (dist >= kInfinity) {
|
||||
logger->SolidProblem( solid,
|
||||
"DistanceToOut(p,v) = kInfinity for point inside", p );
|
||||
return;
|
||||
}
|
||||
s += sign*dist;
|
||||
entering = false;
|
||||
break;
|
||||
case kOutside:
|
||||
dist = solid->DistanceToIn(p,vSearch);
|
||||
if (dist >= kInfinity) return;
|
||||
s += sign*dist;
|
||||
entering = true;
|
||||
break;
|
||||
case kSurface:
|
||||
entering = (v.dot(solid->SurfaceNormal(p)) > 0);
|
||||
break;
|
||||
default:
|
||||
logger->SolidProblem( solid,
|
||||
"Inside returns illegal enumerated value", p );
|
||||
return;
|
||||
}
|
||||
|
||||
//
|
||||
// Loop
|
||||
//
|
||||
// nzero = the number of consequtive zeros
|
||||
//
|
||||
G4int nzero=0;
|
||||
|
||||
for(;;) {
|
||||
//
|
||||
// Locate point
|
||||
//
|
||||
p = p0 + s*v;
|
||||
|
||||
//
|
||||
// Record point
|
||||
//
|
||||
points.push_back( G4GeomTestPoint( p, s, entering==forward ) );
|
||||
|
||||
if (nzero > 2) {
|
||||
//
|
||||
// Oops. Infinite loop. Probably a geometry bug.
|
||||
// We can give the solid a little help with a push
|
||||
//
|
||||
G4double push = 1E-6;
|
||||
s += sign*push;
|
||||
for(;;) {
|
||||
p = p0 + s*v;
|
||||
EInside inside = solid->Inside(p);
|
||||
if (inside == kInside) {
|
||||
entering = false;
|
||||
break;
|
||||
}
|
||||
else if (inside == kOutside) {
|
||||
entering = true;
|
||||
break;
|
||||
}
|
||||
|
||||
push = 2*push;
|
||||
if (push > 0.1) {
|
||||
logger->SolidProblem( solid,
|
||||
"Push fails to fix geometry inconsistency", p );
|
||||
return;
|
||||
}
|
||||
s += sign*push;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Find next intersection
|
||||
//
|
||||
G4double dist;
|
||||
if (entering) {
|
||||
dist = solid->DistanceToOut(p,vSearch);
|
||||
if (dist >= kInfinity) {
|
||||
logger->SolidProblem( solid,
|
||||
"DistanceToOut(p,v) = kInfinity for point inside", p );
|
||||
return;
|
||||
}
|
||||
entering = false;
|
||||
}
|
||||
else {
|
||||
dist = solid->DistanceToIn(p,vSearch);
|
||||
if (dist >= kInfinity) return;
|
||||
entering = true;
|
||||
}
|
||||
|
||||
//
|
||||
// Update s
|
||||
//
|
||||
if (dist <= 0) {
|
||||
nzero++;
|
||||
}
|
||||
else {
|
||||
nzero=0;
|
||||
s += sign*dist;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,285 @@
|
||||
//
|
||||
// ********************************************************************
|
||||
// * DISCLAIMER *
|
||||
// * *
|
||||
// * The following disclaimer summarizes all the specific disclaimers *
|
||||
// * of contributors to this software. The specific disclaimers,which *
|
||||
// * govern, are listed with their locations in: *
|
||||
// * http://cern.ch/geant4/license *
|
||||
// * *
|
||||
// * Neither the authors of this software system, nor their employing *
|
||||
// * institutes,nor the agencies providing financial support for this *
|
||||
// * work make any representation or warranty, express or implied, *
|
||||
// * regarding this software system or assume any liability for its *
|
||||
// * use. *
|
||||
// * *
|
||||
// * This code implementation is the intellectual property of the *
|
||||
// * GEANT4 collaboration. *
|
||||
// * By copying, distributing or modifying the Program (or any work *
|
||||
// * based on the Program) you indicate your acceptance of this *
|
||||
// * statement, and all its terms. *
|
||||
// ********************************************************************
|
||||
//
|
||||
//
|
||||
// $Id: G4GeomTestStreamLogger.cc,v 1.4 2001/10/24 22:09:28 gcosmo Exp $
|
||||
// GEANT4 tag $Name: geant4-04-00 $
|
||||
//
|
||||
// --------------------------------------------------------------------
|
||||
// GEANT 4 class source file
|
||||
//
|
||||
// G4GeomTestStreamLogger
|
||||
//
|
||||
// Author: D.C.Williams, UCSC (davidw@scipp.ucsc.edu)
|
||||
|
||||
#include "G4GeomTestStreamLogger.hh"
|
||||
#include "G4VSolid.hh"
|
||||
#include "G4VPhysicalVolume.hh"
|
||||
#include "g4std/iomanip"
|
||||
|
||||
#include "G4GeomTestOverlapList.hh"
|
||||
#include "G4GeomTestOvershootList.hh"
|
||||
|
||||
//
|
||||
// Constructor
|
||||
//
|
||||
G4GeomTestStreamLogger::G4GeomTestStreamLogger( G4std::ostream &o,
|
||||
G4int theMaxPointsPerError )
|
||||
: out(o), maxPointsPerError(theMaxPointsPerError)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// ::PrintPos
|
||||
//
|
||||
// Utility class for printing a 3 vector position
|
||||
//
|
||||
void G4GeomTestStreamLogger::PrintPos::Print( G4std::ostream &o ) const
|
||||
{
|
||||
o << G4std::setprecision(6) << G4std::setw(14) << p.x()/cm;
|
||||
o << G4std::setprecision(6) << G4std::setw(14) << p.y()/cm;
|
||||
o << G4std::setprecision(6) << G4std::setw(14) << p.z()/cm;
|
||||
if (unit) o << " cm";
|
||||
}
|
||||
|
||||
G4std::ostream &operator<<( G4std::ostream &o,
|
||||
const G4GeomTestStreamLogger::PrintPos &p )
|
||||
{
|
||||
p.Print(o);
|
||||
return o;
|
||||
}
|
||||
|
||||
//
|
||||
// ::VolumeNameAndCopy
|
||||
//
|
||||
// Utility class for printing a volume's name and copy number
|
||||
//
|
||||
void
|
||||
G4GeomTestStreamLogger::VolumeNameAndCopy::Print( G4std::ostream &o ) const
|
||||
{
|
||||
o << volume->GetName() << "[" << volume->GetCopyNo() << "]";
|
||||
}
|
||||
|
||||
G4std::ostream &operator<<( G4std::ostream &o,
|
||||
const G4GeomTestStreamLogger::VolumeNameAndCopy &p )
|
||||
{
|
||||
p.Print(o);
|
||||
return o;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// SolidProblem
|
||||
//
|
||||
void G4GeomTestStreamLogger::SolidProblem( const G4VSolid *solid,
|
||||
const G4String &message,
|
||||
const G4ThreeVector &point )
|
||||
{
|
||||
out << "GeomTest Error: SolidProblem\n"
|
||||
<< " " << message << "\n"
|
||||
<< " Solid name = " << solid->GetName() << "\n"
|
||||
<< " Local position = " << PrintPos(point) << G4std::endl;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// NoProblem
|
||||
//
|
||||
void G4GeomTestStreamLogger::NoProblem( const G4String &message )
|
||||
{
|
||||
out << message << G4std::endl;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// OverlappingDaughters
|
||||
//
|
||||
void
|
||||
G4GeomTestStreamLogger::OverlappingDaughters(const G4GeomTestOverlapList *list)
|
||||
{
|
||||
G4int n = list->NumError();
|
||||
if (n <= 0) return;
|
||||
|
||||
out << "GeomTest Error: Overlapping daughter volumes\n"
|
||||
<< " The volumes " << VolumeNameAndCopy(list->GetDaughter1())
|
||||
<< " and " << VolumeNameAndCopy(list->GetDaughter2()) << ",\n"
|
||||
<< " both daughters of volume " << VolumeNameAndCopy(list->GetMother())
|
||||
<< ",\n"
|
||||
<< " appear to overlap at the following " << (n>1 ? "points" : "point")
|
||||
<< " in global coordinates:";
|
||||
|
||||
G4int nInterval, nStop;
|
||||
|
||||
if (n <= maxPointsPerError) {
|
||||
out << "\n";
|
||||
nInterval = 1;
|
||||
nStop = n;
|
||||
}
|
||||
else {
|
||||
out << " (list truncated)\n";
|
||||
nInterval = n/maxPointsPerError;
|
||||
nStop = maxPointsPerError*nInterval;
|
||||
}
|
||||
|
||||
G4int i;
|
||||
G4ThreeVector s1, s2;
|
||||
|
||||
PrintSegmentListHeader();
|
||||
for(i=0;i<nStop;i+=nInterval) {
|
||||
list->GetGlobalPoints( i, s1, s2 );
|
||||
PrintSegmentListElement( s1, s2 );
|
||||
}
|
||||
|
||||
out << " Which in the mother coordinate system " << IsAre(n) << ":\n";
|
||||
|
||||
PrintSegmentListHeader();
|
||||
for(i=0;i<nStop;i+=nInterval) {
|
||||
list->GetMotherPoints( i, s1, s2 );
|
||||
PrintSegmentListElement( s1, s2 );
|
||||
}
|
||||
|
||||
out << " Which in the coordinate system of "
|
||||
<< VolumeNameAndCopy(list->GetDaughter1()) << " " << IsAre(n) << ":\n";
|
||||
|
||||
PrintSegmentListHeader();
|
||||
for(i=0;i<nStop;i+=nInterval) {
|
||||
list->GetDaught1Points( i, s1, s2 );
|
||||
PrintSegmentListElement( s1, s2 );
|
||||
}
|
||||
|
||||
out << " Which in the coordinate system of "
|
||||
<< VolumeNameAndCopy(list->GetDaughter2()) << " " << IsAre(n) << ":\n";
|
||||
|
||||
PrintSegmentListHeader();
|
||||
for(i=0;i<nStop;i+=nInterval) {
|
||||
list->GetDaught2Points( i, s1, s2 );
|
||||
PrintSegmentListElement( s1, s2 );
|
||||
}
|
||||
|
||||
out << G4std::endl;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// OvershootingDaughter
|
||||
//
|
||||
void G4GeomTestStreamLogger::
|
||||
OvershootingDaughter( const G4GeomTestOvershootList *list )
|
||||
{
|
||||
G4int n = list->NumError();
|
||||
if (n <= 0) return;
|
||||
|
||||
out << "GeomTest Error: Overshooting daughter volume\n"
|
||||
<< " The volume " << VolumeNameAndCopy(list->GetDaughter())
|
||||
<< " appears to extend outside the mother volume "
|
||||
<< VolumeNameAndCopy(list->GetMother()) << "\n"
|
||||
<< " at the following " << (n>1 ? "points" : "point")
|
||||
<< " in global coordinates:";
|
||||
|
||||
|
||||
G4int nInterval, nStop;
|
||||
|
||||
if (n <= maxPointsPerError) {
|
||||
out << "\n";
|
||||
nInterval = 1;
|
||||
nStop = n;
|
||||
}
|
||||
else {
|
||||
out << " (list truncated)\n";
|
||||
nInterval = n/maxPointsPerError;
|
||||
nStop = maxPointsPerError*nInterval;
|
||||
}
|
||||
|
||||
G4int i;
|
||||
G4ThreeVector s1, s2;
|
||||
|
||||
PrintSegmentListHeader();
|
||||
for(i=0;i<nStop;i+=nInterval) {
|
||||
list->GetGlobalPoints( i, s1, s2 );
|
||||
PrintSegmentListElement( s1, s2 );
|
||||
}
|
||||
|
||||
out << " Which in the mother coordinate system " << IsAre(n) << ":\n";
|
||||
|
||||
PrintSegmentListHeader();
|
||||
for(i=0;i<nStop;i+=nInterval) {
|
||||
list->GetMotherPoints( i, s1, s2 );
|
||||
PrintSegmentListElement( s1, s2 );
|
||||
}
|
||||
|
||||
out << " Which in the coordinate system of "
|
||||
<< VolumeNameAndCopy(list->GetDaughter()) << " " << IsAre(n) << ":\n";
|
||||
|
||||
PrintSegmentListHeader();
|
||||
for(i=0;i<nStop;i+=nInterval) {
|
||||
list->GetDaughtPoints( i, s1, s2 );
|
||||
PrintSegmentListElement( s1, s2 );
|
||||
}
|
||||
|
||||
out << G4std::endl;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//
|
||||
// PrintSegmentListHeader (protected)
|
||||
//
|
||||
// Print out a header for a segment list
|
||||
//
|
||||
void G4GeomTestStreamLogger::PrintSegmentListHeader()
|
||||
{
|
||||
static const char *header =
|
||||
" length (cm) ---------- start position (cm) ----------- ----------- end position (cm) ------------\n";
|
||||
// .............| .............|.............|.............| .............|.............|.............|
|
||||
// 1234 1234 123
|
||||
|
||||
out << header;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// PrintSegmentListElement (protected)
|
||||
//
|
||||
// Print out one segment value
|
||||
//
|
||||
void G4GeomTestStreamLogger::PrintSegmentListElement( const G4ThreeVector &s1,
|
||||
const G4ThreeVector &s2 )
|
||||
{
|
||||
out << " " << G4std::setprecision(6) << G4std::setw(14)
|
||||
<< (s1-s2).mag()/cm
|
||||
<< " " << PrintPos(s1,false) << " " << PrintPos(s2,false) << "\n";
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// IsAre (protected)
|
||||
//
|
||||
// Return a pointer to the string "is" if the argument
|
||||
// is equal to 1, otherwise return a pointer to "are"
|
||||
//
|
||||
const char *G4GeomTestStreamLogger::IsAre( G4int n )
|
||||
{
|
||||
const char *is = "is";
|
||||
const char *are = "are";
|
||||
|
||||
return n > 1 ? are : is;
|
||||
}
|
||||
@@ -0,0 +1,105 @@
|
||||
//
|
||||
// ********************************************************************
|
||||
// * DISCLAIMER *
|
||||
// * *
|
||||
// * The following disclaimer summarizes all the specific disclaimers *
|
||||
// * of contributors to this software. The specific disclaimers,which *
|
||||
// * govern, are listed with their locations in: *
|
||||
// * http://cern.ch/geant4/license *
|
||||
// * *
|
||||
// * Neither the authors of this software system, nor their employing *
|
||||
// * institutes,nor the agencies providing financial support for this *
|
||||
// * work make any representation or warranty, express or implied, *
|
||||
// * regarding this software system or assume any liability for its *
|
||||
// * use. *
|
||||
// * *
|
||||
// * This code implementation is the intellectual property of the *
|
||||
// * GEANT4 collaboration. *
|
||||
// * By copying, distributing or modifying the Program (or any work *
|
||||
// * based on the Program) you indicate your acceptance of this *
|
||||
// * statement, and all its terms. *
|
||||
// ********************************************************************
|
||||
//
|
||||
//
|
||||
// $Id: G4GeomTestVolPoint.cc,v 1.1 2001/10/17 13:00:00 gcosmo Exp $
|
||||
// GEANT4 tag $Name: geant4-04-00 $
|
||||
//
|
||||
// --------------------------------------------------------------------
|
||||
// GEANT 4 class source file
|
||||
//
|
||||
// G4GeomTestVolPoint
|
||||
//
|
||||
// Author: D.C.Williams, UCSC (davidw@scipp.ucsc.edu)
|
||||
|
||||
#include "G4GeomTestVolPoint.hh"
|
||||
|
||||
//
|
||||
// Constructor (specific)
|
||||
//
|
||||
G4GeomTestVolPoint::G4GeomTestVolPoint( const G4ThreeVector &thePoint,
|
||||
G4double theS,
|
||||
G4bool isEntering,
|
||||
G4int theDaughterIndex )
|
||||
: G4GeomTestPoint( thePoint, theS, isEntering ),
|
||||
daughterIndex(theDaughterIndex)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Constructor (from base)
|
||||
//
|
||||
G4GeomTestVolPoint::G4GeomTestVolPoint( const G4GeomTestPoint &base,
|
||||
G4int theDaughterIndex )
|
||||
: G4GeomTestPoint( base ), daughterIndex(theDaughterIndex)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Constructor (from base, with coordinate transformation)
|
||||
//
|
||||
G4GeomTestVolPoint::G4GeomTestVolPoint( const G4GeomTestPoint &base,
|
||||
G4int theDaughterIndex,
|
||||
const G4ThreeVector &translation,
|
||||
const G4RotationMatrix *rotation )
|
||||
: G4GeomTestPoint( base ), daughterIndex(theDaughterIndex)
|
||||
{
|
||||
//
|
||||
// Rotate point
|
||||
//
|
||||
if (rotation)
|
||||
p = rotation->inverse()*p - translation;
|
||||
else
|
||||
p = p - translation;
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// Constructor (copy)
|
||||
//
|
||||
G4GeomTestVolPoint::G4GeomTestVolPoint( const G4GeomTestVolPoint &other )
|
||||
: G4GeomTestPoint( other ), daughterIndex(other.daughterIndex)
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Constructor (default)
|
||||
//
|
||||
G4GeomTestVolPoint::G4GeomTestVolPoint()
|
||||
: daughterIndex(-1)
|
||||
{;}
|
||||
|
||||
|
||||
|
||||
//
|
||||
// Destructor
|
||||
//
|
||||
G4GeomTestVolPoint::~G4GeomTestVolPoint() {;}
|
||||
|
||||
|
||||
//
|
||||
// Volume accessor
|
||||
//
|
||||
G4int G4GeomTestVolPoint::GetDaughterIndex() const
|
||||
{
|
||||
return daughterIndex;
|
||||
}
|
||||
@@ -0,0 +1,542 @@
|
||||
//
|
||||
// ********************************************************************
|
||||
// * DISCLAIMER *
|
||||
// * *
|
||||
// * The following disclaimer summarizes all the specific disclaimers *
|
||||
// * of contributors to this software. The specific disclaimers,which *
|
||||
// * govern, are listed with their locations in: *
|
||||
// * http://cern.ch/geant4/license *
|
||||
// * *
|
||||
// * Neither the authors of this software system, nor their employing *
|
||||
// * institutes,nor the agencies providing financial support for this *
|
||||
// * work make any representation or warranty, express or implied, *
|
||||
// * regarding this software system or assume any liability for its *
|
||||
// * use. *
|
||||
// * *
|
||||
// * This code implementation is the intellectual property of the *
|
||||
// * GEANT4 collaboration. *
|
||||
// * By copying, distributing or modifying the Program (or any work *
|
||||
// * based on the Program) you indicate your acceptance of this *
|
||||
// * statement, and all its terms. *
|
||||
// ********************************************************************
|
||||
//
|
||||
//
|
||||
// $Id: G4GeomTestVolume.cc,v 1.4 2001/10/24 22:09:28 gcosmo Exp $
|
||||
// GEANT4 tag $Name: geant4-04-00 $
|
||||
//
|
||||
// --------------------------------------------------------------------
|
||||
// GEANT 4 class source file
|
||||
//
|
||||
// G4GeomTestVolume
|
||||
//
|
||||
// Author: D.C.Williams, UCSC (davidw@scipp.ucsc.edu)
|
||||
|
||||
#include "G4GeomTestVolume.hh"
|
||||
|
||||
#include "G4GeomTestLogger.hh"
|
||||
#include "G4GeomTestVolPoint.hh"
|
||||
#include "G4GeomTestSegment.hh"
|
||||
|
||||
#include "G4VPhysicalVolume.hh"
|
||||
#include "G4LogicalVolume.hh"
|
||||
#include "G4VSolid.hh"
|
||||
|
||||
#include "g4std/vector"
|
||||
#include "g4std/set"
|
||||
#include "g4std/algorithm"
|
||||
#include "g4std/iomanip"
|
||||
|
||||
//
|
||||
// Constructor
|
||||
//
|
||||
G4GeomTestVolume::G4GeomTestVolume( const G4VPhysicalVolume *theTarget,
|
||||
G4GeomTestLogger *theLogger,
|
||||
G4double theTolerance )
|
||||
: target(theTarget),
|
||||
logger(theLogger),
|
||||
tolerance(theTolerance),
|
||||
extent(theTarget->GetLogicalVolume()->GetSolid()->GetExtent())
|
||||
{;}
|
||||
|
||||
|
||||
//
|
||||
// Destructor
|
||||
//
|
||||
G4GeomTestVolume::~G4GeomTestVolume() {;}
|
||||
|
||||
//
|
||||
// Get error tolerance
|
||||
//
|
||||
G4double G4GeomTestVolume::GetTolerance() const
|
||||
{
|
||||
return tolerance;
|
||||
}
|
||||
|
||||
//
|
||||
// Set error tolerance
|
||||
//
|
||||
void G4GeomTestVolume::SetTolerance(G4double val)
|
||||
{
|
||||
tolerance = val;
|
||||
}
|
||||
|
||||
//
|
||||
// TestCartGridXYZ
|
||||
//
|
||||
void G4GeomTestVolume::TestCartGridXYZ( G4int nx, G4int ny, G4int nz )
|
||||
{
|
||||
TestCartGridX( ny, nz );
|
||||
TestCartGridY( nz, nx );
|
||||
TestCartGridZ( nx, ny );
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// TestCartGridX
|
||||
//
|
||||
void G4GeomTestVolume::TestCartGridX( G4int ny, G4int nz )
|
||||
{
|
||||
TestCartGrid( G4ThreeVector(0,1,0), G4ThreeVector(0,0,1),
|
||||
G4ThreeVector(1,0,0), ny, nz );
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// TestCartGridY
|
||||
//
|
||||
void G4GeomTestVolume::TestCartGridY( G4int nz, G4int nx )
|
||||
{
|
||||
TestCartGrid( G4ThreeVector(0,0,1), G4ThreeVector(1,0,0),
|
||||
G4ThreeVector(0,1,0), nz, nx );
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// TestCartGridZ
|
||||
//
|
||||
void G4GeomTestVolume::TestCartGridZ( G4int nx, G4int ny )
|
||||
{
|
||||
TestCartGrid( G4ThreeVector(1,0,0), G4ThreeVector(0,1,0),
|
||||
G4ThreeVector(0,0,1), nx, ny );
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// TestRecursiveCartGrid
|
||||
//
|
||||
void G4GeomTestVolume::TestRecursiveCartGrid( G4int nx, G4int ny, G4int nz )
|
||||
{
|
||||
//
|
||||
// As long as we aren't a replica, test ourselves
|
||||
//
|
||||
if (!target->IsReplicated()) {
|
||||
TestCartGridXYZ( nx, ny, nz );
|
||||
ReportErrors();
|
||||
}
|
||||
|
||||
//
|
||||
// Loop over unique daughters
|
||||
//
|
||||
G4std::set<const G4LogicalVolume *> tested;
|
||||
|
||||
const G4LogicalVolume *logical = target->GetLogicalVolume();
|
||||
G4int nDaughter = logical->GetNoDaughters();
|
||||
G4int iDaughter;
|
||||
for( iDaughter=0; iDaughter<nDaughter; ++iDaughter) {
|
||||
const G4VPhysicalVolume *daughter =
|
||||
logical->GetDaughter(iDaughter);
|
||||
const G4LogicalVolume *daughterLogical =
|
||||
daughter->GetLogicalVolume();
|
||||
|
||||
//
|
||||
// Skip empty daughters
|
||||
//
|
||||
if (daughterLogical->GetNoDaughters() == 0) continue;
|
||||
|
||||
//
|
||||
// Tested already?
|
||||
//
|
||||
G4std::pair<G4std::set<const G4LogicalVolume *>::iterator,G4bool>
|
||||
there = tested.insert(daughterLogical);
|
||||
if (!there.second) continue;
|
||||
|
||||
//
|
||||
// Recurse
|
||||
//
|
||||
G4GeomTestVolume vTest( daughter, logger );
|
||||
vTest.TestRecursiveCartGrid(nx,ny,nz);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// TestCylinder
|
||||
//
|
||||
void G4GeomTestVolume::TestCylinder( G4int nPhi, G4int nZ, G4int nRho,
|
||||
G4double fracZ, G4double fracRho,
|
||||
G4bool usePhi )
|
||||
{
|
||||
//
|
||||
// Get size of our volume
|
||||
//
|
||||
G4double xMax = G4std::max(extent.GetXmax(),-extent.GetXmin());
|
||||
G4double yMax = G4std::max(extent.GetYmax(),-extent.GetYmin());
|
||||
G4double rhoMax = sqrt(xMax*xMax + yMax*yMax);
|
||||
|
||||
G4double zMax = extent.GetZmax();
|
||||
G4double zMin = extent.GetZmin();
|
||||
G4double zHalfLength = 0.5*(zMax-zMin);
|
||||
G4double z0 = 0.5*(zMax+zMin);
|
||||
|
||||
//
|
||||
// Loop over phi
|
||||
//
|
||||
G4double deltaPhi = 2*pi/G4double(nPhi);
|
||||
|
||||
G4double phi = 0;
|
||||
G4int iPhi = nPhi;
|
||||
if ((iPhi&1) == 0) iPhi++; // Also use odd number phi slices
|
||||
do {
|
||||
G4double cosPhi = cos(phi);
|
||||
G4double sinPhi = sin(phi);
|
||||
|
||||
//
|
||||
// Loop over rho
|
||||
//
|
||||
G4double rho = rhoMax;
|
||||
G4int iRho = nRho;
|
||||
do {
|
||||
G4ThreeVector p(rho*cosPhi,rho*sinPhi,0);
|
||||
static G4ThreeVector v(0,0,1);
|
||||
|
||||
TestOneLine( p, v );
|
||||
|
||||
if (usePhi) {
|
||||
//
|
||||
// Loop over z
|
||||
//
|
||||
G4ThreeVector v(sinPhi,-cosPhi,0);
|
||||
|
||||
G4double zScale = 1.0;
|
||||
G4int iZ=nZ;
|
||||
do {
|
||||
p.setZ( z0 + zScale*zHalfLength );
|
||||
TestOneLine(p,v);
|
||||
p.setZ( z0 - zScale*zHalfLength );
|
||||
TestOneLine(p,v);
|
||||
} while( zScale *= fracZ, --iZ );
|
||||
}
|
||||
} while( rho *= fracRho, --iRho );
|
||||
|
||||
//
|
||||
// Loop over z
|
||||
//
|
||||
G4ThreeVector p(0,0,0);
|
||||
G4ThreeVector v(cosPhi,sinPhi,0);
|
||||
|
||||
G4double zScale = 1.0;
|
||||
G4int iZ=nZ;
|
||||
do {
|
||||
p.setZ( z0 + zScale*zHalfLength );
|
||||
|
||||
TestOneLine(p,v);
|
||||
|
||||
p.setZ( z0 - zScale*zHalfLength );
|
||||
|
||||
TestOneLine(p,v);
|
||||
} while( zScale *= fracZ, --iZ );
|
||||
|
||||
} while( phi += deltaPhi, --iPhi );
|
||||
}
|
||||
|
||||
|
||||
|
||||
//
|
||||
// TestCartGrid
|
||||
//
|
||||
void G4GeomTestVolume::TestCartGrid( const G4ThreeVector &theG1,
|
||||
const G4ThreeVector &theG2,
|
||||
const G4ThreeVector &theV,
|
||||
G4int n1, G4int n2 )
|
||||
{
|
||||
if (n1 <= 0 || n2 <= 0)
|
||||
G4Exception( "G4GeomTestVolume::TestCartGrid -- n1 and n2 must be >= 1" );
|
||||
|
||||
G4ThreeVector xMin( extent.GetXmin(), extent.GetYmin(),
|
||||
extent.GetZmin() );
|
||||
G4ThreeVector xMax( extent.GetXmax(), extent.GetYmax(),
|
||||
extent.GetZmax() );
|
||||
|
||||
G4ThreeVector g1(theG1.unit());
|
||||
G4ThreeVector g2(theG2.unit());
|
||||
G4ThreeVector v(theV.unit());
|
||||
|
||||
G4double gMin1 = g1.dot(xMin);
|
||||
G4double gMax1 = g1.dot(xMax);
|
||||
|
||||
G4double gMin2 = g2.dot(xMin);
|
||||
G4double gMax2 = g2.dot(xMax);
|
||||
|
||||
G4double delta1 = (gMax1-gMin1)/G4double(n1);
|
||||
G4double delta2 = (gMax2-gMin2)/G4double(n2);
|
||||
|
||||
G4int i1, i2;
|
||||
|
||||
for(i1=0;i1<=n1;++i1) {
|
||||
G4ThreeVector p1 = (gMin1 + G4double(i1)*delta1)*g1;
|
||||
|
||||
for(i2=0;i2<=n2;++i2) {
|
||||
G4ThreeVector p2 = (gMin2 + G4double(i2)*delta2)*g2;
|
||||
|
||||
TestOneLine( p1+p2, v );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
//
|
||||
// TestOneLine
|
||||
//
|
||||
// Test geometry consistency along a single line
|
||||
//
|
||||
void G4GeomTestVolume::TestOneLine( const G4ThreeVector &p,
|
||||
const G4ThreeVector &v )
|
||||
{
|
||||
//
|
||||
// Keep track of intersection points
|
||||
//
|
||||
G4std::vector<G4GeomTestVolPoint> points;
|
||||
|
||||
//
|
||||
// Calculate intersections with the mother volume
|
||||
//
|
||||
G4GeomTestSegment targetSegment( target->GetLogicalVolume()->GetSolid(),
|
||||
p, v, logger );
|
||||
|
||||
//
|
||||
// Add them to our list
|
||||
//
|
||||
G4int n = targetSegment.GetNumberPoints();
|
||||
G4int i;
|
||||
for(i=0;i<n;++i) {
|
||||
points.push_back( G4GeomTestVolPoint( targetSegment.GetPoint(i), -1 ) );
|
||||
}
|
||||
|
||||
//
|
||||
// Loop over daughter volumes
|
||||
//
|
||||
const G4LogicalVolume *logical = target->GetLogicalVolume();
|
||||
G4int nDaughter = logical->GetNoDaughters();
|
||||
G4int iDaughter;
|
||||
for( iDaughter=0; iDaughter<nDaughter; ++iDaughter) {
|
||||
const G4VPhysicalVolume *daughter =
|
||||
logical->GetDaughter(iDaughter);
|
||||
|
||||
//
|
||||
// Convert coordinates to daughter local coordinates
|
||||
//
|
||||
const G4RotationMatrix *rotation = daughter->GetFrameRotation();
|
||||
const G4ThreeVector &translation = daughter->GetFrameTranslation();
|
||||
|
||||
G4ThreeVector pLocal = translation + p;
|
||||
G4ThreeVector vLocal = v;
|
||||
|
||||
if (rotation) {
|
||||
pLocal = (*rotation)*pLocal;
|
||||
vLocal = (*rotation)*vLocal;
|
||||
}
|
||||
|
||||
//
|
||||
// Find intersections
|
||||
//
|
||||
G4GeomTestSegment
|
||||
daughterSegment( daughter->GetLogicalVolume()->GetSolid(),
|
||||
pLocal, vLocal, logger );
|
||||
|
||||
//
|
||||
// Add them to the list
|
||||
//
|
||||
G4int n = daughterSegment.GetNumberPoints();
|
||||
G4int i;
|
||||
for(i=0;i<n;++i) {
|
||||
points.push_back( G4GeomTestVolPoint( daughterSegment.GetPoint(i),
|
||||
iDaughter, translation, rotation ) );
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Now sort the list of intersection points
|
||||
//
|
||||
G4std::sort( points.begin(), points.end() );
|
||||
|
||||
//
|
||||
// Search for problems:
|
||||
// 1. Overlap daughters will be indicated by intersecting
|
||||
// points that lie within another daughter
|
||||
// 2. Daughter extending outside the mother will be
|
||||
// indicated by intersecting points outside the mother
|
||||
//
|
||||
// The search method is always looking forward when
|
||||
// resolving discrepencies due to roundoff error. Once
|
||||
// one instance of a daughter intersection is analyzed,
|
||||
// it is removed from further consideration
|
||||
//
|
||||
n = points.size();
|
||||
|
||||
//
|
||||
// Set true if this point has been analyzed
|
||||
//
|
||||
G4std::vector<G4bool> checked( n, false );
|
||||
|
||||
for(i=0;i<n;++i) {
|
||||
if (checked[i]) continue;
|
||||
|
||||
G4int iDaug = points[i].GetDaughterIndex();
|
||||
if (iDaug < 0) continue;
|
||||
|
||||
//
|
||||
// Intersection found. Find matching pair.
|
||||
//
|
||||
G4double iS = points[i].GetDistance();
|
||||
G4int j = i;
|
||||
while(++j<n) {
|
||||
if (iDaug == points[j].GetDaughterIndex()) break;
|
||||
}
|
||||
if (j>=n) {
|
||||
//
|
||||
// Unmatched? This shouldn't happen
|
||||
//
|
||||
logger->SolidProblem( logical->GetDaughter(iDaug)->
|
||||
GetLogicalVolume()->GetSolid(),
|
||||
"Unmatched intersection point",
|
||||
points[i].GetPosition() );
|
||||
continue;
|
||||
}
|
||||
|
||||
checked[j] = true;
|
||||
|
||||
G4double jS = points[j].GetDistance();
|
||||
|
||||
//
|
||||
// Otherwise, we could have a problem
|
||||
//
|
||||
G4int k = i;
|
||||
while(++k<j) {
|
||||
if (checked[k]) continue;
|
||||
|
||||
G4bool kEntering = points[k].Entering();
|
||||
G4double kS = points[k].GetDistance();
|
||||
|
||||
|
||||
//
|
||||
// Problem found: catagorize
|
||||
//
|
||||
G4int kDaug = points[k].GetDaughterIndex();
|
||||
if (kDaug < 0) {
|
||||
//
|
||||
// Ignore small overshoots if they are within tolerance
|
||||
//
|
||||
if (kS-iS < tolerance && kEntering ) continue;
|
||||
if (jS-kS < tolerance && (!kEntering)) continue;
|
||||
|
||||
//
|
||||
// We appear to extend outside the mother volume
|
||||
//
|
||||
G4std::map<G4long,G4GeomTestOvershootList>::iterator overshoot =
|
||||
overshoots.find(iDaug);
|
||||
if (overshoot == overshoots.end()) {
|
||||
G4std::pair<G4std::map<G4long,G4GeomTestOvershootList>::iterator,G4bool>
|
||||
result =
|
||||
overshoots.insert( G4std::pair<const G4long,G4GeomTestOvershootList>
|
||||
(iDaug,G4GeomTestOvershootList(target,iDaug)) );
|
||||
assert(result.second);
|
||||
overshoot = result.first;
|
||||
}
|
||||
|
||||
if (kEntering)
|
||||
(*overshoot).second.AddError( points[i].GetPosition(),
|
||||
points[k].GetPosition() );
|
||||
else
|
||||
(*overshoot).second.AddError( points[k].GetPosition(),
|
||||
points[j].GetPosition() );
|
||||
}
|
||||
else {
|
||||
//
|
||||
// Ignore small overlaps if they are within tolerance
|
||||
//
|
||||
if (kS-iS < tolerance && (!kEntering)) continue;
|
||||
if (jS-kS < tolerance && kEntering ) continue;
|
||||
|
||||
//
|
||||
// We appear to overlap with another daughter
|
||||
//
|
||||
G4long key = iDaug < kDaug ?
|
||||
(iDaug*nDaughter + kDaug) : (kDaug*nDaughter + iDaug);
|
||||
|
||||
G4std::map<G4long,G4GeomTestOverlapList>::iterator overlap =
|
||||
overlaps.find(key);
|
||||
if (overlap == overlaps.end()) {
|
||||
G4std::pair<G4std::map<G4long,G4GeomTestOverlapList>::iterator,G4bool>
|
||||
result =
|
||||
overlaps.insert( G4std::pair<const G4long,G4GeomTestOverlapList>
|
||||
(key,G4GeomTestOverlapList(target,iDaug,kDaug)) );
|
||||
assert(result.second);
|
||||
overlap = result.first;
|
||||
}
|
||||
|
||||
if (points[k].Entering())
|
||||
(*overlap).second.AddError( points[k].GetPosition(),
|
||||
points[j].GetPosition() );
|
||||
else
|
||||
(*overlap).second.AddError( points[i].GetPosition(),
|
||||
points[k].GetPosition() );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//
|
||||
// ReportErrors
|
||||
//
|
||||
void G4GeomTestVolume::ReportErrors()
|
||||
{
|
||||
//
|
||||
// Report overshoots
|
||||
//
|
||||
if (overshoots.empty())
|
||||
logger->NoProblem("GeomTest: no daughter volume extending outside mother detected.");
|
||||
else {
|
||||
G4std::map<G4long,G4GeomTestOvershootList>::iterator overshoot =
|
||||
overshoots.begin();
|
||||
while( overshoot != overshoots.end() ) {
|
||||
logger->OvershootingDaughter( &(*overshoot).second );
|
||||
++overshoot;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Report overlaps
|
||||
//
|
||||
if (overlaps.empty())
|
||||
logger->NoProblem("GeomTest: no overlapping daughters detected.");
|
||||
else {
|
||||
G4std::map<G4long,G4GeomTestOverlapList>::iterator overlap =
|
||||
overlaps.begin();
|
||||
while( overlap != overlaps.end() ) {
|
||||
logger->OverlappingDaughters( &(*overlap).second );
|
||||
++overlap;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//
|
||||
// ClearErrors
|
||||
//
|
||||
void G4GeomTestVolume::ClearErrors()
|
||||
{
|
||||
overshoots.clear();
|
||||
overlaps.clear();
|
||||
}
|
||||
Reference in New Issue
Block a user