diff --git a/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/LayerMaterialRecord.h b/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/LayerMaterialRecord.h deleted file mode 100755 index 8de03f8a0acf95d498deef2944f4c887f76c3737..0000000000000000000000000000000000000000 --- a/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/LayerMaterialRecord.h +++ /dev/null @@ -1,133 +0,0 @@ -/* - Copyright (C) 2002-2017 CERN for the benefit of the ATLAS collaboration -*/ - -////////////////////////////////////////////////////////////////// -// LayerMaterialRecord.h, (c) ATLAS Detector software -/////////////////////////////////////////////////////////////////// - -#ifndef TRKDETDESCRALGS_LAYERMATERIALRECORD_H -#define TRKDETDESCRALGS_LAYERMATERIALRECORD_H - -#include "TrkDetDescrUtils/BinUtility.h" -#include "TrkDetDescrUtils/MaterialAssociationType.h" -#include "TrkGeometry/MaterialProperties.h" -#include "GeoPrimitives/GeoPrimitives.h" - - -namespace Trk { - - /** @class LayerMaterialRecord - - Helper Class to record the material during the GeantinoNtupleMappingProcess - - @author Andreas.Salzburger@cern.ch - */ - - class Layer; - class AssociatedMaterial; - - class LayerMaterialRecord { - - public : - /** Default Constructor */ - LayerMaterialRecord(); - - /** Constructor */ - LayerMaterialRecord(double tlayer, - const BinUtility* binutils, - MaterialAssociationType assoc=EffectiveNumAtoms, - int maxSiliconHits = 0); - - /** Constructor */ - LayerMaterialRecord(const LayerMaterialRecord& lmr); - - /** Destructor */ - ~LayerMaterialRecord(); - - /** Assignment operator */ - LayerMaterialRecord& operator=(const LayerMaterialRecord& lmr); - - /** adding the information about the Geantino hit */ - void associateGeantinoHit(const Amg::Vector3D& pos, - double s, - double x0, - double l0, - double a, - double z, - double rho, - int screenoutput=0); - - /** finalize the Event */ - AssociatedMaterial* finalizeEvent(const Trk::Layer& lay, int screenoutput=0); - - /** finalize the Run */ - void finalizeRun(int screenoutput=0); - - /** return method for the LayerMaterial */ - const MaterialPropertiesMatrix& associatedLayerMaterial() const; - - /** return the BinUtility */ - const Trk::BinUtility* binUtility() const; - - private: - - double m_layerThickness; //!< record the layerThickness - BinUtility* m_binUtility; //!< record the BinnedArray - int m_bins1; //!< number of bins in coordinate 1 - int m_bins2; //!< number of bins in coordinate 2 - - //!< event normalizers - int m_steps; - double m_track_effNumAtoms; - - //!< event related information - double m_s; - double m_s_x0; - double m_s_l0; - double m_a; - double m_z; - double m_rho; - - double m_rPosition; - double m_zPosition; - double m_phiPosition; - double m_thetaPosition; - - MaterialAssociationType m_assoc; //!< type of hit association - - //!< run normalizers - std::vector< std::vector<int> > m_events; - - //!< event related information - std::vector< std::vector<double> > m_run_t_x0; - std::vector< std::vector<double> > m_run_t_l0; - std::vector< std::vector<double> > m_run_a; - std::vector< std::vector<double> > m_run_z; - std::vector< std::vector<double> > m_run_rho; - - int m_maxSiliconHits; - int m_siliconHits; - - //!< the final material properties - mutable MaterialPropertiesMatrix m_associatedLayerMaterial; - - static double s_siliconRadiationLength; - - //!< clear the material -> calls delete - void clearMaterial(); - //!< copy from another vector - void copyMaterial(const MaterialPropertiesMatrix& mat); - - }; - - inline const MaterialPropertiesMatrix& LayerMaterialRecord::associatedLayerMaterial() const - { return m_associatedLayerMaterial; } - - inline const Trk::BinUtility* LayerMaterialRecord::binUtility() const - { return m_binUtility; } - -} - -#endif - diff --git a/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/MaterialMapping.h b/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/MaterialMapping.h index d628752fe3beddc3fc6698bf8bb4cd17f87543a5..693bc01cdbca98190958858a31951db7c802399c 100644 --- a/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/MaterialMapping.h +++ b/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/MaterialMapping.h @@ -20,6 +20,20 @@ #include <map> #include "GeoPrimitives/GeoPrimitives.h" +#ifdef TRKDETDESCR_MEMUSAGE +#include "TrkDetDescrUtils/MemoryLogger.h" +#endif + +#ifndef UCHARCONV +#define UCHARCONV +#define ucharbin 0.00392157 // 1./double(1.*UCHAR_MAX) +// int to unsigned char and vv +#define uchar2uint(uchar) static_cast<unsigned int>(uchar) +#define uint2uchar(unint) static_cast<unsigned char>(unint) +// double to unsigned char and vv +#define uchar2dfrac(uchar) double(uchar*ucharbin) +#define dfrac2uchar(dfrac) lrint(dfrac*UCHAR_MAX) +#endif class TTree; @@ -31,18 +45,15 @@ namespace Trk { class SurfaceMaterialRecord; class LayerMaterialRecord; class LayerMaterialMap; + class Material; class MaterialProperties; class BinnedLayerMaterial; class CompressedLayerMaterial; - class IMaterialMapper; + class ElementTable; + class IMaterialMapper; + class ILayerMaterialAnalyser; + class ILayerMaterialCreator; class ITrackingGeometrySvc; - - struct IndexedMaterial { - unsigned short int firstBin; - unsigned short int secondBin; - const Trk::MaterialProperties* materialProperties; - }; - /** @class MaterialMapping @@ -59,6 +70,7 @@ namespace Trk { /** Standard Athena-Algorithm Constructor */ MaterialMapping(const std::string& name, ISvcLocator* pSvcLocator); + /** Default Destructor */ ~MaterialMapping(); @@ -77,11 +89,7 @@ namespace Trk { bool associateHit(const Trk::TrackingVolume& tvol, const Amg::Vector3D& pos, double stepl, - double x0, - double l0, - double a, - double z, - double rho); + const Trk::Material& mat); /** Output information with Level */ void registerVolume(const Trk::TrackingVolume& tvol, int lvl); @@ -89,8 +97,8 @@ namespace Trk { //!< private void Method to map the layer material void assignLayerMaterialProperties(const Trk::TrackingVolume& tvol, Trk::LayerMaterialMap* propSet); - //!< private method to compress material - Trk::CompressedLayerMaterial* compressMaterial(const Trk::BinnedLayerMaterial& binnedLayerMaterial); + //!< create the LayerMaterialRecord */ + void insertLayerMaterialRecord(const Trk::Layer& lay); /** Retrieve the TrackingGeometry */ StatusCode retrieveTrackingGeometry(); @@ -108,34 +116,37 @@ namespace Trk { /** general steering */ double m_etaCutOff; + bool m_useLayerThickness; //!< use the actual layer thickness int m_associationType; + + ToolHandle<ILayerMaterialAnalyser> m_layerMaterialRecordAnalyser; //!< the layer material analyser for the layer material record + ToolHandleArray<ILayerMaterialAnalyser> m_layerMaterialAnalysers; //!< the layer material analysers per creator (if wanted) + ToolHandleArray<ILayerMaterialCreator> m_layerMaterialCreators; //!< the layer material creators /** Mapper and Inspector */ bool m_mapMaterial; - ToolHandle<IMaterialMapper> m_materialMapper; //!< Pointer to an IMaterialMapper algTool - int m_materialMappingEvents; //!< count the number of validation records to avoid 2G files - int m_maxMaterialMappingEvents; //!< limit the number of validation records to avoid 2G files - + ToolHandle<IMaterialMapper> m_materialMapper; //!< Pointer to an IMaterialMapper algTool + bool m_mapComposition; //!< map the composition of the material + double m_minCompositionFraction; //!< minimal fraction to be accounted for the composition recording + + + Trk::ElementTable* m_elementTable; //!< the accumulated element table + std::string m_inputEventElementTable; //!< input event table + // the material maps ordered with layer keys std::map<const Layer*, LayerMaterialRecord > m_layerRecords; - - // compression - bool m_compressMaterial; - double m_compressedMaterialThickness; - size_t m_compressedMaterialX0Bins; - size_t m_compressedMaterialZARhoBins; - // statistics + // statistics for steps size_t m_mapped; size_t m_unmapped; size_t m_skippedOutside; - // break for validation - size_t m_mappedEvents; - size_t m_maxMappedEvents; - int m_layerMaterialScreenOutput; +#ifdef TRKDETDESCR_MEMUSAGE + MemoryLogger m_memoryLogger; //!< in case the memory is logged +#endif + }; } diff --git a/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/MaterialValidation.h b/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/MaterialValidation.h index c51e1a2a7a2419edd7788bebbbf5b1786440c025..086f121f96ff81c13cd80c1326aef051fdedcbe0 100755 --- a/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/MaterialValidation.h +++ b/Tracking/TrkDetDescr/TrkDetDescrAlgs/TrkDetDescrAlgs/MaterialValidation.h @@ -26,6 +26,7 @@ namespace Trk { class IMaterialMapper; class TrackingGeometry; class TrackingVolume; + class Surface; typedef std::pair<Amg::Vector3D, const Trk::TrackingVolume*> PositionAtBoundary; @@ -34,6 +35,23 @@ namespace Trk { @author Andreas.Salzburger@cern.ch */ + + // exit the volume + struct VolumeExit { + // the triple struct + const Trk::TrackingVolume* nVolume; + const Trk::Surface* bSurface; + Amg::Vector3D vExit; + + VolumeExit( const Trk::TrackingVolume* itv = 0, + const Trk::Surface* ibs = 0, + Amg::Vector3D iexit = Amg::Vector3D(0.,0.,0.)) : + nVolume(itv), + bSurface(ibs), + vExit(iexit){} + + }; + class MaterialValidation : public AthAlgorithm { public: @@ -70,9 +88,13 @@ namespace Trk { int m_maxMaterialMappingEvents; //!< limit the number of validation records to avoid 2G files - Rndm::Numbers* m_flatDist; //!< Random generator for flat distribution - double m_etaMin; - double m_etaMax; + Rndm::Numbers* m_flatDist; //!< Random generator for flat distribution + double m_etaMin; //!< eta boundary + double m_etaMax; //!< eta boundary + bool m_runNativeNavigation; //!< validate the native TG navigation + + double m_accTinX0; //!< accumulated t in X0 + }; diff --git a/Tracking/TrkDetDescr/TrkDetDescrAlgs/cmt/requirements b/Tracking/TrkDetDescr/TrkDetDescrAlgs/cmt/requirements index e463d311fe209ad2048ddee7796cbff720b43b19..a94ac811b86c77bbcb3050f7a99e23d6747fe5e6 100755 --- a/Tracking/TrkDetDescr/TrkDetDescrAlgs/cmt/requirements +++ b/Tracking/TrkDetDescr/TrkDetDescrAlgs/cmt/requirements @@ -9,25 +9,24 @@ use AtlasPolicy AtlasPolicy-* use AthenaBaseComps AthenaBaseComps-* Control use AtlasROOT AtlasROOT-* External use GaudiInterface GaudiInterface-* External -use TrkDetDescrUtils TrkDetDescrUtils-* Tracking/TrkDetDescr -use TrkGeometry TrkGeometry-* Tracking/TrkDetDescr use GeoPrimitives GeoPrimitives-* DetectorDescription +use TrkDetDescrUtils TrkDetDescrUtils-* Tracking/TrkDetDescr ################################################################# # private use statements private use TrkDetDescrInterfaces TrkDetDescrInterfaces-* Tracking/TrkDetDescr -use TrkSurfaces TrkSurfaces-* Tracking/TrkDetDescr use TrkVolumes TrkVolumes-* Tracking/TrkDetDescr - +use TrkGeometry TrkGeometry-* Tracking/TrkDetDescr +use TrkNeutralParameters TrkNeutralParameters-* Tracking/TrkEvent public library TrkDetDescrAlgs *.cxx components/*.cxx apply_pattern component_library # uncomment this line if you do want to build the memory monitoring lines -# apply_tag use_trkdetdescr_memmon +apply_tag use_trkdetdescr_memmon macro_append TrkDetDescrMemMonMacro "-DTRKDETDESCR_MEMUSAGE" diff --git a/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/LayerMaterialRecord.cxx b/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/LayerMaterialRecord.cxx deleted file mode 100755 index 9d260bda70c2389a057bf946ad8feec53570baff..0000000000000000000000000000000000000000 --- a/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/LayerMaterialRecord.cxx +++ /dev/null @@ -1,425 +0,0 @@ -/* - Copyright (C) 2002-2017 CERN for the benefit of the ATLAS collaboration -*/ - -////////////////////////////////////////////////////////////////// -// LayerMaterialRecord.cxx, (c) ATLAS Detector software -/////////////////////////////////////////////////////////////////// - -#include "TrkDetDescrAlgs/LayerMaterialRecord.h" -#include "TrkGeometry/MaterialProperties.h" -#include "TrkGeometry/AssociatedMaterial.h" -#include "TrkGeometry/Layer.h" -#include "TrkGeometry/CylinderLayer.h" -#include "TrkGeometry/DiscLayer.h" -#include "TrkSurfaces/Surface.h" -#include "TrkSurfaces/SurfaceBounds.h" -#include "TrkSurfaces/DiscBounds.h" -#include "TrkSurfaces/CylinderBounds.h" - -double Trk::LayerMaterialRecord::s_siliconRadiationLength = 93.6; - -Trk::LayerMaterialRecord::LayerMaterialRecord() -: m_layerThickness(0.), - m_binUtility(0), - m_bins1(0), - m_bins2(0), - m_steps(0), - m_track_effNumAtoms(0.), - m_s(0.), - m_s_x0(0.), - m_s_l0(0.), - m_a(0.), - m_z(0.), - m_rho(0.), - m_rPosition(0.), - m_zPosition(0.), - m_phiPosition(0.), - m_thetaPosition(0.), - m_assoc(Trk::EffectiveNumAtoms), - m_maxSiliconHits(0), - m_siliconHits(0) -{} - -Trk::LayerMaterialRecord::LayerMaterialRecord(double thickness, - const BinUtility* binutils, - Trk::MaterialAssociationType assoc, - int maxSiliconHits) -: m_layerThickness(thickness), - m_binUtility(binutils ? binutils->clone() : 0), - m_bins1(binutils ? (binutils->max(0) + 1) : 1), - m_bins2(binutils && binutils->dimensions() > 1 ? (binutils->max(1) + 1) : 1), - m_steps(0), - m_track_effNumAtoms(0.), - m_s(0.), - m_s_x0(0.), - m_s_l0(0.), - m_a(0.), - m_z(0.), - m_rho(0.), - m_rPosition(0.), - m_zPosition(0.), - m_phiPosition(0.), - m_thetaPosition(0.), - m_assoc(assoc), - m_maxSiliconHits(maxSiliconHits), - m_siliconHits(0) - -{ - for (int ibin=0; ibin<m_bins2; ++ibin) { - // event - m_events.push_back(std::vector<int>(m_bins1, 0)); - // run - m_run_t_x0.push_back(std::vector<double>(m_bins1, 0.)); - m_run_t_l0.push_back(std::vector<double>(m_bins1, 0.)); - m_run_a.push_back(std::vector<double>(m_bins1, 0.)); - m_run_z.push_back(std::vector<double>(m_bins1, 0.)); - m_run_rho.push_back(std::vector<double>(m_bins1, 0.)); - } -} - - -Trk::LayerMaterialRecord::LayerMaterialRecord(const Trk::LayerMaterialRecord& lmr) -: m_layerThickness(lmr.m_layerThickness), - m_binUtility(lmr.m_binUtility ? lmr.m_binUtility->clone() : 0), - m_bins1(lmr.m_bins1), - m_bins2(lmr.m_bins2), - m_steps(lmr.m_steps), - m_track_effNumAtoms(lmr.m_track_effNumAtoms), - m_s(lmr.m_s), - m_s_x0(lmr.m_s_x0), - m_s_l0(lmr.m_s_l0), - m_a(lmr.m_a), - m_z(lmr.m_z), - m_rho(lmr.m_rho), - m_rPosition(lmr.m_rPosition), - m_zPosition(lmr.m_zPosition), - m_phiPosition(lmr.m_phiPosition), - m_thetaPosition(lmr.m_thetaPosition), - m_assoc(lmr.m_assoc), - m_events(lmr.m_events), - m_run_t_x0(lmr.m_run_t_x0), - m_run_t_l0(lmr.m_run_t_l0), - m_run_a(lmr.m_run_a), - m_run_z(lmr.m_run_z), - m_run_rho(lmr.m_run_rho), - m_maxSiliconHits(lmr.m_maxSiliconHits), - m_siliconHits(lmr.m_siliconHits) -{ - copyMaterial(lmr.m_associatedLayerMaterial); -} - - -Trk::LayerMaterialRecord& Trk::LayerMaterialRecord::operator=(const Trk::LayerMaterialRecord& lmr) -{ - if (this != &lmr) { - m_layerThickness = lmr.m_layerThickness; - m_binUtility = lmr.m_binUtility ? lmr.m_binUtility->clone() : 0; - m_bins1 = lmr.m_bins1; - m_bins2 = lmr.m_bins2; - m_assoc = lmr.m_assoc; - m_steps = lmr.m_steps; - m_s = lmr.m_s; - m_s_x0 = lmr.m_s_x0; - m_s_l0 = lmr.m_s_l0; - m_a = lmr.m_a; - m_z = lmr.m_z; - m_rho = lmr.m_rho; - m_rPosition = lmr.m_rPosition; - m_zPosition = lmr.m_zPosition; - m_phiPosition = lmr.m_phiPosition; - m_thetaPosition = lmr.m_thetaPosition; - m_events = lmr.m_events; - m_track_effNumAtoms = lmr.m_track_effNumAtoms; - m_run_t_x0 = lmr.m_run_t_x0; - m_run_t_l0 = lmr.m_run_t_l0; - m_run_a = lmr.m_run_a; - m_run_z = lmr.m_run_z; - m_run_rho = lmr.m_run_rho; - m_maxSiliconHits = lmr.m_maxSiliconHits; - m_siliconHits = lmr.m_siliconHits; - // deal with the material - clearMaterial(); - copyMaterial( lmr.m_associatedLayerMaterial ); - } - - return (*this); -} - - -Trk::LayerMaterialRecord::~LayerMaterialRecord() -{ - // don't delete the material -> its given to the outside world - delete m_binUtility; -} - -void Trk::LayerMaterialRecord::associateGeantinoHit(const Amg::Vector3D& pos, - double s, - double x0, - double l0, - double a, - double z, - double rho, - int) -{ - - // spatial information - m_rPosition += pos.perp(); - m_zPosition += pos.z(); - m_phiPosition += pos.phi(); - m_thetaPosition += pos.theta(); - - m_track_effNumAtoms += s*rho/a; - m_steps++; - m_s += s; - - // must be true for all association methods - m_s_x0 += s/x0; - m_s_l0 += s/l0; - m_rho += rho * s; - - if (m_maxSiliconHits && fabs(x0-s_siliconRadiationLength)<0.5) ++m_siliconHits; - - if (m_assoc==Trk::EffectiveNumSteps) { - m_a += a; - m_z += z; - } else if (m_assoc==Trk::EffectiveNumAtoms) { - m_a += s*rho; - m_z += s*rho * z/a; - } else if (m_assoc==Trk::RadiationLength) { - m_a += a*s/x0; - m_z += z*s/x0; - } else { - m_a += a*s; - m_z += z*s; - } - -} - -Trk::AssociatedMaterial* Trk::LayerMaterialRecord::finalizeEvent(const Trk::Layer& lay, int screenoutput) -{ - // the corrFactor - double corrFactorInv = 0.; - // the return value - Trk::AssociatedMaterial* returnStep = 0; - - if (screenoutput) - std::cout << " o Finalize Event for layer " << lay.layerIndex().value() << std::endl; - - - // the silicon double counting can veto the entire event - bool vetoEvent = (m_maxSiliconHits && m_siliconHits > m_maxSiliconHits) ? true : false; - - if (!vetoEvent && m_s_x0 >10e-10 && m_bins1 && m_bins2 && m_steps) { - - // the densed phi/theta values - double hitPhi = m_phiPosition/m_steps; - double hitTheta = m_thetaPosition/m_steps; - - // the densed hit information - double densedHitX = 0.; - double densedHitY = 0.; - double densedHitZ = 0.; - double densedHitR = 0.; - - // cast it to cylinder/disc - const Trk::CylinderLayer* cylLayer = dynamic_cast<const Trk::CylinderLayer*>(&lay); - - // get the position - if (cylLayer) { - // Cylinder Bounds needed - const Trk::CylinderBounds& cylBounds = cylLayer->surfaceRepresentation().bounds(); - densedHitR = cylBounds.r(); - double halflengthZ = cylBounds.halflengthZ(); - double centerZ = lay.surfaceRepresentation().center().z(); - densedHitZ = densedHitR/tan(hitTheta); - // the corrfactor is - corrFactorInv = fabs(sin(hitTheta)); - // veto the event if the densed radius is outside the cylinder - vetoEvent = densedHitZ < centerZ-halflengthZ || densedHitZ > centerZ+halflengthZ; - - } else { - // DiscBounds needed - const Trk::DiscBounds* discBounds = dynamic_cast<const Trk::DiscBounds*>(&(lay.surfaceRepresentation().bounds())); - if (discBounds) { - densedHitZ = lay.surfaceRepresentation().center().z(); - densedHitR = densedHitZ*tan(hitTheta); - // the corrfactor is - corrFactorInv = fabs(cos(hitTheta)); - // veto the event if the densed radius is outside the disc - vetoEvent = densedHitR < discBounds->rMin() || densedHitR > discBounds->rMax(); - } - } - - if (!vetoEvent) { - - densedHitX = densedHitR*cos(hitPhi); - densedHitY = densedHitR*sin(hitPhi); - - Amg::Vector3D hitPosition(densedHitX,densedHitY,densedHitZ); - - int recordBin1 = m_binUtility ? m_binUtility->bin(hitPosition, 0) : 0; - int recordBin2 = ( m_binUtility && m_binUtility->dimensions() > 1) ? m_binUtility->bin(hitPosition, 1) : 0; - - // safety checks - recordBin1 = ( recordBin1 < 0 ) ? 0 : recordBin1; - recordBin1 = ( recordBin1 >= m_bins1) ? m_bins1-1 : recordBin1; - recordBin2 = ( recordBin2 < 0 ) ? 0 : recordBin2; - recordBin2 = ( recordBin2 >= m_bins2) ? m_bins2-1 : recordBin2; - - // finalization - m_rho *= corrFactorInv; - m_rho /= (m_layerThickness); // condense to layer thickness - // the different methods - if (m_assoc==Trk::EffectiveNumSteps && m_steps) { - m_a /= m_steps; - m_z /= m_steps; - } else if (m_assoc==Trk::EffectiveNumAtoms && m_track_effNumAtoms>10e-23) { - m_a /= m_track_effNumAtoms; - m_z /= m_track_effNumAtoms; - } else if (m_assoc==Trk::RadiationLength && m_s_x0 > 10e-10) { - m_a /= m_s_x0; - m_z /= m_s_x0; - } else if (m_s > 10e-10) { - m_a /= m_s; - m_z /= m_s; - } - - // assign the variables for the outside world - double x0 = m_s/m_s_x0; - double l0 = m_s/m_s_l0; - - if (screenoutput > 1) - std::cout << " Collected information for bin [" - << recordBin1 << ", " << recordBin2 << "] in this event ( steps, s/x0, x0 ) = " - << m_steps << ", " << m_s_x0 << ", " << x0 << std::endl; - - // assign the run variables - m_events[recordBin2][recordBin1]++; - - m_run_t_x0[recordBin2][recordBin1] += m_s_x0*corrFactorInv; - m_run_t_l0[recordBin2][recordBin1] += m_s_l0*corrFactorInv; - m_run_a[recordBin2][recordBin1] += m_a; - m_run_z[recordBin2][recordBin1] += m_z; - m_run_rho[recordBin2][recordBin1] += m_rho; - - if (screenoutput >1) - std::cout << " Cummulated material from " << m_events[recordBin2][recordBin1] - << " events ( s/x0 ) = " << m_run_t_x0[recordBin2][recordBin1] << std::endl; - - // create the return step - returnStep = (corrFactorInv >1.) ? 0 : new Trk::AssociatedMaterial( hitPosition, - m_s_x0*x0, - x0, - l0, - m_a, - m_z, - m_rho, - 1./corrFactorInv, - lay.enclosingTrackingVolume(), - &lay); - - } - } - - // reset silicon hits - m_siliconHits = 0; - - // reset event variables - m_steps = 0; - m_s = 0.; - m_s_x0 = 0.; - m_s_l0 = 0.; - m_a = 0.; - m_z = 0.; - m_rho = 0.; - m_track_effNumAtoms = 0.; - - m_rPosition = 0.; - m_zPosition = 0.; - m_phiPosition = 0.; - m_thetaPosition = 0.; - - return returnStep; - -} - -void Trk::LayerMaterialRecord::finalizeRun(int screenoutput) -{ - - if (screenoutput) - std::cout << " o Finalize Layer with [bins1,bins2] = [" << m_bins1 << ", " << m_bins2 << "] material bins " << std::endl; - - m_associatedLayerMaterial.reserve(m_bins2); - - for (int ibin2 = 0; ibin2 < m_bins2; ++ibin2) { - // create the vector first - Trk::MaterialPropertiesVector matVector; - matVector.reserve(m_bins1); - // loop over local 1 bins - for (int ibin1 = 0; ibin1 < m_bins1; ++ibin1) { - Trk::MaterialProperties* binMaterial = 0; - if (m_events[ibin2][ibin1]) { - - if (screenoutput) - std::cout << " Bin [" << ibin1 << "," << ibin2 << "]" << " has " << m_events[ibin2][ibin1] << " recorded events." << std::endl; - - m_run_t_x0[ibin2][ibin1] /= m_events[ibin2][ibin1]; - m_run_t_l0[ibin2][ibin1] /= m_events[ibin2][ibin1]; - m_run_a[ibin2][ibin1] /= m_events[ibin2][ibin1]; - m_run_z[ibin2][ibin1] /= m_events[ibin2][ibin1]; - m_run_rho[ibin2][ibin1] /= m_events[ibin2][ibin1]; - - std::cout << " Averaged material from " << m_events[ibin2][ibin1] - << " events ( s/x0 ) = " << m_run_t_x0[ibin2][ibin1] << std::endl; - - binMaterial = new Trk::MaterialProperties(1., - 1./m_run_t_x0[ibin2][ibin1], - 1./m_run_t_l0[ibin2][ibin1], - m_run_a[ibin2][ibin1], - m_run_z[ibin2][ibin1], - m_run_rho[ibin2][ibin1]); - if (screenoutput > 1) - std::cout << " Created Material : " << *binMaterial << std::endl; - - } - matVector.push_back(binMaterial); - } - m_associatedLayerMaterial.push_back(matVector); - } -} - -void Trk::LayerMaterialRecord::clearMaterial() -{ - - Trk::MaterialPropertiesMatrix::iterator matMatrixIter = m_associatedLayerMaterial.begin(); - Trk::MaterialPropertiesMatrix::iterator matMatrixIterEnd = m_associatedLayerMaterial.end(); - for ( ; matMatrixIter != matMatrixIterEnd; ++matMatrixIter) { - // loop over the subsets - std::vector<const Trk::MaterialProperties*>::iterator matIter = (*matMatrixIter).begin(); - std::vector<const Trk::MaterialProperties*>::iterator matIterEnd = (*matMatrixIter).end(); - for ( ; matIter != matIterEnd; ++matIter) - delete (*matIter); - } -} - -void Trk::LayerMaterialRecord::copyMaterial(const MaterialPropertiesMatrix& materialMatrix) -{ - // clear the vector - m_associatedLayerMaterial.clear(); - - Trk::MaterialPropertiesMatrix::const_iterator matMatrixIter = materialMatrix.begin(); - Trk::MaterialPropertiesMatrix::const_iterator matMatrixIterEnd = materialMatrix.end(); - for ( ; matMatrixIter != matMatrixIterEnd; ++matMatrixIter) { - Trk::MaterialPropertiesVector matProp; - // loop over the subsets - std::vector<const Trk::MaterialProperties*>::const_iterator matIter = (*matMatrixIter).begin(); - std::vector<const Trk::MaterialProperties*>::const_iterator matIterEnd = (*matMatrixIter).end(); - for ( ; matIter != matIterEnd; ++matIter) { - // test it - matProp.push_back( ( (*matIter) ? (*matIter)->clone() : 0 ) ); - } - // and now push back the vector - m_associatedLayerMaterial.push_back(matProp); - } -} diff --git a/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/MaterialMapping.cxx b/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/MaterialMapping.cxx index c731dafa59c3e86da00f9d4e39bb664bced025ef..d927cb4edb27d63f161fcb3e70ea8cf312ff0b06 100755 --- a/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/MaterialMapping.cxx +++ b/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/MaterialMapping.cxx @@ -8,16 +8,18 @@ // Gaudi Units #include "GaudiKernel/SystemOfUnits.h" -//TrkDetDescrAlgs +//TrkDetDescr Algs, Interfaces, Utils #include "TrkDetDescrAlgs/MaterialMapping.h" -#include "TrkDetDescrAlgs/LayerMaterialRecord.h" -// Trk #include "TrkDetDescrInterfaces/ITrackingGeometrySvc.h" #include "TrkDetDescrInterfaces/IMaterialMapper.h" +#include "TrkDetDescrInterfaces/ILayerMaterialCreator.h" +#include "TrkDetDescrInterfaces/ILayerMaterialAnalyser.h" #include "TrkDetDescrUtils/GeometryStatics.h" #include "TrkDetDescrUtils/LayerIndex.h" #include "TrkDetDescrUtils/BinUtility.h" -#include "TrkGeometry/EntryLayerProvider.h" +// TrkGeometry +#include "TrkGeometry/LayerMaterialRecord.h" +//#include "TrkGeometry/ElementTable.h" #include "TrkGeometry/TrackingGeometry.h" #include "TrkGeometry/TrackingVolume.h" #include "TrkGeometry/MaterialStep.h" @@ -34,7 +36,6 @@ #include <unistd.h> #endif - Trk::MaterialMapping::MaterialMapping(const std::string& name, ISvcLocator* pSvcLocator) : AthAlgorithm(name,pSvcLocator), m_trackingGeometrySvc("AtlasTrackingGeometrySvc",name), @@ -42,42 +43,48 @@ Trk::MaterialMapping::MaterialMapping(const std::string& name, ISvcLocator* pSvc m_mappingVolumeName("Atlas"), m_mappingVolume(0), m_inputMaterialStepCollection("MaterialStepRecords"), - m_outputLayerMaterialSetName("AtlasTrackingMaterial"), m_etaCutOff(6.0), + m_useLayerThickness(false), m_associationType(1), + m_layerMaterialRecordAnalyser(""), m_mapMaterial(true), - m_materialMapper("Trk::MaterialMapper/MappingMaterialMapper"), - m_materialMappingEvents(0), - m_maxMaterialMappingEvents(25000), + m_materialMapper(""), + m_mapComposition(true), + m_minCompositionFraction(0.005), + m_elementTable(0), + m_inputEventElementTable("ElementTable"), m_mapped(0), m_unmapped(0), m_skippedOutside(0), - m_mappedEvents(0), - m_maxMappedEvents(-1), m_layerMaterialScreenOutput(0) +#ifdef TRKDETDESCR_MEMUSAGE + ,m_memoryLogger() +#endif { // the name of the TrackingGeometry to be retrieved declareProperty("TrackingGeometrySvc" , m_trackingGeometrySvc); declareProperty("MappingVolumeName" , m_mappingVolumeName); // general steering declareProperty("EtaCutOff" , m_etaCutOff); + // for the analysis of the material + declareProperty("LayerMaterialRecordAnalyser" , m_layerMaterialRecordAnalyser); + // for the creation of the material + declareProperty("LayerMaterialCreators" , m_layerMaterialCreators); + declareProperty("LayerMaterialAnalysers" , m_layerMaterialAnalysers); // the toolhandle of the MaterialMapper to be used - declareProperty("MapMaterial" , m_mapMaterial); - declareProperty("MaterialMapper" , m_materialMapper); - declareProperty("MaximumMappingEvents" , m_maxMaterialMappingEvents); - // Compression section - declareProperty("CompressMaterial" , m_compressMaterial); - declareProperty("CompressMaterialThickness" , m_compressedMaterialThickness); - declareProperty("CompressMaterialBinsX0" , m_compressedMaterialX0Bins); - declareProperty("CompressMaterialBinsZARho" , m_compressedMaterialZARhoBins); + declareProperty("MapMaterial" , m_mapMaterial); + declareProperty("MaterialMapper" , m_materialMapper); + // Composition related parameters + declareProperty("MapComposition" , m_mapComposition); + declareProperty("MinCompositionFraction" , m_minCompositionFraction); + // Steer the layer thickness + declareProperty("UseActualLayerThicknesss" , m_useLayerThickness); // some job setup - declareProperty("MaterialAssociationType" , m_associationType); - declareProperty("InputMaterialStepCollection" , m_inputMaterialStepCollection); - declareProperty("OutputLayerMaterialSetName" , m_outputLayerMaterialSetName); - // Maximum of mapped events - declareProperty("MaximumMappedEvents" , m_maxMappedEvents); + declareProperty("MaterialAssociationType" , m_associationType); + declareProperty("InputMaterialStepCollection" , m_inputMaterialStepCollection); + declareProperty("InputElementTable" , m_inputEventElementTable); // Output screen stuff - declareProperty("MaterialScreenOutputLevel" , m_layerMaterialScreenOutput); + declareProperty("MaterialScreenOutputLevel" , m_layerMaterialScreenOutput); } @@ -88,13 +95,22 @@ Trk::MaterialMapping::~MaterialMapping() StatusCode Trk::MaterialMapping::initialize() { - ATH_MSG_INFO( "initialize()" ); + ATH_MSG_INFO("initialize()"); if ( (m_trackingGeometrySvc.retrieve()).isFailure() ) ATH_MSG_WARNING("Could not retrieve TrackingGeometrySvc"); - if ( (m_materialMapper.retrieve()).isFailure() ) + if (!m_materialMapper.empty() && (m_materialMapper.retrieve()).isFailure() ) ATH_MSG_WARNING("Could not retrieve MaterialMapper"); + + if ( !m_layerMaterialRecordAnalyser.empty() && m_layerMaterialRecordAnalyser.retrieve().isFailure() ) + ATH_MSG_WARNING("Could not retrieve LayerMaterialAnalyser"); + + if ( m_layerMaterialCreators.size() && m_layerMaterialCreators.retrieve().isFailure() ) + ATH_MSG_WARNING("Could not retrieve any LayerMaterialCreators"); + + if ( m_layerMaterialAnalysers.size() && m_layerMaterialAnalysers.retrieve().isFailure() ) + ATH_MSG_WARNING("Could not retrieve any LayerMaterialAnalysers"); return StatusCode::SUCCESS; } @@ -102,122 +118,79 @@ StatusCode Trk::MaterialMapping::initialize() StatusCode Trk::MaterialMapping::execute() { - ATH_MSG_VERBOSE( "MaterialMapping execute() start" ); + ATH_MSG_VERBOSE("MaterialMapping execute() start"); // ------------------------------- get the trackingGeometry at first place if (!m_trackingGeometry) { StatusCode retrieveCode = retrieveTrackingGeometry(); if (retrieveCode.isFailure()){ - ATH_MSG_INFO( "Could not retrieve TrackingGeometry. Exiting." ); + ATH_MSG_INFO("Could not retrieve TrackingGeometry. Exiting."); return retrieveCode; } - } + } + if (m_trackingGeometry) + ATH_MSG_VERBOSE("TrackingGeometry sucessfully retrieved"); // get the material step vector const MaterialStepCollection* materialSteps = 0; - - // try this StatusCode retrieveCode = evtStore()->retrieve(materialSteps,m_inputMaterialStepCollection); if (retrieveCode.isFailure()) { - - ATH_MSG_WARNING( "[!] Could not retrieve the step vector!"); + ATH_MSG_WARNING("[!] Could not retrieve the step vector!"); return retrieveCode; - - } else if (m_maxMappedEvents > 0 && m_mappedEvents >= m_maxMappedEvents ) { - - ATH_MSG_VERBOSE( "Maximunm mapped events already reached. Skipping."); - return StatusCode::SUCCESS; - } else { // successful retrieval - // average numbers for the weighting - int associatedSteps = 0 ; - double av_eta = 0.; - double av_phi = 0.; - - double eta = 0.; - double phi = 0.; - - ATH_MSG_VERBOSE( "[+] Successfully read " << materialSteps->size() << " geantino steps" ); - - auto stepIter = materialSteps->begin(); - auto stepIterEnd = materialSteps->end(); + const Trk::ElementTable* eTableEvent = 0; + if (evtStore()->contains<Trk::ElementTable>(m_inputEventElementTable) && evtStore()->retrieve(eTableEvent,m_inputEventElementTable).isFailure()){ + ATH_MSG_WARNING("No ElementTable coud be retrieved. Switching composition recording off."); + } else if (eTableEvent) + (*m_elementTable) += (*eTableEvent); // accummulate the table + m_mapComposition = eTableEvent ? true : false; + + ATH_MSG_DEBUG("[+] Successfully read "<< materialSteps->size() << " geantino steps"); + int associatedSteps = 0; // loop over the hits and associate that to the layers - for ( ; stepIter != stepIterEnd; ++stepIter) { - - double hitX = (*stepIter)->hitX(); - double hitY = (*stepIter)->hitY(); - double hitZ = (*stepIter)->hitZ(); - - double t = (*stepIter)->steplength(); - double x0 = (*stepIter)->x0(); - double l0 = (*stepIter)->l0(); - double a = (*stepIter)->A(); - double z = (*stepIter)->Z(); - double rho = (*stepIter)->rho(); - - Amg::Vector3D pos(hitX,hitY,hitZ); - - // skip if outside the mapping volume - if (m_mappingVolume && !m_mappingVolume->inside(pos)){ + for ( auto& step : (*materialSteps) ) { + + // step length and position + double t = step->steplength(); + Amg::Vector3D pos(step->hitX(), step->hitY(), step->hitZ()); + // skip if : + // -- 0) no mapping volume exists + // -- 1) outside the mapping volume + // -- 2) outside the eta acceptance + if (!m_mappingVolume || !(m_mappingVolume->inside(pos)) || fabs(pos.eta()) > m_etaCutOff ){ ++m_skippedOutside; continue; } - // go ahead - eta = pos.eta(); - phi = pos.phi(); - // get the lowest TrackingVolume const Trk::TrackingVolume* associatedVolume = m_trackingGeometry->lowestTrackingVolume(pos); // add associated volume to volumes map - if (!associatedVolume) + if (!associatedVolume) { + ATH_MSG_FATAL("No associated TrackingVolume found. Aborting."); return StatusCode::FAILURE; - - // ------ CUT ------ (e.g. dummy/giant steps, non-physical atomic numbers, high eta ...) - if (pos.mag() > 1. * Gaudi::Units::mm && t > 10e-10 && t < 10000. && a < 252. && a > 0. && fabs(eta) < m_etaCutOff) { - if (associateHit(*associatedVolume, pos,t,x0,l0,a,z,rho)) { - // average over eta, phi, theta - av_eta += eta; - av_phi += phi; - ++associatedSteps; - } } + // associate the hit + if (associateHit(*associatedVolume, pos, t, step->fullMaterial())) + ++associatedSteps; + } // end of loop over steps - ATH_MSG_VERBOSE(" Loop over Material steps done, now finalizing event ..."); + ATH_MSG_VERBOSE("Loop over Material steps done, now finalizing event ..."); // check whether the event was good for at least one hit if (associatedSteps) { - - // at least one step was associated -> thus the event counts - ++m_mappedEvents; - - ATH_MSG_VERBOSE(" There are associated steps, need to call finalizeEvent() & record to the MaterialMapper."); - // accepted hits - av_eta /= associatedSteps; - av_phi /= associatedSteps; - + ATH_MSG_VERBOSE("There are associated steps, need to call finalizeEvent() & record to the MaterialMapper."); // finalize the event --------------------- Layers --------------------------------------------- - auto lIter = m_layerRecords.begin(); - for ( ; lIter != m_layerRecords.end(); ++lIter) { - - const Trk::Layer* layer = lIter->first; - if (!layer) continue; - - Trk::AssociatedMaterial* assMatHit = (lIter->second).finalizeEvent(*layer, m_layerMaterialScreenOutput); - if (assMatHit) - m_materialMapper->recordFullLayerHit(*assMatHit); + for (auto& lRecord : m_layerRecords ) { + // associated material + Trk::AssociatedMaterial* assMatHit = lRecord.second.finalizeEvent((*lRecord.first)); + // record the full layer hit + if (assMatHit && !m_materialMapper.empty()) m_materialMapper->recordLayerHit(*assMatHit, true); delete assMatHit; - // call the material mapper finalize method - ATH_MSG_VERBOSE( " Calling finalizeEvent on the MaterialMapper ..." ); - // increase the number - ++m_materialMappingEvents; - // material mapper - m_materialMapper->finalizeEvent(av_eta,av_phi); - + ATH_MSG_VERBOSE("Calling finalizeEvent on the MaterialMapper ..."); } } // the event had at least one associated hit } @@ -229,61 +202,31 @@ StatusCode Trk::MaterialMapping::execute() bool Trk::MaterialMapping::associateHit( const Trk::TrackingVolume& associatedVolume, const Amg::Vector3D& pos, double stepl, - double x0, - double l0, - double a, - double z, - double rho) -{ - - - + const Trk::Material& mat) +{ // get the intersection with the layer Amg::Vector3D dir = pos.normalized(); - const Trk::LayerIntersection lIntersect = associatedVolume.closestMaterialLayer(pos, dir, Trk::mappingMode, true); - if (lIntersect.sIntersection.valid){ + const Trk::LayerIntersection<Amg::Vector3D> lIntersect = associatedVolume.closestMaterialLayer(pos, dir, Trk::mappingMode, true); + if (lIntersect.intersection.valid){ ++m_mapped; // try to find the layer material record - auto clIter = m_layerRecords.find(lIntersect.layer); + auto clIter = m_layerRecords.find(lIntersect.object); if (clIter != m_layerRecords.end() ){ // record the plain information w/o correction & intersection - if (m_mapMaterial) - m_materialMapper->recordMaterialHit(Trk::AssociatedMaterial(pos, - stepl, - x0, - l0, - a, - z, - rho, - 1., - &associatedVolume, - lIntersect.layer), - lIntersect.sIntersection.intersection); + if (m_mapMaterial && !m_materialMapper.empty()) + m_materialMapper->recordMaterialHit(Trk::AssociatedMaterial(pos, stepl, mat, 1., &associatedVolume, lIntersect.object), lIntersect.intersection.position); // LayerMaterialRecord found, add the hit - (*clIter).second.associateGeantinoHit(lIntersect.sIntersection.intersection, stepl, x0, l0, a, z, rho, m_layerMaterialScreenOutput); - ATH_MSG_VERBOSE(" - associate Geantino Information ( s/x0 , x0 , l0, a, z, rho ) = " - << stepl/x0 << ", " << x0 << " , " << l0 << ", " << a << ", " << z << ", " << rho ); - ATH_MSG_VERBOSE(" - to layer with index " << lIntersect.layer->layerIndex().value() << " in '" << associatedVolume.volumeName() << "'."); + (*clIter).second.associateGeantinoHit(lIntersect.intersection.position, stepl, mat); + ATH_MSG_VERBOSE("- associate Geantino Information at intersection [r/z] = "<< lIntersect.intersection.position.perp() << "/"<< lIntersect.intersection.position.z() ); + ATH_MSG_VERBOSE("- associate Geantino Information ( s, s/x0 , x0 , l0, a, z, rho ) = " + << stepl << ", "<< stepl/mat.X0 << ", "<< mat.X0 << ", "<< mat.L0 << ", "<< mat.A << ", "<< mat.Z << ", "<< mat.rho ); + ATH_MSG_VERBOSE("- to layer with index "<< lIntersect.object->layerIndex().value() << "in '"<< associatedVolume.volumeName() << "'."); } else { ATH_MSG_WARNING("No Layer found in the associated map! Should not happen."); return false; } - } else { - // unmapped - record for validation + } else ++m_unmapped; - if (m_mapMaterial) - m_materialMapper->recordMaterialHit(Trk::AssociatedMaterial(pos, - stepl, - x0, - l0, - a, - z, - rho, - 1., - &associatedVolume, - 0), Amg::Vector3D(0.,0.,0.)); - - } // return return true; } @@ -295,60 +238,28 @@ void Trk::MaterialMapping::assignLayerMaterialProperties( const Trk::TrackingVol if (!propSet) return; - ATH_MSG_INFO( "Processing TrackingVolume: " << tvol.volumeName() ); - - // ----------------------------------- loop over the entry layers ---------------------------- - const Trk::EntryLayerProvider* entryLayerProvider = tvol.entryLayerProvider(); - if (entryLayerProvider) { - // get the objects in a vector-like format - const std::vector<const Trk::Layer*>& elayers = entryLayerProvider->layers(); - ATH_MSG_INFO( " --> found : " << elayers.size() << " entry Layers" ); - // iterator - auto elayerIter = elayers.begin(); - // loop over layers - for ( ; elayerIter != elayers.end(); ++elayerIter) { - // check if the layer has material properties - if (*elayerIter) { - ATH_MSG_INFO( " > LayerIndex: " << (**elayerIter).layerIndex() ); - // set the material! - if (propSet) { - // find the pair - auto curIt = propSet->find((**elayerIter).layerIndex()); - if (curIt != propSet->end()) { - ATH_MSG_INFO( "LayerMaterial assigned for Layer with index: " << (**elayerIter).layerIndex() ); - // set it to the layer - (**elayerIter).assignMaterialProperties(*((*curIt).second), 1.); - - } - } - } - } - } - // -------------------------------------- END OF ENTRY LAYER SECTION -------------------------------------- + ATH_MSG_INFO("Processing TrackingVolume: "<< tvol.volumeName() ); - - // ----------------------------------- loop over confined layers ----------------------------- + // ----------------------------------- loop over confined layers ------------------------------------------ const Trk::BinnedArray< Trk::Layer >* confinedLayers = tvol.confinedLayers(); if (confinedLayers) { // get the objects in a vector-like format const std::vector<const Trk::Layer*>& layers = confinedLayers->arrayObjects(); - ATH_MSG_INFO( " --> found : " << layers.size() << " confined Layers" ); + ATH_MSG_INFO("--> found : "<< layers.size() << "confined Layers"); // the iterator over the vector - auto layerIter = layers.begin(); // loop over layers - for ( ; layerIter != layers.end(); ++layerIter) { + for (auto& layer : layers) { // assign the material and output - if (*layerIter && (**layerIter).layerIndex().value() ) { - ATH_MSG_INFO( " > LayerIndex: " << (**layerIter).layerIndex() ); + if (layer && (*layer).layerIndex().value() ) { + ATH_MSG_INFO(" > LayerIndex: "<< (*layer).layerIndex() ); // set the material! if (propSet) { // find the pair - auto curIt = propSet->find((**layerIter).layerIndex()); + auto curIt = propSet->find((*layer).layerIndex()); if (curIt != propSet->end()) { - ATH_MSG_INFO( "LayerMaterial assigned for Layer with index: " << (**layerIter).layerIndex() ); + ATH_MSG_INFO("LayerMaterial assigned for Layer with index: "<< (*layer).layerIndex() ); // set it to the layer - (**layerIter).assignMaterialProperties(*((*curIt).second), 1.); - + (*layer).assignMaterialProperties(*((*curIt).second), 1.); } } } @@ -360,14 +271,12 @@ void Trk::MaterialMapping::assignLayerMaterialProperties( const Trk::TrackingVol if (confinedVolumes) { // get the objects in a vector-like format const std::vector<const Trk::TrackingVolume*>& volumes = confinedVolumes->arrayObjects(); - ATH_MSG_INFO( " --> found : " << volumes.size() << " confined TrackingVolumes" ); - // the iterator over the vector - auto volumeIter = volumes.begin(); + ATH_MSG_INFO("--> found : "<< volumes.size() << "confined TrackingVolumes"); // loop over volumes - for ( ; volumeIter != volumes.end(); ++volumeIter) { + for (auto& volume : volumes) { // assing the material and output - if (*volumeIter) - assignLayerMaterialProperties(**volumeIter, propSet); // call itself recursively + if (volume) + assignLayerMaterialProperties(*volume, propSet); // call itself recursively } } } @@ -376,76 +285,101 @@ void Trk::MaterialMapping::assignLayerMaterialProperties( const Trk::TrackingVol StatusCode Trk::MaterialMapping::finalize() { - ATH_MSG_INFO( "========================================================================================= " ); - ATH_MSG_INFO( "finalize() starts ..."); - - // record the final map to be written to POOL - Trk::LayerMaterialMap* associatedLayerMaterialProperties = new Trk::LayerMaterialMap(); - - ATH_MSG_INFO( m_layerRecords.size() << " LayerMaterialRecords to be finalized for this material mapping run." ); - + ATH_MSG_INFO("========================================================================================= "); + ATH_MSG_INFO("finalize() starts ..."); + +#ifdef TRKDETDESCR_MEMUSAGE + m_memoryLogger.refresh(getpid()); + ATH_MSG_INFO("[ memory usage ] Start building of material maps: " ); + ATH_MSG_INFO( m_memoryLogger ); +#endif + + // create a dedicated LayerMaterialMap by layerMaterialCreator; + std::map< std::string, Trk::LayerMaterialMap* > layerMaterialMaps; + for ( auto& lmcIter : m_layerMaterialCreators ){ + ATH_MSG_INFO("-> Creating material map '"<< lmcIter->layerMaterialName() << "' from creator "<< lmcIter.typeAndName() ); + layerMaterialMaps[lmcIter->layerMaterialName()] = new Trk::LayerMaterialMap(); + } + + ATH_MSG_INFO( m_layerRecords.size() << "LayerMaterialRecords to be finalized for this material mapping run."); + // loop over the layers and output the stuff --- fill the associatedLayerMaterialProperties - auto lIter = m_layerRecords.begin(); - for ( ; lIter != m_layerRecords.end(); ++lIter) { + for ( auto& lIter : m_layerRecords ) { // Get the key map, the layer & the volume name - const Trk::Layer* layer = (lIter->first); - Trk::LayerIndex layerKey = (layer->layerIndex()); + const Trk::Layer* layer = lIter.first; + Trk::LayerIndex layerKey = layer->layerIndex(); // get the enclosing tracking volume const Trk::TrackingVolume* eVolume = layer->enclosingTrackingVolume(); // assign the string - std::string vName = eVolume ? (eVolume->volumeName()) : "Unknown"; - - ATH_MSG_INFO( "Finalize MaterialAssociation for Layer " << layerKey.value() << " in " << eVolume->volumeName() ); + std::string vName = eVolume ? (eVolume->volumeName()) : " BoundaryCollection "; + ATH_MSG_INFO("Finalize MaterialAssociation for Layer "<< layerKey.value() << " in " << vName ); // normalize - use m_finalizeRunDebug - (lIter->second).finalizeRun(m_layerMaterialScreenOutput); - - // the new ones to create - Trk::LayerMaterialProperties* layerMaterialProperties = 0; - // get the vector of MaterialProperties - const Trk::MaterialPropertiesMatrix& recordedLayerMaterialProperties = (lIter->second).associatedLayerMaterial(); - if (recordedLayerMaterialProperties.size()==1 && recordedLayerMaterialProperties[0].size()==1) { - // create homogeneous - const Trk::MaterialProperties* singleProperties = (recordedLayerMaterialProperties[0][0]) ? - (recordedLayerMaterialProperties[0][0]) : new Trk::MaterialProperties(); - layerMaterialProperties = new Trk::HomogeneousLayerMaterial(*singleProperties,1.); - delete singleProperties; - } else if (recordedLayerMaterialProperties.size()) { - // get the BinUtility - const Trk::BinUtility& recordLayerMaterialBinUtil = (*(lIter->second).binUtility()); - // create the new BinnedMaterial - Trk::BinnedLayerMaterial* binnedMaterial = new Trk::BinnedLayerMaterial(recordLayerMaterialBinUtil, - recordedLayerMaterialProperties, - 1.); - // the compress option for 2D material - simple gif algorithm - if (m_compressMaterial && recordLayerMaterialBinUtil.max(1) > 1) { - layerMaterialProperties = compressMaterial(*binnedMaterial); - delete binnedMaterial; - } else // this is the option for 1D -> don't compress - layerMaterialProperties = binnedMaterial; + (lIter.second).finalizeRun(m_mapComposition); + // output the material to the analyser if registered + if (!m_layerMaterialRecordAnalyser.empty() && m_layerMaterialRecordAnalyser->analyseLayerMaterial(*layer, lIter.second).isFailure() ) + ATH_MSG_WARNING("Could not analyse the LayerMaterialRecord for layer "<< layerKey.value() ); + // check if we have analysers per creator + bool analyse = (m_layerMaterialCreators.size() == m_layerMaterialAnalysers.size()); + // and now use the creators to make the maps out of the LayerMaterialRecord + size_t ilmc = 0; + for ( auto& lmcIter : m_layerMaterialCreators ){ + // call the creator and register in the according map +#ifdef TRKDETDESCR_MEMUSAGE + m_memoryLogger.refresh(getpid()); + ATH_MSG_INFO("[ memory usage ] Before building the map for Layer "<< layerKey.value() ); + ATH_MSG_INFO( m_memoryLogger ); +#endif + const Trk::LayerMaterialProperties* lMaterial = lmcIter->createLayerMaterial(*layer, lIter.second); +#ifdef TRKDETDESCR_MEMUSAGE + m_memoryLogger.refresh(getpid()); + ATH_MSG_INFO("[ memory usage ] After building the map for Layer "<< layerKey.value() ); + ATH_MSG_INFO( m_memoryLogger ); +#endif + if (lMaterial) + ATH_MSG_VERBOSE("LayerMaterial map created as "<< *lMaterial ); + // insert the created map for the given layer + (*layerMaterialMaps[lmcIter->layerMaterialName()])[layerKey.value()] = lMaterial; + // analyse the it if configured + if (analyse && lMaterial && (m_layerMaterialAnalysers[ilmc]->analyseLayerMaterial(*layer, *lMaterial)).isFailure() ) + ATH_MSG_WARNING("Could not analyse created LayerMaterialProperties for layer "<< layerKey.value() ); + ++ilmc; } - // fill them into the map that is written to POOL - (*associatedLayerMaterialProperties)[layerKey] = layerMaterialProperties; } - ATH_MSG_INFO( " LayerMaterialProperties for " << associatedLayerMaterialProperties->size() << " layers recorded." ); - - // write output to detector store - if ( (detStore()->record(associatedLayerMaterialProperties, m_outputLayerMaterialSetName, false)).isFailure()) - ATH_MSG_ERROR( "Writing to DetectorStore was not successful!" ); - else { - ATH_MSG_INFO( "LayerMaterialPropertiesMap: " << m_outputLayerMaterialSetName << " written to the DetectorStore!" ); + ATH_MSG_INFO("Finalize map synchronization and write the maps to the DetectorStore."); + + for (auto& ilmIter : layerMaterialMaps ){ + // elementTable handling - if existent + if (m_mapComposition){ + Trk::SharedObject<const Trk::ElementTable> tElementTable(new Trk::ElementTable(*m_elementTable)); + ilmIter.second->updateElementTable(tElementTable); + if (ilmIter.second->elementTable()){ + ATH_MSG_INFO("ElementTable for LayerMaterialMap '" << ilmIter.first << "' found and syncrhonized." ); + ATH_MSG_INFO( *(ilmIter.second->elementTable()) ); + } + } + // detector store writing + if ( (detStore()->record(ilmIter.second, ilmIter.first, false)).isFailure()){ + ATH_MSG_ERROR( "Writing of LayerMaterialMap with name '" << ilmIter.first << "' was not successful." ); + delete ilmIter.second; + } else ATH_MSG_INFO( "LayerMaterialMap: " << ilmIter.first << " written to the DetectorStore!" ); } + delete m_elementTable; + +#ifdef TRKDETDESCR_MEMUSAGE + m_memoryLogger.refresh(getpid()); + ATH_MSG_INFO( "[ memory usage ] At the end of the material map creation."); + ATH_MSG_INFO( m_memoryLogger ); +#endif ATH_MSG_INFO( "========================================================================================= " ); ATH_MSG_INFO( " -> Total mapped hits : " << m_mapped ); double unmapped = (m_unmapped+m_mapped) ? double(m_unmapped)/double(m_unmapped+m_mapped) : 0.; ATH_MSG_INFO( " -> Total (rel.) unmapped hits : " << m_unmapped << " (" << unmapped << ")" ); - ATH_MSG_INFO(" -> Skipped (outisde) : " << m_skippedOutside ); + ATH_MSG_INFO( " -> Skipped (outisde) : " << m_skippedOutside ); ATH_MSG_INFO( "========================================================================================= " ); ATH_MSG_INFO( "finalize() successful"); - return StatusCode::SUCCESS; - } @@ -454,19 +388,28 @@ StatusCode Trk::MaterialMapping::retrieveTrackingGeometry() // Retrieve the TrackingGeometry from the DetectorStore if ((detStore()->retrieve(m_trackingGeometry, m_trackingGeometrySvc->trackingGeometryName())).isFailure()) { - ATH_MSG_FATAL( "Could not retrieve TrackingGeometry from DetectorStore!" ); + ATH_MSG_FATAL("Could not retrieve TrackingGeometry from DetectorStore!"); return StatusCode::FAILURE; } + // either get a string volume or the highest one - const Trk::TrackingVolume* trackingVolume = m_trackingGeometry->highestTrackingVolume(); // prepare the mapping volume m_mappingVolume = m_trackingGeometry->trackingVolume(m_mappingVolumeName); + // register the confined layers from the TrackingVolume registerVolume(*trackingVolume, 0); + + ATH_MSG_INFO("Add "<< m_layerRecords.size() << " confined volume layers to mapping setup."); + ATH_MSG_INFO("Add "<< m_trackingGeometry->boundaryLayers().size() << " boundary layers to mapping setup."); + + // register the layers from boundary surfaces + auto bLayerIter = m_trackingGeometry->boundaryLayers().begin(); + for (; bLayerIter != m_trackingGeometry->boundaryLayers().end(); ++bLayerIter) + insertLayerMaterialRecord(*bLayerIter->first); - ATH_MSG_INFO( "Map for " << m_layerRecords.size() << " Layers booked & prepared" ); + ATH_MSG_INFO("Map for "<< m_layerRecords.size() << " layers booked & prepared for mapping procedure"); return StatusCode::SUCCESS; @@ -478,8 +421,8 @@ void Trk::MaterialMapping::registerVolume(const Trk::TrackingVolume& tvol, int l int sublevel = lvl+1; for (int indent=0; indent<sublevel; ++indent) - std::cout << " "; - std::cout << "TrackingVolume name: " << tvol.volumeName() << std::endl; + std::cout << " "; + std::cout << "TrackingVolume name: "<< tvol.volumeName() << std::endl; // all those to be processed std::vector<const Trk::Layer*> volumeLayers; @@ -490,8 +433,8 @@ void Trk::MaterialMapping::registerVolume(const Trk::TrackingVolume& tvol, int l // this go ahead with the layers const std::vector<const Trk::Layer*>& layers = confinedLayers->arrayObjects(); for (int indent=0; indent<sublevel; ++indent) - std::cout << " "; - std::cout << "- found : " << layers.size() << " confined Layers" << std::endl; + std::cout << " "; + std::cout << "- found : "<< layers.size() << "confined Layers"<< std::endl; // loop over and fill them auto clIter = layers.begin(); auto clIterE = layers.end(); @@ -503,58 +446,19 @@ void Trk::MaterialMapping::registerVolume(const Trk::TrackingVolume& tvol, int l volumeLayers.push_back((*clIter)); } } - - // collect all entry layers treatment - const Trk::EntryLayerProvider* entryLayerProvider = tvol.entryLayerProvider(); - if (entryLayerProvider) { - // ------------------------- - const std::vector<const Trk::Layer*>& entryLayers = entryLayerProvider->layers(); - for (int indent=0; indent<sublevel; ++indent) - std::cout << " "; - std::cout << "- found : " << entryLayers.size() << " entry Layers" << std::endl; - auto elIter = entryLayers.begin(); - auto elIterE = entryLayers.end(); - for ( ; elIter != elIterE; ++elIter ) { - const Amg::Vector3D& sReferencePoint = (*elIter)->surfaceRepresentation().globalReferencePoint(); - bool insideMappingVolume = m_mappingVolume ? m_mappingVolume->inside(sReferencePoint) : true; - if ((*elIter)->layerMaterialProperties() && insideMappingVolume) - volumeLayers.push_back((*elIter)); - } - } - // now create LayerMaterialRecords for all - auto lIter = volumeLayers.begin(); - auto lIterE = volumeLayers.end(); - for ( ; lIter != lIterE; ++lIter ){ - // first occurrance, create a new LayerMaterialRecord - // - get the bin utility for the binned material (if necessary) - // - get the material first - const Trk::LayerMaterialProperties* layerMaterialProperties = (*lIter)->layerMaterialProperties(); - // - dynamic cast to the BinnedLayerMaterial - const Trk::BinnedLayerMaterial* layerBinnedMaterial - = dynamic_cast<const Trk::BinnedLayerMaterial*>(layerMaterialProperties); - // get the binned array - const Trk::BinUtility* layerMaterialBinUtility = (layerBinnedMaterial) ? layerBinnedMaterial->binUtility() : 0; - // now fill the layer material record - if (layerMaterialBinUtility){ - // create a new Layer Material record in the map - Trk::LayerMaterialRecord lmr((*lIter)->thickness(), - layerMaterialBinUtility, - (Trk::MaterialAssociationType)m_associationType); - // and fill it into the map - m_layerRecords[(*lIter)] = lmr; - } - } - + for ( auto& lIter : volumeLayers ) + insertLayerMaterialRecord(*lIter); + // step dopwn the navigation tree to reach the confined volumes const Trk::BinnedArray< Trk::TrackingVolume >* confinedVolumes = tvol.confinedVolumes(); if (confinedVolumes) { const std::vector<const Trk::TrackingVolume*>& volumes = confinedVolumes->arrayObjects(); for (int indent=0; indent<sublevel; ++indent) - std::cout << " "; - std::cout << "- found : " << volumes.size() << " confined TrackingVolumes" << std::endl; + std::cout << " "; + std::cout << "- found : "<< volumes.size() << "confined TrackingVolumes"<< std::endl; // loop over the confined volumes auto volumesIter = volumes.begin(); for (; volumesIter != volumes.end(); ++volumesIter) @@ -565,146 +469,25 @@ void Trk::MaterialMapping::registerVolume(const Trk::TrackingVolume& tvol, int l } -Trk::CompressedLayerMaterial* Trk::MaterialMapping::compressMaterial(const Trk::BinnedLayerMaterial& binnedMaterial) { - // get the matrix - const Trk::MaterialPropertiesMatrix& materialProperties = binnedMaterial.fullMaterial(); - // the vector to be created and reserve the maximum - Trk::MaterialPropertiesVector materialVector; - materialVector.reserve(m_compressedMaterialZARhoBins*m_compressedMaterialX0Bins); - // this method creates a compressed representation of the BinnedLayerMaterial - const Trk::BinUtility* cbinutil = binnedMaterial.binUtility(); - // nF x nS - size_t nFirstBins = cbinutil->max(0)+1; - size_t nSecondBins = cbinutil->max(1)+1; - // low, high boundaries - double x0min = 10e10; - double x0max = 0.; - double avZArhoMin = 10e10; - double avZArhoMax = 0.; - // create two maps, the compression map and the index map - std::vector< std::vector<unsigned short int> > materialBins; - // (1) FIRST LOOP, get boundaries - materialBins.reserve(nSecondBins); - for (size_t isec = 0; isec < nSecondBins; ++isec) { - std::vector<unsigned short int> firstbins(nFirstBins,0); - materialBins.push_back(firstbins); - // loop over the bins - for (size_t ifir = 0; ifir < nFirstBins; ++ifir) { - // get the current material properties - const Trk::MaterialProperties* matProp = materialProperties[isec][ifir]; - if (matProp) { - double tinX0 = matProp->thicknessInX0(); - double avZArho = matProp->zOverAtimesRho(); - x0min = tinX0 < x0min ? tinX0 : x0min; - x0max = tinX0 > x0max ? tinX0 : x0max; - avZArhoMin = avZArho < avZArhoMin ? avZArho : avZArhoMin; - avZArhoMax = avZArho > avZArhoMax ? avZArho : avZArhoMax; - } - } - } - // min / max is defined, find step size - double stepX0 = (x0max-x0min)/m_compressedMaterialX0Bins; - double stepZArho = (avZArhoMax-avZArhoMin)/m_compressedMaterialZARhoBins; - // get the material histogram - std::vector< std::vector< std::vector< Trk::IndexedMaterial> > > materialHistogram; - materialHistogram.reserve(m_compressedMaterialZARhoBins); - // prepare the histogram - for (size_t izarho = 0; izarho < m_compressedMaterialZARhoBins; ++izarho) { - std::vector< std::vector < Trk::IndexedMaterial > > x0materialbins; - x0materialbins.reserve(m_compressedMaterialX0Bins); - for (size_t ix0 = 0; ix0 < m_compressedMaterialX0Bins; ++ix0) { - std::vector < Trk::IndexedMaterial > materialBin; - x0materialbins.push_back( materialBin ); - } - materialHistogram.push_back(x0materialbins); - } - // fill the histogram - for (size_t isec = 0; isec < nSecondBins; ++isec) { - for (size_t ifir = 0; ifir < nFirstBins; ++ifir) { - // get the material properties - const Trk::MaterialProperties* matProp = dynamic_cast<const Trk::MaterialProperties*>(materialProperties[isec][ifir]); - if (matProp) { - // calculate the bins of the material histogram - double tinX0 = matProp->thicknessInX0(); - double avZArho = matProp->zOverAtimesRho(); - int x0bin = int( (tinX0-x0min)/stepX0 ); - int zarhobin = int( (avZArho-avZArhoMin)/stepZArho ); - // range protection - x0bin = ( (size_t)x0bin >= m_compressedMaterialX0Bins) ? m_compressedMaterialX0Bins-1 : x0bin; - x0bin = x0bin < 0 ? 0 : x0bin; - zarhobin = ( (size_t)zarhobin >= m_compressedMaterialZARhoBins) ? m_compressedMaterialZARhoBins-1 : zarhobin; - zarhobin = zarhobin < 0 ? 0 : zarhobin; - // create indexed material - Trk::IndexedMaterial idxMaterial; - idxMaterial.materialProperties = matProp; - idxMaterial.firstBin = ifir; - idxMaterial.secondBin = isec; - // fill into the material histogram - materialHistogram[zarhobin][x0bin].push_back(idxMaterial); - } - } - } - // merge the bins and ready - materialVector.push_back(0); - // prepare the histogram - for (size_t izarho = 0; izarho < m_compressedMaterialZARhoBins; ++izarho) { - for (size_t ix0 = 0; ix0 < m_compressedMaterialX0Bins; ++ix0) { - // get the indexed material properties - std::vector< Trk::IndexedMaterial > indexedMaterial = materialHistogram[izarho][ix0]; - if (indexedMaterial.size()) { - double avT = 0.; // thickness: by default on one layer it should be the same ! - double tinX0 = 0.; - double tinL0 = 0.; - double avA = 0.; - double avZ = 0.; - double avRho = 0.; - std::vector< Trk::IndexedMaterial >::iterator idmIter = indexedMaterial.begin(); - std::vector< Trk::IndexedMaterial >::iterator idmIterEnd = indexedMaterial.end(); - for ( ; idmIter != idmIterEnd; ++idmIter ) { - tinX0 += (*idmIter).materialProperties->thicknessInX0(); - tinL0 += (*idmIter).materialProperties->thicknessInL0(); - avA += (*idmIter).materialProperties->averageA(); - avZ += (*idmIter).materialProperties->averageZ(); - avRho += (*idmIter).materialProperties->averageRho(); - } - double measure = 1./(indexedMaterial.size()); - // average it - tinX0 *= measure; - tinL0 *= measure; - avA *= measure; - avZ *= measure; - avRho *= measure; - avT *= measure; - // compress to a model thickness [ rho affected ] - avRho *= avT/m_compressedMaterialThickness; - materialVector.push_back(new Trk::MaterialProperties(m_compressedMaterialThickness, - m_compressedMaterialThickness/tinX0, - m_compressedMaterialThickness/tinL0, - avA, - avZ, - avRho)); - // now set the index - int matindex = int(materialVector.size()-1); - idmIter = indexedMaterial.begin(); - for ( ; idmIter != idmIterEnd; ++idmIter ) - materialBins[(*idmIter).secondBin][(*idmIter).firstBin] = matindex; - } - } - } - - // change the 2bin matrix to a 1bin vector (better for persistency) - std::vector<unsigned short int> materialBinsVector; - materialBinsVector.reserve( (cbinutil->max(0)+1)*(cbinutil->max(1)+1) ); - std::vector< std::vector<unsigned short int> >::iterator binVecIter = materialBins.begin(); - std::vector< std::vector<unsigned short int> >::iterator binVecIterEnd = materialBins.end(); - for ( ; binVecIter != binVecIterEnd; ++binVecIter) { - std::vector<unsigned short int>::iterator binIter = (*binVecIter).begin(); - std::vector<unsigned short int>::iterator binIterEnd = (*binVecIter).end(); - for ( ; binIter != binIterEnd; ++binIter ) - materialBinsVector.push_back(*binIter); - } - // create the compressed material - return new Trk::CompressedLayerMaterial(*cbinutil,materialVector,materialBinsVector); +void Trk::MaterialMapping::insertLayerMaterialRecord(const Trk::Layer& lay){ + // first occurrance, create a new LayerMaterialRecord + // - get the bin utility for the binned material (if necessary) + // - get the material first + const Trk::LayerMaterialProperties* layerMaterialProperties = lay.layerMaterialProperties(); + // - dynamic cast to the BinnedLayerMaterial + const Trk::BinnedLayerMaterial* layerBinnedMaterial + = dynamic_cast<const Trk::BinnedLayerMaterial*>(layerMaterialProperties); + // get the binned array + const Trk::BinUtility* layerMaterialBinUtility = (layerBinnedMaterial) ? layerBinnedMaterial->binUtility() : 0; + // now fill the layer material record + if (layerMaterialBinUtility){ + // create a new Layer Material record in the map + Trk::LayerMaterialRecord lmr((m_useLayerThickness ? lay.thickness() : 1.), + layerMaterialBinUtility, + (Trk::MaterialAssociationType)m_associationType); + // and fill it into the map + m_layerRecords[&lay] = lmr; + } } diff --git a/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/MaterialValidation.cxx b/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/MaterialValidation.cxx index 432e77762234b193a69f363ad0ba7d6e91131fa2..102d5e9e105bf3ba1b230a8cd5d8500039d9325e 100755 --- a/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/MaterialValidation.cxx +++ b/Tracking/TrkDetDescr/TrkDetDescrAlgs/src/MaterialValidation.cxx @@ -10,7 +10,6 @@ #include "GeoPrimitives/GeoPrimitivesToStringConverter.h" // Trk #include "TrkDetDescrAlgs/MaterialValidation.h" -#include "TrkGeometry/EntryLayerProvider.h" #include "TrkGeometry/TrackingVolume.h" #include "TrkGeometry/TrackingGeometry.h" #include "TrkGeometry/Layer.h" @@ -19,6 +18,7 @@ #include "TrkGeometry/AssociatedMaterial.h" #include "TrkDetDescrInterfaces/ITrackingGeometrySvc.h" #include "TrkDetDescrInterfaces/IMaterialMapper.h" +#include "TrkNeutralParameters/NeutralParameters.h" // test #include "TrkVolumes/CylinderVolumeBounds.h" @@ -36,7 +36,9 @@ Trk::MaterialValidation::MaterialValidation(const std::string& name, ISvcLocator m_maxMaterialMappingEvents(25000), m_flatDist(0), m_etaMin(-3.), - m_etaMax(3.) + m_etaMax(3.), + m_runNativeNavigation(true), + m_accTinX0(0) { // ---------------------- The TrackingGeometrySvc ------------------------ // @@ -48,6 +50,8 @@ Trk::MaterialValidation::MaterialValidation(const std::string& name, ISvcLocator // ---------------------- Range setup ----------------------------------- // declareProperty("MinEta" , m_etaMin); declareProperty("MaxEta" , m_etaMax); + // ---------------------- Native navigation ----------------------------- // + declareProperty("NativeNavigation" , m_runNativeNavigation); } Trk::MaterialValidation::~MaterialValidation() @@ -77,7 +81,7 @@ StatusCode Trk::MaterialValidation::initialize() StatusCode Trk::MaterialValidation::execute() { - ATH_MSG_VERBOSE( "MaterialValidation execute() start" ); + ATH_MSG_VERBOSE( "MaterialValidation execute() start ================================================" ); // ------------------------------- get the trackingGeometry at first place if (!m_trackingGeometry) { @@ -92,10 +96,13 @@ StatusCode Trk::MaterialValidation::execute() double eta = m_etaMin + (m_etaMax-m_etaMin)*m_flatDist->shoot(); double theta = 2.*atan(exp(-eta)); double phi = M_PI * ( 2*m_flatDist->shoot() - 1.); + m_accTinX0 = 0; // get the position and riection from the random numbers Amg::Vector3D position(0.,0.,0.); Amg::Vector3D direction(sin(theta)*cos(phi),sin(theta)*sin(phi), cos(theta)); + + ATH_MSG_DEBUG("[>] Start mapping event with phi | eta = " << phi << " | " << direction.eta()); // find the start TrackingVolume const Trk::TrackingVolume* sVolume = m_trackingGeometry->lowestTrackingVolume(position); @@ -104,11 +111,8 @@ StatusCode Trk::MaterialValidation::execute() Trk::PositionAtBoundary paB = collectMaterialAndExit(*nVolume, position, direction); position = paB.first; nVolume = paB.second; - } - - // finalize the event - m_materialMapper->finalizeEvent(eta,phi); - + } + ATH_MSG_DEBUG("[<] Finishing event with collected path [X0] = " << m_accTinX0); return StatusCode::SUCCESS; } @@ -117,135 +121,172 @@ Trk::PositionAtBoundary Trk::MaterialValidation::collectMaterialAndExit(const Tr const Amg::Vector3D& direction) { // get the entry layers ----------------------------------------------------------- - std::map<double, std::pair<const Trk::Layer*, Amg::Vector3D> > intersectedLayers; std::map<double, Trk::AssociatedMaterial> collectedMaterial; - ATH_MSG_VERBOSE("Entering Volume: " << tvol.volumeName() << "- at " << Amg::toString(position)); + // all boundaries found --- proceed + Trk::PositionAtBoundary pab(position, 0); - // get theta from the direction - double theta = direction.theta(); + ATH_MSG_DEBUG("[>>] Entering Volume: " << tvol.volumeName() << "- at " << Amg::toString(position)); - // Process the entry layers if they exist - const Trk::EntryLayerProvider* entryLayerProvider = tvol.entryLayerProvider(); - if (entryLayerProvider) { - // display output - const std::vector<const Trk::Layer*>& entryLayers = entryLayerProvider->layers(); - auto eLayIter = entryLayers.begin(); - auto eLayIterE = entryLayers.end(); - for ( ; eLayIter != eLayIterE; ++eLayIter){ - Trk::SurfaceIntersection esIntersection = (*eLayIter)->surfaceRepresentation().straightLineIntersection(position, direction, true, true); - if (esIntersection.valid){ - // intersection valid : record it - intersectedLayers[esIntersection.pathLength] = std::pair<const Trk::Layer*, Amg::Vector3D>(*eLayIter,esIntersection.intersection); - // calculate the pathCorrection - double stepLength = (*eLayIter)->surfaceRepresentation().type() == Trk::Surface::Cylinder ? fabs(1./sin(theta)) : fabs(1./cos(theta)); - // get & record the material - const Trk::MaterialProperties* mprop = 0; - if ((*eLayIter)->layerMaterialProperties()){ - Amg::Vector3D mposition = (*eLayIter)->surfaceRepresentation().transform().inverse()*esIntersection.intersection; - mprop = (*eLayIter)->layerMaterialProperties()->fullMaterial(mposition); - } - // if you have material properties - if (mprop) - collectedMaterial[esIntersection.pathLength] = Trk::AssociatedMaterial(esIntersection.intersection, mprop, stepLength, &tvol, (*eLayIter)); - else - collectedMaterial[esIntersection.pathLength] = Trk::AssociatedMaterial(esIntersection.intersection, &tvol, (*eLayIter)); - - ATH_MSG_VERBOSE(" - record material hit at (entry) layer with index " << (*eLayIter)->layerIndex().value() << " - at " << Amg::toString(esIntersection.intersection) ); - if (mprop) - ATH_MSG_VERBOSE(" - MaterialProperties are " << (*mprop) ); - else - ATH_MSG_VERBOSE(" - No MaterialProperties found." ); - - } - } - } + Trk::NeutralCurvilinearParameters cvp(position,direction,0.); - // Process the contained layers if they exist - const Trk::LayerArray* layerArray = tvol.confinedLayers(); - if (layerArray) { - // display output - const std::vector<const Trk::Layer*>& layers = layerArray->arrayObjects(); - auto layIter = layers.begin(); - auto layIterE = layers.end(); - for ( ; layIter != layIterE; ++layIter){ - if ( (*layIter)->layerMaterialProperties() ){ - Trk::SurfaceIntersection lsIntersection = (*layIter)->surfaceRepresentation().straightLineIntersection(position, direction, true, true); - if (lsIntersection.valid){ - intersectedLayers[lsIntersection.pathLength] = std::pair<const Trk::Layer*, Amg::Vector3D>(*layIter,lsIntersection.intersection); - // calculate the pathCorrection - double stepLength = (*layIter)->surfaceRepresentation().type() == Trk::Surface::Cylinder ? fabs(1./sin(theta)) : fabs(1./cos(theta)); - // get & record the material - // - the position on the surface - Amg::Vector3D mposition = (*layIter)->surfaceRepresentation().transform().inverse()*lsIntersection.intersection; - const Trk::MaterialProperties* mprop = (*layIter)->layerMaterialProperties()->fullMaterial(mposition); - if (mprop) - collectedMaterial[lsIntersection.pathLength] = Trk::AssociatedMaterial(lsIntersection.intersection, mprop, stepLength, &tvol, (*layIter)); - else - collectedMaterial[lsIntersection.pathLength] = Trk::AssociatedMaterial(lsIntersection.intersection, &tvol, (*layIter)); - - ATH_MSG_VERBOSE(" - record material hit at (conf.) layer with index " << (*layIter)->layerIndex().value() << " - at " << Amg::toString(lsIntersection.intersection) ); - if (mprop) - ATH_MSG_VERBOSE(" - MaterialProperties are " << (*mprop) ); - else - ATH_MSG_VERBOSE(" - No MaterialProperties found." ); + if (m_runNativeNavigation){ + // A : collect all hit layers + auto layerIntersections = tvol.materialLayersOrdered<Trk::NeutralCurvilinearParameters>(NULL,NULL,cvp,Trk::alongMomentum); + // loop over the layers + for (auto& lCandidate : layerIntersections ) { + // get the layer + const Trk::Layer* layer = lCandidate.object; + double pathLength = lCandidate.intersection.pathLength; + // get the associate material + if (layer->layerMaterialProperties()){ + // take it from the global position + const Trk::MaterialProperties* mprop = layer->layerMaterialProperties()->fullMaterial(lCandidate.intersection.position); + if (mprop){ + double stepLength = mprop->thickness()*fabs(layer->surfaceRepresentation().pathCorrection(lCandidate.intersection.position,direction)); + collectedMaterial[pathLength] = Trk::AssociatedMaterial(lCandidate.intersection.position, mprop, stepLength, &tvol, layer); + } + } + } + // B : collect all boundary layers, start from last hit layer + Amg::Vector3D lastPosition = collectedMaterial.size() ? collectedMaterial.rbegin()->second.materialPosition() : (position + direction.unit()); + Trk::NeutralCurvilinearParameters lcp(lastPosition,direction,0.); + // boundary surfaces + auto boundaryIntersections = tvol.boundarySurfacesOrdered<Trk::NeutralCurvilinearParameters>(lcp,Trk::alongMomentum); + if (boundaryIntersections.size()){ + // by definition is the first one + lastPosition = boundaryIntersections.begin()->intersection.position; + const Trk::BoundarySurface<Trk::TrackingVolume>* bSurfaceTV = boundaryIntersections.begin()->object; + const Trk::Surface& bSurface = bSurfaceTV->surfaceRepresentation(); + // get the path lenght to it + if (bSurface.materialLayer() && bSurface.materialLayer()->layerMaterialProperties()){ + const Trk::MaterialProperties* mprop = bSurface.materialLayer()->layerMaterialProperties()->fullMaterial(lastPosition); + double pathLength = (lastPosition-position).mag(); + if (mprop){ + double stepLength = mprop->thickness()*fabs(bSurface.pathCorrection(lastPosition,direction)); + collectedMaterial[pathLength] = Trk::AssociatedMaterial(lastPosition, mprop, stepLength, &tvol, bSurface.materialLayer()); + } else + collectedMaterial[pathLength] = Trk::AssociatedMaterial(lastPosition, &tvol, bSurface.materialLayer()); + } + // set the new volume + const Trk::TrackingVolume* naVolume = bSurfaceTV->attachedVolume(lastPosition, direction, Trk::alongMomentum); + pab = Trk::PositionAtBoundary(lastPosition,naVolume); + } else + pab = Trk::PositionAtBoundary(lastPosition,0); + } else { + std::map<double, std::pair<const Trk::Layer*, Amg::Vector3D> > intersectedLayers; + + // Process the contained layers if they exist + const Trk::LayerArray* layerArray = tvol.confinedLayers(); + if (layerArray) { + // display output + const std::vector<const Trk::Layer*>& layers = layerArray->arrayObjects(); + auto layIter = layers.begin(); + auto layIterE = layers.end(); + for ( ; layIter != layIterE; ++layIter){ + if ( (*layIter)->layerMaterialProperties() ){ + Trk::Intersection lsIntersection = (*layIter)->surfaceRepresentation().straightLineIntersection(position, direction, true, true); + if (lsIntersection.valid){ + intersectedLayers[lsIntersection.pathLength] = std::pair<const Trk::Layer*, Amg::Vector3D>(*layIter,lsIntersection.position); + // get & record the material + // - the position on the surface + Amg::Vector3D mposition = (*layIter)->surfaceRepresentation().transform().inverse()*lsIntersection.position; + const Trk::MaterialProperties* mprop = (*layIter)->layerMaterialProperties()->fullMaterial(mposition); + if (mprop) { + double stepLength = mprop->thickness()*fabs((*layIter)->surfaceRepresentation().pathCorrection(lsIntersection.position,direction)); + collectedMaterial[lsIntersection.pathLength] = Trk::AssociatedMaterial(lsIntersection.position, mprop, stepLength, &tvol, (*layIter)); + } else + collectedMaterial[lsIntersection.pathLength] = Trk::AssociatedMaterial(lsIntersection.position, &tvol, (*layIter)); + + ATH_MSG_VERBOSE("[>>>>] record material hit at layer with index " << (*layIter)->layerIndex().value() << " - at " << Amg::toString(lsIntersection.position) ); + if (mprop) + ATH_MSG_VERBOSE("[>>>>] MaterialProperties are " << (*mprop) ); + else + ATH_MSG_VERBOSE("[>>>>] No MaterialProperties found." ); + } } } - } - } + } + + // material for confined layers collected, now go to boundary + + // update the position to the last one + Amg::Vector3D lastPosition = intersectedLayers.size() ? (*(--(intersectedLayers.end()))).second.second : position; + + std::map<double, Trk::VolumeExit > volumeExits; + // now find the exit point + const std::vector< Trk::SharedObject<const Trk::BoundarySurface<Trk::TrackingVolume> > >& bSurfaces = tvol.boundarySurfaces(); + auto bSurfIter = bSurfaces.begin(); + auto bSurfIterE = bSurfaces.end(); + for ( ; bSurfIter != bSurfIterE; ++bSurfIter){ + // omit positions on the surface + if ( !(*bSurfIter)->surfaceRepresentation().isOnSurface(lastPosition, true, 0.1, 0.1) ){ + Trk::Intersection evIntersection = (*bSurfIter)->surfaceRepresentation().straightLineIntersection(lastPosition, direction, true, true); + ATH_MSG_VERBOSE("[>>>>] boundary surface intersection / validity :" << Amg::toString(evIntersection.position) << " / " << evIntersection.valid); + ATH_MSG_VERBOSE("[>>>>] with path length = " << evIntersection.pathLength ); + if (evIntersection.valid){ + // next attached Tracking Volume + const Trk::TrackingVolume* naVolume = (*bSurfIter)->attachedVolume(evIntersection.position, direction, Trk::alongMomentum); + // put it into the map + volumeExits[evIntersection.pathLength] = Trk::VolumeExit(naVolume, (&(*bSurfIter)->surfaceRepresentation()), evIntersection.position); + // volume exit + ATH_MSG_VERBOSE("[>>>>] found volume exit - at " << Amg::toString(evIntersection.position) ); + } + } else + ATH_MSG_VERBOSE("[>>>>] starting position is on surface ! " ); + } + // prepare the boundary + if (volumeExits.size()){ + // get the first entry in the map: closest next volume + VolumeExit closestVolumeExit = (*volumeExits.begin()).second; + // check if the volume exit boundary has material attached + const Trk::Surface* bSurface = closestVolumeExit.bSurface; + if ( bSurface && bSurface->materialLayer() && bSurface->materialLayer()->layerMaterialProperties()){ + ATH_MSG_VERBOSE("[>>>>] The boundary surface has an associated layer, collect material from there"); + const Trk::MaterialProperties* mprop = bSurface->materialLayer()->layerMaterialProperties()->fullMaterial(closestVolumeExit.vExit); + double pathToExit = (closestVolumeExit.vExit-lastPosition).mag(); + if (mprop){ + double stepLength = mprop->thickness()*fabs(bSurface->pathCorrection(closestVolumeExit.vExit,direction)); + collectedMaterial[pathToExit] = Trk::AssociatedMaterial(closestVolumeExit.vExit, mprop, stepLength, &tvol, bSurface->materialLayer()); + } else + collectedMaterial[pathToExit] = Trk::AssociatedMaterial(closestVolumeExit.vExit, &tvol, bSurface->materialLayer()); + } + // + if (closestVolumeExit.nVolume != &tvol && closestVolumeExit.nVolume) { + ATH_MSG_VERBOSE("[>>>>] Next Volume: " << closestVolumeExit.nVolume->volumeName() << " - at " << Amg::toString(closestVolumeExit.vExit) ); + // return for further navigation + pab = Trk::PositionAtBoundary(closestVolumeExit.vExit,closestVolumeExit.nVolume); + } + } else { + ATH_MSG_VERBOSE( "[>>>>] No exit found from Volume '" << tvol.volumeName() << "' - starting radius = " << lastPosition.perp() ); + const Trk::CylinderVolumeBounds* cvb = dynamic_cast<const Trk::CylinderVolumeBounds*>(&(tvol.volumeBounds())); + if (cvb) + ATH_MSG_VERBOSE( "[>>>>] Volume outer radius = " << cvb->outerRadius() ); + } + } + // finally collect the material + ATH_MSG_DEBUG("[>>>] Collecting materials from "<< collectedMaterial.size() << " layers"); // provide the material to the material mapper auto cmIter = collectedMaterial.begin(); auto cmIterE = collectedMaterial.end(); - for ( ; cmIter != cmIterE; ++cmIter ) + for ( ; cmIter != cmIterE; ++cmIter ){ m_materialMapper->recordMaterialHit(cmIter->second, cmIter->second.materialPosition()); - - // update the position to the last one - Amg::Vector3D lastPosition = intersectedLayers.size() ? (*(--(intersectedLayers.end()))).second.second : position; - // exit the volume - std::map<double, std::pair<const Trk::TrackingVolume*, Amg::Vector3D> > volumeExits; - // now find the exit point - const std::vector< Trk::SharedObject<const Trk::BoundarySurface<Trk::TrackingVolume> > >& bSurfaces = tvol.boundarySurfaces(); - auto bSurfIter = bSurfaces.begin(); - auto bSurfIterE = bSurfaces.end(); - for ( ; bSurfIter != bSurfIterE; ++bSurfIter){ - // omit positions on the surface - if ( !(*bSurfIter)->surfaceRepresentation().isOnSurface(lastPosition, true, 0.1, 0.1) ){ - Trk::SurfaceIntersection evIntersection = (*bSurfIter)->surfaceRepresentation().straightLineIntersection(lastPosition, direction, true, true); - ATH_MSG_DEBUG(" - boundary surface intersection / validity :" << Amg::toString(evIntersection.intersection) << " / " << evIntersection.valid); - ATH_MSG_DEBUG(" - with path length = " << evIntersection.pathLength ); - if (evIntersection.valid){ - // next attached Tracking Volume - const Trk::TrackingVolume* naVolume = (*bSurfIter)->attachedVolume(evIntersection.intersection, direction, Trk::alongMomentum); - // put it into the map - volumeExits[evIntersection.pathLength] = std::pair<const Trk::TrackingVolume*, Amg::Vector3D>(naVolume,evIntersection.intersection); - // volume exit - ATH_MSG_DEBUG(" - found volume exit - at " << Amg::toString(evIntersection.intersection) ); - } - } else { - ATH_MSG_DEBUG(" - starting position is on surface ! " ); - } - } - - if (volumeExits.size()){ - // get the first entry in the map: closest next volume - const Trk::TrackingVolume* cnVolume = (*volumeExits.begin()).second.first; - if (cnVolume != &tvol) { - if (cnVolume) - ATH_MSG_VERBOSE("Next Volume: " << cnVolume->volumeName() << " - at " << Amg::toString((*volumeExits.begin()).second.second) ); - // record that - m_materialMapper->record((*volumeExits.begin()).second.second); - // return for further navigation - return Trk::PositionAtBoundary((*volumeExits.begin()).second.second ,cnVolume); + m_accTinX0 += cmIter->second.steplengthInX0(); + int layerIndex = cmIter->second.associatedLayer() ? cmIter->second.associatedLayer()->layerIndex().value() : 0; + ATH_MSG_DEBUG("[>>>] Accumulate pathLength/X0 on layer with index " << layerIndex << " - t/X0 (total so far) = " << cmIter->second.steplengthInX0() << " (" << m_accTinX0 << ")"); + if (layerIndex){ + std::string surfaceType = cmIter->second.associatedLayer()->surfaceRepresentation().type() == Trk::Surface::Cylinder ? "Cylinder at radius = " : "Disc at z-position = "; + std::string layerType = cmIter->second.associatedLayer()->surfaceArray() ? "Active " : "Passive "; + double rz = cmIter->second.associatedLayer()->surfaceRepresentation().type() == Trk::Surface::Cylinder ? cmIter->second.associatedLayer()->surfaceRepresentation().bounds().r() : + cmIter->second.associatedLayer()->surfaceRepresentation().center().z(); + ATH_MSG_DEBUG(" " << layerType << surfaceType << rz); } - } else{ - ATH_MSG_DEBUG( "No exit found from Volume '" << tvol.volumeName() << "' - starting radius = " << lastPosition.perp() ); - const Trk::CylinderVolumeBounds* cvb = dynamic_cast<const Trk::CylinderVolumeBounds*>(&(tvol.volumeBounds())); - if (cvb) - ATH_MSG_DEBUG( " Volume outer radius = " << cvb->outerRadius() ); + ATH_MSG_DEBUG(" Distance to origin is " << cmIter->second.materialPosition().mag() ); } - return Trk::PositionAtBoundary(position, 0); + // return what you have + return pab; }