/search.css" rel="stylesheet" type="text/css"/> /search.js">
| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

In This Package:

Public Member Functions | Static Public Member Functions | Private Member Functions | Private Attributes
AutoPositionerTool Class Reference

Implementation of IPositionerTool which automatically determines parent volume and support path. More...

#include <AutoPositionerTool.h>

Inheritance diagram for AutoPositionerTool:
Inheritance graph
[legend]
Collaboration diagram for AutoPositionerTool:
Collaboration graph
[legend]

List of all members.

Public Member Functions

 AutoPositionerTool (const std::string &type, const std::string &name, const IInterface *parent)
 ~AutoPositionerTool ()
virtual StatusCode initialize ()
virtual StatusCode reinitialize ()
virtual StatusCode finalize ()
virtual StatusCode queryInterface (const InterfaceID &riid, void **ppvInterface)
StatusCode placeVolume ()
 IPositionerTool interface.

Static Public Member Functions

static const InterfaceID & interfaceID ()

Private Member Functions

StatusCode addDetectorElement (std::string detElemName, std::string detElemPath, std::string logVolName, std::string support, std::string npath)

Private Attributes

IDataProviderSvc * m_detSvc
ICoordSysSvcm_coordSvc
std::string m_physVolName
std::string m_logVolName
std::string m_coordDetElemPath
std::vector< double > m_position
std::vector< double > m_rotation
std::string m_detElemName
std::string m_detElemPath
std::vector< std::vector
< std::string > > 
m_subDetElements

Detailed Description

Implementation of IPositionerTool which automatically determines parent volume and support path.

Example Use:

DiffBallPositioner.PhysicalVolume = "pvDiffuserBall" DiffBallPositioner.LogicalVolume = "/dd/Geometry/CalibrationSources/lvDiffuserBall" DiffBallPositioner.CoordinateDetElem = "/dd/Structure/AD/db-oil1" DiffBallPositioner.Position = [0., 0., 0.] DiffBallPositioner.Rotation = [0., 0., 0., 0., 0., 0., 0., 0., 0.] DiffBallPositioner.Element = "db-diffuserBallCenter1"

dandwyer@caltech.edu 25/11/2008

Definition at line 28 of file AutoPositionerTool.h.


Constructor & Destructor Documentation

AutoPositionerTool::AutoPositionerTool ( const std::string &  type,
const std::string &  name,
const IInterface *  parent 
)

Definition at line 16 of file AutoPositionerTool.cc.

  : GaudiTool(type, name, parent)
  , m_detSvc(0)
  , m_coordSvc(0)
{
  declareProperty("PhysicalVolume",m_physVolName="",
                  "Name of the physical volume to add to geometry");
  declareProperty("LogicalVolume",m_logVolName="",
                  "Name of the logical volume to associate with the physical");
  declareProperty("CoordinateDetElem",m_coordDetElemPath="",
                  "Name of the detector element used for coordinates");
  declareProperty("Position",m_position=std::vector<double>(3,0.),
                  "Position of the new volume in the parent coordinates");
  double identity[] = {1., 0., 0., 
                       0., 1., 0.,
                       0., 0., 1.};
  declareProperty("Rotation",m_rotation=std::vector<double>(identity,
                                                            identity+9),
                  "Rotation of the new volume in the parent coordinates");
  declareProperty("Element",m_detElemName="",
                  "Name of the detector element to place in the TDS");
  declareProperty("ElementPath",m_detElemPath="/dd/Structure/DayaBay",
                  "Path for the new detector element in the TDS");
  declareProperty("SubDetectorElements",
                  m_subDetElements=std::vector< std::vector<std::string> >(),
                  "Information for defining additional daughter detector elements");
}
AutoPositionerTool::~AutoPositionerTool ( )

Definition at line 46 of file AutoPositionerTool.cc.

{
}

Member Function Documentation

StatusCode AutoPositionerTool::initialize ( ) [virtual]

Definition at line 50 of file AutoPositionerTool.cc.

{
    this->GaudiTool::initialize();

    debug() << "AutoPositionerTool::initialize()" << endreq;
    StatusCode sc = service("DetectorDataSvc",m_detSvc,true);
    if (sc.isFailure()) return sc;

    sc = service("CoordSysSvc",m_coordSvc,true);
    if (sc.isFailure()) return sc;

    return sc;
}
StatusCode AutoPositionerTool::reinitialize ( ) [virtual]

Definition at line 64 of file AutoPositionerTool.cc.

{
    return StatusCode::SUCCESS;
}
StatusCode AutoPositionerTool::finalize ( ) [virtual]

Definition at line 69 of file AutoPositionerTool.cc.

{
    m_detSvc->release();
    m_coordSvc->release();
    return this->GaudiTool::finalize();
}
StatusCode AutoPositionerTool::queryInterface ( const InterfaceID &  riid,
void **  ppvInterface 
) [virtual]

Definition at line 76 of file AutoPositionerTool.cc.

{
  StatusCode sc = StatusCode::FAILURE;
  if (ppvInterface) {
    *ppvInterface = 0;
    
    if (IPositionerTool::interfaceID().versionMatch(riid)) {
      *ppvInterface = static_cast<IPositionerTool*>(this);
      sc = StatusCode::SUCCESS;
      addRef();
    }
    else sc = GaudiTool::queryInterface( riid, ppvInterface );    
  }
  return sc;
}
StatusCode AutoPositionerTool::placeVolume ( ) [virtual]

IPositionerTool interface.

Place volume in the geometry.

Place a volume in the geometry

Implements IPositionerTool.

Definition at line 97 of file AutoPositionerTool.cc.

{

  // Find placement detector element based on coordinate volume
  IDetectorElement* coordDetElem = getDet<IDetectorElement>(m_coordDetElemPath);
  if(!coordDetElem){
    error() << "AutoPositionerTool::placeVolume(): "
            << "could not find detector element at: " << m_coordDetElemPath
            << endreq;
    return StatusCode::FAILURE;
  }

  // Find global coordinates of new volume
  Gaudi::XYZPoint referencePosition(m_position[0],m_position[1],m_position[2]);
  Gaudi::XYZPoint globalPosition = 
    coordDetElem->geometry()->toGlobal( referencePosition );

  info() << "Using " << coordDetElem->name() 
         << " as reference system for placement of " << m_detElemName 
         << " at local position " << referencePosition 
         << " and global position " << globalPosition << endreq;

  // Find parent detector element
  IDetectorElement* parentDetElem = m_coordSvc->belongsToDE(globalPosition);
  if(!parentDetElem){
    error() << "AutoPositionerTool::placeVolume(): "
            << "could not find detector element at global position: " 
            << globalPosition << endreq;
    return StatusCode::FAILURE;
  }
  info() << "Using " << parentDetElem->name() 
         << " as supporting element for placement of " 
         << m_detElemName << endreq;

  // Find parent logical volume and relative path
  //IGeometryInfo* parentGeometry = 
  //  parentDetElem->geometry()->belongsTo(globalPosition, -1);
  //std::string npath;
  IGeometryInfo* startGeom = parentDetElem->geometry();
  ILVolume::PVolumePath pvPath;
  StatusCode sc = 
    parentDetElem->geometry()->fullGeoInfoForPoint(globalPosition, -1,
                                                   startGeom, pvPath);
  if(!sc.isSuccess()){
    error() << "AutoPositionerTool::placeVolume(): "
            << "could not find parent geometry at global position: " 
            << globalPosition << endreq;
    return StatusCode::FAILURE;
  }
  info() << "FullGeoInfoForPoint: " << startGeom->lvolumeName() << endreq;
  ILVolume::PVolumePath::iterator pvPathIter, pvPathEnd = pvPath.end();
  std::string npath;
  std::string parentLVolName = startGeom->lvolumeName();
  for(pvPathIter = pvPath.begin(); pvPathIter != pvPathEnd; pvPathIter++){
    parentLVolName = (*pvPathIter)->lvolumeName();
    if( npath.size() > 0 ) npath.append( "/" );
    npath.append( (*pvPathIter)->name() );
    info() << "  npath: " << npath << endreq;
  }
  if( npath.size() > 0 ){
    error() << "Parent volume " << parentLVolName 
            << " must have a defined detector element."
            << " Please define a detector element, and then you can place "
            <<  m_logVolName << " inside." << endreq;
    return StatusCode::FAILURE;
  }
  info() << "Using " << parentLVolName 
         << " as parent volume for placement of " << m_logVolName << endreq;
  IGeometryInfo* parentGeometry = parentDetElem->geometry();

  // Find parent logical volume for physical volume
  SmartDataPtr<LVolume> parentLogVol(m_detSvc, parentLVolName);
  if(!parentLogVol){
    error() << "AutoPositionerTool::placeVolume(): "
            << "could not find parent volume of name: " << parentLVolName
            << endreq;
    return StatusCode::FAILURE;
  }

  // Check if physical volume already exists in parent logical volume
  bool pvolumeExists = false;
  ILVolume::PVolumes::const_iterator pvIter = parentLogVol->pvBegin();
  for(;pvIter != parentLogVol->pvEnd(); pvIter++){
    if((*pvIter)->name() == m_physVolName){
      warning() << "AutoPositionerTool::placeVolume(): "
                << "physical volume " << m_physVolName
                << " already exists in parent volume " << parentLVolName
                << endreq;
      pvolumeExists = true;
      break;
    }
  }

  if( !pvolumeExists ){
    // Place physical volume
    // Find placement coordinates in local parent volume
    Gaudi::XYZPoint localPosition = parentGeometry->toLocal( globalPosition );
    Gaudi::XYZPoint parGlobalPosition = 
      parentGeometry->toGlobal( Gaudi::XYZPoint(0.,0.,0.) );
    info() << "Parent Global position is " << parGlobalPosition << endreq;
    info() << "CoordRef Global position is " << globalPosition << endreq;
    info() << "Difference is " << parGlobalPosition - globalPosition << endreq;
    info() << "Placing " << m_detElemName 
           << " at " << localPosition << " in parent volume " 
           << parentLVolName<< endreq;

    // Check if point is inside
    if( parentLogVol->isInside(localPosition) ){
      info() << "Yep, position " << localPosition
             << "is inside " << parentLVolName<< endreq;
    }else{
      info() << "Ack!  Position " << localPosition
             << "is not inside " << parentLVolName << endreq;
    }      

    {
      const SolidBase* solid = dynamic_cast<const SolidBase*>(parentLogVol->solid());
      info() << "X-extent: " << solid->xMin() << " " << solid->xMax() << endreq;
      info() << "Y-extent: " << solid->yMin() << " " << solid->yMax() << endreq;
      info() << "Z-extent: " << solid->zMin() << " " << solid->zMax() << endreq;
    }
    {
      SmartDataPtr<LVolume> logVol(m_detSvc, m_logVolName);
      const SolidBase* solid = dynamic_cast<const SolidBase*>(logVol->solid());
      info() << "X-extent: " << solid->xMin() << " " << solid->xMax() << endreq;
      info() << "Y-extent: " << solid->yMin() << " " << solid->yMax() << endreq;
      info() << "Z-extent: " << solid->zMin() << " " << solid->zMax() << endreq;
    }

    // Create the physical volume
    Gaudi::Rotation3D rotation(m_rotation.begin(), m_rotation.end());
    IPVolume* pv = 
      parentLogVol->createPVolume(m_physVolName, m_logVolName,
                                  Gaudi::Transform3D(rotation, Gaudi::XYZVector(localPosition)).Inverse() );
  
    if( 0 == pv ) {
      error() << "AutoPositionerTool::placeVolume(): "
              << "could not create volume: " << m_physVolName
              << endreq;
      return StatusCode::FAILURE;
    }
  }

  if(m_detElemName != ""){
    // Add the corresponding detector element if a name is provided
    std::string pvPath = npath;
    if(pvPath.size() > 0) npath.append( "/" );
    pvPath.append( m_physVolName );

    sc = addDetectorElement(m_detElemName, m_detElemPath, m_logVolName,
                            parentDetElem->name(), pvPath);
    if( !sc.isSuccess() ) return sc; 

    // Add any sub-detector elements below the current detector element
    std::vector< std::vector<std::string> >::iterator sdIter, 
      sdEnd = m_subDetElements.end(); 
    for(sdIter = m_subDetElements.begin(); sdIter != sdEnd; sdIter++){
      std::vector<std::string> fields = *sdIter;
      if( fields.size() != 4 ){
        error() << "Wrong number of sub-detector element fields: " 
                << fields.size() << endreq;
        for(int fieldIdx=0; fieldIdx<fields.size(); fieldIdx++){
          error() << "  Field " << fieldIdx << ": " << fields[fieldIdx] 
                  <<endreq;
        }
        return StatusCode::FAILURE;
      }
      std::string subDetElemName = fields[0];
      std::string support = fields[1];
      std::string logVolName = fields[2];
      std::string subPvPath = fields[3];
      sc = addDetectorElement(subDetElemName, m_detElemPath, logVolName,
                              support, subPvPath);
      if( !sc.isSuccess() ) return sc; 
    }
  }

  return sc;
}
StatusCode AutoPositionerTool::addDetectorElement ( std::string  detElemName,
std::string  detElemPath,
std::string  logVolName,
std::string  support,
std::string  npath 
) [private]

Definition at line 277 of file AutoPositionerTool.cc.

                                                                  {
  // Add the detector element for existing geometry
  info() << "Using " << support 
         << " as support path for placement of " << detElemName
         << " at path " << detElemPath << endreq;  
  DetectorElement* detElem = new DetectorElement;
  StatusCode sc = m_detSvc->registerObject( detElemPath, detElemName, detElem);
  if( sc.isFailure() ){
    error() << "Failed to register object with support / name: " 
            << support << " / " << detElemName << endreq;
    return sc;
  }
  info() << "Using physical path " << npath 
         << "relative to support " << support
         << " for placement of " << logVolName << endreq;  
  detElem->createGeometryInfo( logVolName, support, npath);
  return sc;
}
const InterfaceID & IPositionerTool::interfaceID ( ) [static, inherited]

Definition at line 7 of file IPositionerTool.cc.

                                                {
  return IID_IPositionerTool;
}

Member Data Documentation

IDataProviderSvc* AutoPositionerTool::m_detSvc [private]

Definition at line 55 of file AutoPositionerTool.h.

Definition at line 56 of file AutoPositionerTool.h.

std::string AutoPositionerTool::m_physVolName [private]

Definition at line 58 of file AutoPositionerTool.h.

std::string AutoPositionerTool::m_logVolName [private]

Definition at line 59 of file AutoPositionerTool.h.

Definition at line 60 of file AutoPositionerTool.h.

std::vector<double> AutoPositionerTool::m_position [private]

Definition at line 61 of file AutoPositionerTool.h.

std::vector<double> AutoPositionerTool::m_rotation [private]

Definition at line 62 of file AutoPositionerTool.h.

std::string AutoPositionerTool::m_detElemName [private]

Definition at line 63 of file AutoPositionerTool.h.

std::string AutoPositionerTool::m_detElemPath [private]

Definition at line 64 of file AutoPositionerTool.h.

std::vector< std::vector<std::string> > AutoPositionerTool::m_subDetElements [private]

Definition at line 65 of file AutoPositionerTool.h.


The documentation for this class was generated from the following files:
| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

Generated on Fri May 16 2014 09:56:27 for DetHelpers by doxygen 1.7.4