Files
geant4/source/g3tog4/src/G3toG4BuildTree.cc
T
2016-06-09 12:11:21 +02:00

199 lines
6.9 KiB
C++

//
// ********************************************************************
// * 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: G3toG4BuildTree.cc,v 1.19 2005/05/26 14:18:11 gcosmo Exp $
// GEANT4 tag $Name: geant4-07-01 $
//
// modified by I. Hrivnacova, 2.8.99
#include "globals.hh"
#include "G3toG4BuildTree.hh"
#include "G3RotTable.hh"
#include "G3MedTable.hh"
#include "G3VolTable.hh"
#include "G3SensVolVector.hh"
#include "G3Pos.hh"
#include "G4LogicalVolume.hh"
#include "G4PVPlacement.hh"
#include "G4ReflectionFactory.hh"
#include "G4Transform3D.hh"
void G3toG4BuildTree(G3VolTableEntry* curVTE, G3VolTableEntry* motherVTE)
{
G3toG4BuildLVTree(curVTE, motherVTE);
G3toG4BuildPVTree(curVTE);
}
void G3toG4BuildLVTree(G3VolTableEntry* curVTE, G3VolTableEntry* motherVTE)
{
// check existence of the solid
if (curVTE->GetSolid()) {
G4LogicalVolume* curLog = curVTE->GetLV();
if (!curLog) {
// skip creating logical volume
// in case it already exists
// material
G4Material* material = 0;
G3MedTableEntry* mte = G3Med.get(curVTE->GetNmed());
if (mte) material = mte->GetMaterial();
if (!material) {
G4Exception("VTE " + curVTE->GetName() + " has not defined material!!");
}
// logical volume
curLog =
new G4LogicalVolume(curVTE->GetSolid(), material, curVTE->GetName());
curVTE->SetLV(curLog);
// insert logical volume to G3SensVol vector
// in case it is sensitive
if (mte->GetISVOL()) G3SensVol.push_back(curLog);
}
}
else {
if ( !(curVTE->GetDivision() && motherVTE->GetMasterClone() == motherVTE &&
motherVTE->GetNoClones()>1)) {
// ignore dummy vte's
// (this should be the only case when the vte is dummy but
// is present in mother <-> daughters tree
G4Exception("VTE " + curVTE->GetName() + " has not defined solid!!");
}
}
// process daughters
G4int Ndau = curVTE->GetNoDaughters();
for (int Idau=0; Idau<Ndau; Idau++){
G3toG4BuildLVTree(curVTE->GetDaughter(Idau), curVTE);
}
}
void G3toG4BuildPVTree(G3VolTableEntry* curVTE)
{
// check existence of the solid
if (curVTE->GetSolid()) {
G4LogicalVolume* curLog = curVTE->GetLV();
// positions in motherVTE
for (G4int i=0; i<curVTE->NPCopies(); i++){
G3Pos* theG3Pos = curVTE->GetG3PosCopy(i);
if (theG3Pos) {
// loop over all mothers
for (G4int im=0; im<curVTE->GetNoMothers(); im++) {
G3VolTableEntry* motherVTE = curVTE->GetMother(im);
if (theG3Pos->GetMotherName() == motherVTE->GetMasterClone()->GetName()) {
// get mother logical volume
G4LogicalVolume* mothLV=0;
if (motherVTE) {
G4String motherName = motherVTE->GetName();
if (!curVTE->FindMother(motherName)) continue;
if (curVTE->FindMother(motherName)->GetName() != motherName) {
// check consistency - tbr
G4Exception("G3toG4BuildTree: Inconsistent mother <-> daughter !!");
}
mothLV = motherVTE->GetLV();
}
else {
mothLV = 0;
}
// copy number
// (in G3 numbering starts from 1 but in G4 from 0)
G4int copyNo = theG3Pos->GetCopy() - 1;
// position it if not top-level volume
if (mothLV != 0) {
// transformation
G4int irot = theG3Pos->GetIrot();
G4RotationMatrix* theMatrix = 0;
if (irot>0) theMatrix = G3Rot.Get(irot);
G4Rotate3D rotation;
if (theMatrix) {
rotation = G4Rotate3D(*theMatrix);
}
#ifndef G3G4_NO_REFLECTION
G4Translate3D translation(*(theG3Pos->GetPos()));
G4Transform3D transform3D = translation * (rotation.inverse());
G4ReflectionFactory::Instance()
->Place(transform3D, // transformation
curVTE->GetName(), // PV name
curLog, // its logical volume
mothLV, // mother logical volume
false, // only
copyNo); // copy
#else
new G4PVPlacement(theMatrix, // rotation matrix
*(theG3Pos->GetPos()), // its position
curLog, // its LogicalVolume
curVTE->GetName(), // PV name
mothLV, // Mother LV
0, // only
copyNo); // copy
#endif
// verbose
#ifdef G3G4DEBUG
G4cout << "PV: " << i << "th copy of " << curVTE->GetName()
<< " in " << motherVTE->GetName() << " copyNo: "
<< copyNo << " irot: " << irot << " pos: "
<< *(theG3Pos->GetPos()) << G4endl;
#endif
}
}
}
// clear this position
curVTE->ClearG3PosCopy(i);
i--;
}
}
// divisions
if (curVTE->GetDivision()) {
curVTE->GetDivision()->CreatePVReplica();
// verbose
#ifdef G3G4DEBUG
G4cout << "CreatePVReplica: " << curVTE->GetName()
<< " in " << curVTE->GetMother()->GetName() << G4endl;
#endif
// clear this divison
curVTE->ClearDivision();
}
}
// process daughters
G4int Ndau = curVTE->GetNoDaughters();
for (int Idau=0; Idau<Ndau; Idau++){
G3toG4BuildPVTree(curVTE->GetDaughter(Idau));
}
}