Skip to content
Snippets Groups Projects

Compare revisions

Changes are shown as if the source revision was being merged into the target revision. Learn more about comparing revisions.

Source

Select target project
No results found

Target

Select target project
  • 1810337/CEPCSW
  • shexin/CEPCSW
  • dudejing/CEPCSW
  • yudian2002/cepcsw-otb-development
  • cepcsw/CEPCSW
  • cepc/CEPCSW
  • shixin/CEPCSW
  • lizhan/CEPCSW
  • 1365447033/CEPCSW
  • shihy/CEPCSW
  • sunwy/CEPCSW
  • guofangyi/cepcsw-release
  • lintao/CEPCSW
  • tanggy/CEPCSW
  • gongjd1119/CEPCSW
  • 221840222/CEPCSW
  • lihn/CEPCSW
  • thinking/CEPCSW
  • myliu/CEPCSW
  • shihy/cepcsw-dose
  • zhaog/CEPCSW
  • 201840277/CEPCSW
  • wangchu/CEPCSW
  • xiaolin.wang/CEPCSW
  • fucd/CEPCSW1
  • tyzhang/CEPCSW
  • yudian2002/cepcsw-ote-development
  • songwz/cepcsw-tdr
  • luhc/CEPCSW
  • tangyb/CEPCSW
  • dhb112358/CEPCSW
  • chenbp/CEPCSW
  • guolei/CEPCSW
  • yudian2002/cepcsw-otk-end-cap-development
  • jiangxj/CEPCSW
  • yudian2002/cepcsw-geo-upgrade
  • fangwx/CEPCSW
  • yudian2002/cepcsw-geo-upgrade-v-2
  • mengwq/CEPCSW
  • zhangxm/CEPCSW
  • chenye/CEPCSW
  • wuchonghao9612/CEPCSW
  • xuchj7/CEPCSW
  • yudian2002/cepcsw-otk-endcap-update-01
  • lizhihao/CEPCSW
  • laipz/CEPCSW
  • zhangkl/CEPCSW
  • lihp29/CEPCSW
  • shuxian/CEPCSW
  • zhangyz/CEPCSW
  • zhangjinxian/CEPCSW_20250110
  • glliu/CEPCSW
  • shuohan/CEPCSW
  • fucd/CEPCSW
  • starr136a/CEPCSW
  • yudian2002/CEPCSW
  • wanjw03/CEPCSW
  • zyjonah/CEPCSW
  • maxt/CEPCSW
  • wangshi/CEPCSW
60 results
Show changes
Showing
with 4265 additions and 31 deletions
//====================================================================
// DDSim - LC detector models in DD4hep
//--------------------------------------------------------------------
// F.Gaede, DESY
// $Id$
//====================================================================
#include "DD4hep/DetFactoryHelper.h"
#include "DD4hep/DD4hepUnits.h"
#include "DD4hep/DetType.h"
#include "DDRec/Surface.h"
#include "XMLHandlerDB.h"
#include "XML/Utilities.h"
#include <cmath>
#include "DDRec/DetectorData.h"
//#include "GearWrapper.h"
using namespace std;
using dd4hep::BUILD_ENVELOPE;
using dd4hep::Box;
using dd4hep::DetElement;
using dd4hep::Detector;
using dd4hep::Material;
using dd4hep::PlacedVolume;
using dd4hep::PolyhedraRegular;
using dd4hep::Position;
using dd4hep::Ref_t;
using dd4hep::RotationZYX;
using dd4hep::SensitiveDetector;
using dd4hep::Transform3D;
using dd4hep::Tube;
using dd4hep::Volume;
using dd4hep::xml::_toString;
using dd4hep::rec::LayeredCalorimeterData;
/** Construction of the coil, ported from Mokka drivers SCoil02.cc and Coil01.cc
*
* Mokka History:
* SCoil02.cc
* F.Gaede, DESY: based on SCoil01, with added parameters for the
* clearance to the yoke:
* Hcal_Coil_additional_gap : adjust the actual gap in r (Hcal_R_max allready defines a gap)
* Coil_Yoke_radial_clearance : -> defines inner r of yoke
* Coil_Yoke_lateral_clearance : -> defines zEndcap of yoke
* Coil00.cc
* - first implementation P. Mora de Freitas (may 01)
* - F.Gaede: write out parameters to GEAR (Oct 08)
* Coil00.cc:
* - V. Saveliev: replaced simple Al-tube with more detailed structure (cryostat, etc )
*
* @author: F.Gaede, DESY, Aug 2014
*/
static Ref_t create_element(Detector& theDetector, xml_h element, SensitiveDetector sens) {
//------------------------------------------
// See comments starting with '//**' for
// hints on porting issues
//------------------------------------------
xml_det_t x_det = element;
string name = x_det.nameStr();
DetElement coil( name, x_det.id() ) ;
// --- create an envelope volume and position it into the world ---------------------
Volume envelope = dd4hep::xml::createPlacedEnvelope( theDetector, element , coil ) ;
dd4hep::xml::setDetectorTypeFlag( element, coil ) ;
if( theDetector.buildType() == BUILD_ENVELOPE ) return coil ;
//-----------------------------------------------------------------------------------
sens.setType("tracker");
PlacedVolume pv;
//######################################################################################################################################################################
// code ported from Coil02::construct() :
//##################################
cout << "\nBuilding Coil..." << endl;
xml_comp_t x_tube (x_det.child(_U(tube)));
double inner_radius = x_tube.rmin() ;
double outer_radius = x_tube.rmax() ;
double half_z = x_tube.dz() ;
cout << "\n... cryostat inner_radius " << inner_radius
<< "\n... cryostat outer_radius " << outer_radius
<< "\n... cryostat half_z " << half_z
<< endl;
double tCoil = outer_radius - inner_radius;
double zMandrel = half_z-197*dd4hep::mm;
double rInnerMain = 175./750.*tCoil;
double rOuterMain = 426./750.*tCoil;
double zCorrect = zMandrel/3;
double zMain = (zMandrel-zCorrect)*2/3;
double rInnerMandrel = rOuterMain;
double rOuterMandrel = 654./750.*tCoil;
double rInnerSci1 = 90*dd4hep::mm;
double rInnerSci2 = 105*dd4hep::mm;
double rInnerSci3 = -90*dd4hep::mm;
double rInnerSci4 = -105*dd4hep::mm;
double zReduceSci = 100*dd4hep::mm;
Material coilMaterial = theDetector.material( x_tube.materialStr() ) ;
//FG: for now fall back to a simple tube filled with Al
// the code below has to many hard coded numbers
// that need verification and then need to be converted
// to xml parameters ...
#define code_is_cleaned_up true
#if 0 //!code_is_cleaned_up
Tube coil_tube( x_tube.rmin(), x_tube.rmax(), x_tube.dz() );
Volume coil_vol( "coil_vol", coil_tube , coilMaterial );
pv = envelope.placeVolume( coil_vol ) ;
coil.setVisAttributes( theDetector, "BlueVis" , coil_vol );
cout << " ... for the time being simply use a tube of aluminum ..." << endl ;
//=========================================================================================================
#else
//... Coil Cryostat (Al, inside vacuum)
//... inner cylinder
Tube CoilEnvelopeSolid_1( inner_radius, 40.* dd4hep::mm + inner_radius , half_z ) ;
Volume CoilLogical_1( "CoilEnvelope_1", CoilEnvelopeSolid_1, coilMaterial ) ;
coil.setVisAttributes( theDetector, "ShellVis" , CoilLogical_1 );
pv = envelope.placeVolume( CoilLogical_1 ) ;
//... outer cylinder
Tube CoilEnvelopeSolid_2 ( -30*dd4hep::mm + outer_radius, outer_radius , half_z ) ;
Volume CoilLogical_2( "CoilEnvelope_2", CoilEnvelopeSolid_2, coilMaterial ) ;
coil.setVisAttributes( theDetector, "ShellVis" , CoilLogical_2 );
pv = envelope.placeVolume( CoilLogical_2 ) ;
//... side wall left
Tube CoilEnvelopeSolid_3( 40*dd4hep::mm + inner_radius, -30*dd4hep::mm + outer_radius, 25.* dd4hep::mm ) ;
Volume CoilLogical_3( "CoilEnvelope_3", CoilEnvelopeSolid_3, coilMaterial ) ;
coil.setVisAttributes( theDetector, "ShellVis" , CoilLogical_3 );
pv = envelope.placeVolume( CoilLogical_3 , Position( 0., 0., -25.*dd4hep::mm + half_z ) ) ;
//... side wall right
// Tube CoilEnvelopeSolid_4( 40*dd4hep::mm + inner_radius, -30*dd4hep::mm + outer_radius, 25.* dd4hep::mm ) ;
// Volume CoilLogical_4( "CoilEnvelope_4", CoilEnvelopeSolid_4, coilMaterial ) ;
// coil.setVisAttributes( theDetector, "BlueVis" , CoilLogical_4 );
// pv = envelope.placeVolume( CoilLogical_4 , Position( 0., 0., 25.*dd4hep::mm - half_z ) ) ;
//simply place the same volume again
pv = envelope.placeVolume( CoilLogical_3 , Position( 0., 0., 25.*dd4hep::mm - half_z ) ) ;
//... Coil modules
//... main coll module 1,2,3
Tube CoilMainSolid_1( rInnerMain + inner_radius, rOuterMain + inner_radius, zMain/2-0.*dd4hep::mm ) ;
Volume CoilMainLogical_1( "CoilMain_1" , CoilMainSolid_1, coilMaterial ) ;
coil.setVisAttributes( theDetector, "GreyVis" , CoilMainLogical_1 );
pv = envelope.placeVolume( CoilMainLogical_1 , Position( 0., 0., -zMain ) ) ;
pv = envelope.placeVolume( CoilMainLogical_1 , Position( 0., 0., 0. ) ) ;
pv = envelope.placeVolume( CoilMainLogical_1 , Position( 0., 0., zMain ) ) ;
Material aluminium = theDetector.material("G4_Al");
Material polystyrene = theDetector.material("G4_POLYSTYRENE");
//... corrected coil module 1,2
Tube CoilCorrectSolid_1(rInnerMain + inner_radius, rOuterMain + inner_radius, zCorrect/2);
Volume CoilCorrectLogical_1("CoilCorrect_1", CoilCorrectSolid_1, aluminium);
coil.setVisAttributes( theDetector, "BlueVis", CoilCorrectLogical_1);
pv = envelope.placeVolume(CoilCorrectLogical_1, Position(0., 0., -zMain*3/2-zCorrect/2));
pv = envelope.placeVolume(CoilCorrectLogical_1, Position(0., 0., zMain*3/2+zCorrect/2));
//... Coil mandrel
Tube CoilMandrelSolid(rInnerMandrel + inner_radius, rOuterMandrel + inner_radius, zMandrel);
Volume CoilMandrelLogical("CoilMandrel", CoilMandrelSolid, aluminium);
coil.setVisAttributes( theDetector, "GreenVis", CoilMandrelLogical);
pv = envelope.placeVolume(CoilMandrelLogical, Position(0., 0., 0.));
//... Coil sensitive detectors
int layer_id=1; //Put in the database!!!
// Threshold is 20%. mip = 200 keV/dd4hep::mm
const double sensitive_thickness = 10. *dd4hep::mm;
//theCoilSD = new TRKSD00("COIL", sensitive_thickness * 200 * keV * 0.01);
//RegisterSensitiveDetector(theCoilSD);
double rOuterSci1 = rInnerSci1 + sensitive_thickness;
double rOuterSci2 = rInnerSci2 + sensitive_thickness;
double rOuterSci3 = rInnerSci3 + sensitive_thickness;
double rOuterSci4 = rInnerSci4 + sensitive_thickness;
double halfZSci = half_z - zReduceSci;
//... Scintillator Detector layer 1
if((rOuterSci1+inner_radius)/cos(dd4hep::pi/24)<rInnerMain+inner_radius){
const double zPozBarrelArray_1 = halfZSci;
const double rInnerBarrelArray_1 = rInnerSci1+inner_radius;
const double rOuterBarrelArray_1 = rOuterSci1+inner_radius;
PolyhedraRegular CoilScintSolid_1(24, rInnerBarrelArray_1, rOuterBarrelArray_1, zPozBarrelArray_1*2);
Volume CoilScintLogical_1("CoilScint_1", CoilScintSolid_1, polystyrene);
coil.setVisAttributes( theDetector, "RedVis", CoilScintLogical_1);
CoilScintLogical_1.setSensitiveDetector(sens);
pv = envelope.placeVolume(CoilScintLogical_1, Position(0., 0., 0.));
pv.addPhysVolID("layer",layer_id);
}
layer_id++;
//... Scintillation Detector layer 2
if((rOuterSci2+inner_radius)/cos(dd4hep::pi/24)<rInnerMain+inner_radius){
const double zPozBarrelArray_2 = halfZSci;
const double rInnerBarrelArray_2 = rInnerSci2+inner_radius;
const double rOuterBarrelArray_2 = rOuterSci2+inner_radius;
PolyhedraRegular CoilScintSolid_2(24, rInnerBarrelArray_2, rOuterBarrelArray_2, zPozBarrelArray_2*2);
Volume CoilScintLogical_2("CoilScint_2", CoilScintSolid_2, polystyrene);
coil.setVisAttributes( theDetector, "RedVis", CoilScintLogical_2);
CoilScintLogical_2.setSensitiveDetector(sens);
pv = envelope.placeVolume(CoilScintLogical_2, Position(0., 0., 0.));
pv.addPhysVolID("layer",layer_id);
}
layer_id++;
//... Scint detector layer 3
if(rInnerSci3+outer_radius>rOuterMandrel+inner_radius){
const double zPozBarrelArray_3 = halfZSci;
const double rInnerBarrelArray_3 = rInnerSci3+outer_radius;
const double rOuterBarrelArray_3 = rOuterSci3+outer_radius;
PolyhedraRegular CoilScintSolid_3(24, rInnerBarrelArray_3, rOuterBarrelArray_3, zPozBarrelArray_3*2);
Volume CoilScintLogical_3("CoilScint_3", CoilScintSolid_3, polystyrene);
coil.setVisAttributes( theDetector, "RedVis", CoilScintLogical_3);
CoilScintLogical_3.setSensitiveDetector(sens);
pv = envelope.placeVolume(CoilScintLogical_3, Position(0., 0., 0.));
pv.addPhysVolID("layer",layer_id);
}
layer_id++;
//... Scintillation Detector layer 4
if(rInnerSci4+outer_radius>rOuterMandrel+inner_radius){
const double zPozBarrelArray_4 = halfZSci;
const double rInnerBarrelArray_4 = rInnerSci4+outer_radius;
const double rOuterBarrelArray_4 = rOuterSci4+outer_radius;
PolyhedraRegular CoilScintSolid_4(24, rInnerBarrelArray_4, rOuterBarrelArray_4, zPozBarrelArray_4*2);
Volume CoilScintLogical_4("CoilScint_4", CoilScintSolid_4, polystyrene);
coil.setVisAttributes( theDetector, "RedVis", CoilScintLogical_4);
CoilScintLogical_4.setSensitiveDetector(sens);
pv = envelope.placeVolume(CoilScintLogical_4, Position(0., 0., 0.));
pv.addPhysVolID("layer",layer_id);
}
#ifdef MOKKA_GEAR
//----------------------------------------------------
// MokkaGear
//----------------------------------------------------
MokkaGear* gearMgr = MokkaGear::getMgr() ;
gear::GearParametersImpl* gp = new gear::GearParametersImpl ;
//Inner Cylinder
gp->setDoubleVal("Coil_cryostat_inner_cyl_inner_radius",
inner_radius);
gp->setDoubleVal("Coil_cryostat_inner_cyl_outer_radius",
40.*dd4hep::mm+inner_radius);
gp->setDoubleVal("Coil_cryostat_inner_cyl_half_z", half_z);
gp->setStringVal("Coil_material_inner_cyl", "aluminium");
//Outer Cylinder
gp->setDoubleVal("Coil_cryostat_outer_cyl_inner_radius",
-30*dd4hep::mm+outer_radius);
gp->setDoubleVal("Coil_cryostat_outer_cyl_outer_radius",
outer_radius);
gp->setDoubleVal("Coil_cryostat_outer_cyl_half_z", half_z);
gp->setStringVal("Coil_material_outer_cyl", "aluminium");
//FG: add the parameters under the 'old' names as expected by the reconstruction:
gp->setDoubleVal("Coil_cryostat_inner_radius", inner_radius);
gp->setDoubleVal("Coil_cryostat_outer_radius", outer_radius);
gp->setDoubleVal("Coil_cryostat_half_z", half_z);
//Side wall left
gp->setDoubleVal("Coil_cryostat_side_l_inner_radius",
40*dd4hep::mm+inner_radius);
gp->setDoubleVal("Coil_cryostat_side_l_outer_radius",
-30*dd4hep::mm+outer_radius);
gp->setDoubleVal("Coil_cryostat_side_l_half_z", 25.*dd4hep::mm);
gp->setStringVal("Coil_material_side_l", "aluminium");
//Side wall right
gp->setDoubleVal("Coil_cryostat_side_r_inner_radius",
40*dd4hep::mm+inner_radius);
gp->setDoubleVal("Coil_cryostat_side_r_outer_radius",
-30*dd4hep::mm+outer_radius);
gp->setDoubleVal("Coil_cryostat_side_r_half_z", 25.*dd4hep::mm);
gp->setStringVal("Coil_material_side_r", "aluminium");
// Coil modules
gp->setDoubleVal("Coil_cryostat_modules_inner_radius",
rInnerMain+inner_radius);
gp->setDoubleVal("Coil_cryostat_modules_outer_radius",
rOuterMain+inner_radius);
gp->setDoubleVal("Coil_cryostat_modules_half_z", zMain/2-20.*dd4hep::mm);
gp->setStringVal("Coil_material_modules", "aluminium");
gp->setDoubleVal("Coil_cryostat_c_modules_inner_radius",
rInnerMain+inner_radius);
gp->setDoubleVal("Coil_cryostat_c_modules_outer_radius",
rOuterMain+inner_radius);
gp->setDoubleVal("Coil_cryostat_c_modules_half_z", zCorrect);
gp->setStringVal("Coil_material_c_modules", "aluminium");
//Coil mandrel
gp->setDoubleVal("Coil_cryostat_mandrel_inner_radius",
rInnerMandrel+inner_radius);
gp->setDoubleVal("Coil_cryostat_mandrel_outer_radius",
rOuterMandrel+inner_radius);
gp->setDoubleVal("Coil_cryostat_mandrel_half_z", zMandrel);
gp->setStringVal("Coil_material_mandrel", "aluminium");
//Sensitive detectors
gp->setDoubleVal("Coil_cryostat_scint1_inner_radius",
rInnerSci1+inner_radius);
gp->setDoubleVal("Coil_cryostat_scint1_outer_radius",
rOuterSci1+inner_radius);
gp->setDoubleVal("Coil_cryostat_scint1_zposin",
-zReduceSci+half_z);
gp->setDoubleVal("Coil_cryostat_scint1_zposend",
+zReduceSci+half_z);
gp->setStringVal("Coil_material_scint1", "polystyrene");
gp->setDoubleVal("Coil_cryostat_scint2_inner_radius",
rInnerSci2+inner_radius);
gp->setDoubleVal("Coil_cryostat_scint2_outer_radius",
rOuterSci2+inner_radius);
gp->setDoubleVal("Coil_cryostat_scint2_zposin",
-zReduceSci+half_z);
gp->setDoubleVal("Coil_cryostat_scint2_zposend",
+zReduceSci+half_z);
gp->setStringVal("Coil_material_scint2", "polystyrene");
gp->setDoubleVal("Coil_cryostat_scint3_inner_radius",
rInnerSci3+outer_radius);
gp->setDoubleVal("Coil_cryostat_scint3_outer_radius",
rOuterSci3+outer_radius);
gp->setDoubleVal("Coil_cryostat_scint3_zposin",
-zReduceSci+half_z);
gp->setDoubleVal("Coil_cryostat_scint3_zposend",
+zReduceSci+half_z);
gp->setStringVal("Coil_material_scint3", "polystyrene");
gp->setDoubleVal("Coil_cryostat_scint4_inner_radius",
rInnerSci4+outer_radius);
gp->setDoubleVal("Coil_cryostat_scint4_outer_radius",
rOuterSci4+outer_radius);
gp->setDoubleVal("Coil_cryostat_scint4_zposin",
-zReduceSci+half_z);
gp->setDoubleVal("Coil_cryostat_scint4_zposend",
+zReduceSci+half_z);
gp->setStringVal("Coil_material_scint4", "polystyrene");
gearMgr->setGearParameters("CoilParameters", gp);
#endif
cout << "Coil done.\n" << endl;
// //====== create the meassurement surface ===================
// Vector3D u,v,n ;
// if( faces_IP == 0 ){
// // will be rotated around z-axis later
// u.fill( 0. , -1. , 0. ) ;
// v.fill( 0. , 0. , 1. ) ;
// n.fill( -1. , 0. , 0. ) ;
// // implement 7 deg stereo angle
// u.fill( 0. , -cos( 3.5 * dd4hep::deg ) , -sin( 3.5 * dd4hep::deg ) ) ;
// v.fill( 0. , -sin( 3.5 * dd4hep::deg ) , cos( 3.5 * dd4hep::deg ) ) ;
// } else {
// u.fill( 0. , 1. , 0. ) ;
// v.fill( 0. , 0. , 1. ) ;
// n.fill( 1. , 0. , 0. ) ;
// // implement 7 deg stereo angle
// u.fill( 0. , cos( 3.5 * dd4hep::deg ) , sin( 3.5 * dd4hep::deg ) ) ;
// v.fill( 0. , -sin( 3.5 * dd4hep::deg ) , cos( 3.5 * dd4hep::deg ) ) ;
// }
// double inner_thick = sensitive_thickness / 2.0 ;
// double outer_thick = sensitive_thickness / 2.0 + support_thickness ; // support is on top
// VolPlane surf( sitSenLogical , SurfaceType(SurfaceType::Sensitive,SurfaceType::Measurement1D) ,inner_thick, outer_thick , u,v,n ) ; //,o ) ;
// // vector of sensor placements - needed for DetElements in ladder loop below
// std::vector<PlacedVolume> pvV( layer_geom.n_sensors_per_ladder ) ;
// //============================================================
#endif //code_is_cleaned_up
//=========================================================================================================
cout << "SCoil02 done.\n" << endl;
//######################################################################################################################################################################
//--------------------------------------
//coil.setVisAttributes( theDetector, x_det.visStr(), envelope );
//added coded by Thorben Quast
//the coil is modelled as a calorimeter layer to be consistent with the
//implementation of the solenoid (layers) of CLIC
LayeredCalorimeterData* coilData = new LayeredCalorimeterData;
//NN: Adding the rest of the data
coilData->inner_symmetry = 0;
coilData->outer_symmetry = 0;
coilData->layoutType = LayeredCalorimeterData::BarrelLayout ;
coilData->extent[0] = inner_radius ;
coilData->extent[1] = outer_radius;
coilData->extent[2] = 0. ;
coilData->extent[3] = half_z;
//NN: These probably need to be fixed and ced modified to read the extent, rather than the layer
LayeredCalorimeterData::Layer coilLayer;
coilLayer.distance = inner_radius;
coilLayer.inner_thickness = ( outer_radius - inner_radius ) / 2. ;
coilLayer.outer_thickness = coilLayer.inner_thickness ;
coilLayer.cellSize0 = 0; //equivalent to
coilLayer.cellSize1 = half_z; //half extension along z-axis
coilData->layers.push_back(coilLayer);
coil.addExtension< LayeredCalorimeterData >( coilData ) ;
return coil;
}
DECLARE_DETELEMENT(SCoil02,create_element)
......@@ -327,7 +327,13 @@ static Ref_t create_element(Detector& theDetector, xml_h e, SensitiveDetector se
PlacedVolume pv;
sens.setType("tracker");
if (x_det.hasChild(_U(sensitive))) {
xml_dim_t sd_typ = x_det.child(_U(sensitive));
sens.setType(sd_typ.typeStr());
}
else {
sens.setType("tracker");
}
// --- create assembly and DetElement for support and service volumes
......@@ -1016,7 +1022,11 @@ static Ref_t create_element(Detector& theDetector, xml_h e, SensitiveDetector se
petalSupport(theDetector, ftd, valuesDict, FTDPetalAirLogical ) ;
VolVec volV = petalSensor( theDetector, ftd, sens, valuesDict, FTDPetalAirLogical );
if (x_det.hasAttr(_U(limits))) {
for (auto vol : volV) {
vol.first.setLimitSet(theDetector, x_det.limitsStr());
}
}
//---- meassurement surface vectors
......@@ -1274,7 +1284,9 @@ static Ref_t create_element(Detector& theDetector, xml_h e, SensitiveDetector se
ftd.addExtension< ZDiskPetalsData >( zDiskPetalsData ) ;
//--------------------------------------
if ( x_det.hasAttr(_U(combineHits)) ) {
ftd.setCombineHits(x_det.attr<bool>(_U(combineHits)),sens);
}
return ftd;
}
......
//====================================================================
// lcgeo - LC detector models in DD4hep
//--------------------------------------------------------------------
// F.Gaede, DESY
// $Id$
//====================================================================
#include "DD4hep/DetFactoryHelper.h"
#include "DD4hep/DD4hepUnits.h"
#include "DD4hep/DetFactoryHelper.h"
#include "DD4hep/DetType.h"
#include "XMLHandlerDB.h"
#include "XML/Utilities.h"
#include "DDRec/Surface.h"
#include "DDRec/DetectorData.h"
#include "FTD_Simple_Staggered.h"
// #define DEBUG_VALUES
// #define DEBUG_PETAL 4
//#include "DDRec/DDGear.h"
//#define MOKKA_GEAR
#include <cmath>
#include <string>
#include <map>
#include <assert.h>
using namespace std;
using namespace dd4hep;
using namespace rec;
namespace cepc{
/// helper to wrap access to global constants
struct EnvDetector{
Detector* _theDetector;
EnvDetector() : _theDetector(0) {} ;
EnvDetector(Detector& theDetector) : _theDetector( &theDetector) {} ;
inline double GetParameterAsDouble(const std::string& name) const { return _theDetector->constant<double>( name ) ; }
} ;
/// Helper vector for creation of DetElements holding Volumes and their placement
typedef std::vector< std::pair< Volume, PlacedVolume > > VolVec ;
///Helper vector for DetElements (e.g. petals in disk)
typedef std::vector< DetElement > DEVec ;
/// Storing all the gear parameters
std::map<int,std::vector<double> > _ftdparameters;
/// Global environment variables
glEnviron _glEnv;
/// common DB Parameters
dbInfoCommon _dbParCommon;
/// disk DB Parameters
dbInfoDisk _dbParDisk;
/// reco DB Parameters
dbExtended_reconstruction_parameters _dbParExReco;
double _inner_radius = 0.0;
double _outer_radius = 0.0;
double _z_position = 0.0;
double _beamTubeRadius = 0.0;
double _zEnd = 0.0;
Material _SiMat ;
Material _KaptonMat ;
Material _CuMat ;
Material _AirMat ;
Material _CarbonFiberMat ;
// function prototpyes
double Getdy(const double & innerRadius );
double Getdx( const double & innerRadius );
//void DoAndPlaceDisk( Detector& theDetector,DetElement det,SensitiveDetector sens, std::map<std::string,double> valuesDict, Volume mother ) ;
void petalSupport( Detector& theDetector,DetElement det, std::map<std::string,double> valuesDict, Volume FTDPetalAirLogical ) ;
VolVec petalSensor( Detector& theDetector, DetElement ftd, SensitiveDetector sens, std::map<std::string,double> valuesDict, Volume FTDPetalAirLogical ) ;
Trap SemiPetalSolid(const double& petal_cp_support_dy, const std::string& whereItgoes, const bool isSilicon ) ;
//debug print function
void printVolume( Volume v ){
std::cout << " ++++ create Volume " << v.name() << std::endl ;
}
//=========================== PARAMETERS SETTERS FUNCTIONS ====================================/
//*********************************************************************************************
// Set Environment variables (dependent of other subdetectors)
void SetEnvironPar(const EnvDetector& env)
{
_glEnv.TPC_Ecal_Hcal_barrel_halfZ = env.GetParameterAsDouble("TPC_Ecal_Hcal_barrel_halfZ") ;
_glEnv.Ecal_endcap_zmin = env.GetParameterAsDouble("Ecal_endcap_zmin") ;
_glEnv.TPC_inner_radius = env.GetParameterAsDouble("TPC_inner_radius") ;
_glEnv.SIT1_Half_Length_Z = env.GetParameterAsDouble("SIT1_Half_Length_Z") ;
_glEnv.SIT2_Half_Length_Z = env.GetParameterAsDouble("SIT2_Half_Length_Z") ;
_glEnv.SIT1_Radius = env.GetParameterAsDouble("SIT1_Radius") ;
_glEnv.SIT2_Radius = env.GetParameterAsDouble("SIT2_Radius") ;
_glEnv.VXD_layer3_maxZ = env.GetParameterAsDouble("VXD_length_r3") ;
_glEnv.zEnd_IPOuterTube = (env.GetParameterAsDouble("TUBE_IPOuterTube_end_z")) ; // ---> A lo mejor no hacen falta
_glEnv.rEnd_IPOuterTube = (env.GetParameterAsDouble("TUBE_IPOuterTube_end_radius")) ;
_glEnv.zEnd_IPOuterBulge = (env.GetParameterAsDouble("TUBE_IPOuterBulge_end_z")) ;
_glEnv.rEnd_IPOuterBulge = (env.GetParameterAsDouble("TUBE_IPOuterBulge_end_radius")) ;
_glEnv.beamTubeTangent = ( _glEnv.rEnd_IPOuterBulge - _glEnv.rEnd_IPOuterTube ) / (_glEnv.zEnd_IPOuterBulge - _glEnv.zEnd_IPOuterTube);
}
//*********************************************************************************************
// Set variables common to all disk, dumping 'common_parameters' table from 'ftd08' database
void SetdbParCommon(xml_comp_t x_det)
{
// Getting common_parameters table
//db->exec("select * from common_parameters;");
{
XMLHandlerDB db( x_det.child( _Unicode( common_parameters ) ) );
// db->getTuple();
_dbParCommon.beamTubeClearance = db->fetchDouble("beamtube_clearance") ;
_dbParCommon.outer_cylinder_total_thickness = db->fetchDouble("outer_cylinder_total_thickness") ;
_dbParCommon.inner_cylinder_total_thickness = _dbParCommon.outer_cylinder_total_thickness;
_dbParCommon.cable_shield_thickness = db->fetchDouble("cable_shield_thickness") ;
_dbParCommon.cables_thickness = db->fetchDouble("cables_thickness") ;
// check that there is enough space for the cables and support
if( _dbParCommon.beamTubeClearance < (_dbParCommon.cables_thickness + (2.0*_dbParCommon.cable_shield_thickness) + 0.5 *mm) )
{
cout << "FTD_Simple_Staggered:Stop: Not enough space for inner support structure and cables: increase beamTubeClearance" << endl;
exit(1);
}
_dbParCommon.ftd1_vtx3_distance_z = db->fetchDouble("ftd1_vtx3_distance_z") ;
_dbParCommon.ftd7_ecal_distance_z = db->fetchDouble("ftd7_ecal_distance_z") ;
_dbParCommon.ftd1_sit1_radial_diff = db->fetchDouble("ftd1_sit1_radial_diff") ;
_dbParCommon.ftd2_sit1_radial_diff = db->fetchDouble("ftd2_sit1_radial_diff") ;
_dbParCommon.ftd3_sit2_radial_diff = db->fetchDouble("ftd3_sit2_radial_diff") ;
_dbParCommon.ftd4to7_tpc_radial_gap = db->fetchDouble("ftd4to7_tpc_radial_gap") ;
// Petal Central Part Support: X-Y dimensions, thickness and angles. Same constant values
// for all the micro-strips disks
_dbParCommon.petal_half_angle_support = db->fetchDouble("petal_half_angle_support") ;
_dbParCommon.petal_y_ratio = db->fetchDouble("petal_y_ratio") ;
//fg: add additional parameter:
_dbParCommon.support_spaceframe_width= db->fetchDouble("support_spaceframe_width") ;
}
// db->exec("select * from extended_reconstruction_parameters;");
// db->getTuple();
{
XMLHandlerDB db( x_det.child( _Unicode( extended_reconstruction_parameters ) ) );
_dbParExReco.strip_width = db->fetchDouble("strip_width") ;
_dbParExReco.strip_length = db->fetchDouble("strip_length") ;
_dbParExReco.strip_pitch = db->fetchDouble("strip_pitch") ;
_dbParExReco.strip_angle = db->fetchDouble("strip_angle") ;
}
#ifdef DEBUG_VALUES
cout << "FTD_Simple_Staggered:SetdbParCommon:\n"
<< "beamTubeClearance = " << _dbParCommon.beamTubeClearance << " \n"
<< "outer_cylinder_total_thickness = " << _dbParCommon.outer_cylinder_total_thickness << " \n"
<< "inner_cylinder_total_thickness = " << _dbParCommon.inner_cylinder_total_thickness << " \n"
<< "cable_shield_thickness = " << _dbParCommon.cable_shield_thickness << " \n"
<< "cables_thickness = " << _dbParCommon.cables_thickness << " \n"
<< "ftd1_vtx3_distance_z = " << _dbParCommon.ftd1_vtx3_distance_z << " \n"
<< "ftd7_ecal_distance_z = " << _dbParCommon.ftd7_ecal_distance_z << " \n"
<< "ftd1_sit1_radial_diff = " << _dbParCommon.ftd1_sit1_radial_diff << " \n"
<< "ftd2_sit1_radial_diff = " << _dbParCommon.ftd2_sit1_radial_diff << " \n"
<< "ftd3_sit2_radial_diff = " << _dbParCommon.ftd3_sit2_radial_diff << " \n"
<< "ftd4to7_tpc_radial_gap = " << _dbParCommon.ftd4to7_tpc_radial_gap << " \n"
<< "petal_half_angle_support = " << _dbParCommon.petal_half_angle_support << " \n"
<< "petal_y_ratio = " << _dbParCommon.petal_y_ratio << " \n"
<< "strip_width = " << _dbParExReco.strip_width << " \n"
<< "strip_length = " << _dbParExReco.strip_length << " \n"
<< "strip_pitch = " << _dbParExReco.strip_pitch << " \n"
<< "strip_angle = " << _dbParExReco.strip_angle << " \n"
<< endl;
#endif
}
//*********************************************************************************************
// Set variables disk number specific, dumping 'disk' table from 'ftd08' database
void SetParDisk( XMLHandlerDB db)
{
_dbParDisk.disk_number = db->fetchInt( "disk_number" );
_dbParDisk.disks_Si_thickness = db->fetchDouble("disk_si_thickness") ;
_dbParDisk.petal_cp_support_thickness = db->fetchDouble("petal_cp_support_thickness") ;
_dbParDisk.petal_cp_support_dxMax = db->fetchDouble("petal_cp_support_dxMax") ;
_dbParDisk.petal_support_zoffset = db->fetchDouble("petal_support_zoffset") ; //NEW
_dbParDisk.sensor_is_pixel = db->fetchInt("sensor_is_pixel"); //NEW
_dbParDisk.double_sided = db->fetchInt("double_sided"); //NEW
#ifdef DEBUG_VALUES
cout << "FTD_Simple_Staggered:SetParDisk:\n"
<< "disk_number = " << _dbParDisk.disk_number << " \n"
<< "sensor_is_pixel = " << _dbParDisk.sensor_is_pixel << " \n"
<< "double_sided = " << _dbParDisk.double_sided << " \n"
<< "petal_support_zoffset = " << _dbParDisk.petal_support_zoffset << " \n"
<< "disks_Si_thickness = " << _dbParDisk.disks_Si_thickness << " \n"
<< "petal_cp_support_thickness = " << _dbParDisk.petal_cp_support_thickness << " \n"
<< "petal_cp_support_dxMax = " << _dbParDisk.petal_cp_support_dxMax << " \n"
<< "petal_support_zoffset = " << _dbParDisk.petal_support_zoffset << " \n"
<< endl;
#endif
}
//=END======================= PARAMETERS SETTERS FUNCTIONS ================================END=/
}
using namespace cepc;
/** Construction of FTD detector, ported from Mokka driver FTD_simple_Staggered.cc
*
* FTD_Simple_Staggered.cc
*
* Simplified Implementation of a self scaling 7 disk FTD
* Based on SFtd06 but using simple trapezoid sensitive and support structures
* All disks have the same structure
* Sensitive material Silicon
* Support material Carbon Fiber, Foam
*
* All disks' envelop:
* Dimensions and coordinates are specified for the sensitive layer, support disks are built on to these
* _inner_radius = ( _beamTubeRadius + beamTubeClearance)
*
* First Disk:
* z defined by distance from end of VTX layer 3
* outer r defined by radial difference to SIT layer 1
*
* Second Disk:
* z defined relative to TPC half-length: to ensure positioning with SIT set these numbers to the same value in DB
* outer r defined by radial difference to SIT layer 1
*
* Third Disk:
* z defined relative to TPC half-length: to ensure positioning with SIT set these numbers to the same value in DB
* outer r defined by radial difference to SIT layer 1
*
* Fourth, Fifth and Sixth Disk:
* z defined relative to TPC half-length
* outer r defined by gap between TPC inner radius and FTD disks
*
* Last Disk:
* z defined by distance from front of ECal endcap
* outer r defined by gap between TPC inner radius and FTD disks
*
* Parameters Set in Model Parameter DB Table:
* TPC_Ecal_Hcal_barrel_halfZ
* _glEnv.Ecal_endcap_zmin
* _glEnv.TPC_inner_radius
* VXD_length_r3
*
* Parameters shared with other drivers:
* SSit03:_glEnv.SIT1_Half_Length_Z
* SSit03:_glEnv.SIT2_Half_Length_Z
* SSit03:_glEnv.SIT1_Radius
* SSit03:_glEnv.SIT2_Radius
* TubeX01:TUBE_IPOuterTube_end_z
* TubeX01:TUBE_IPOuterTube_end_radius
* TubeX01:TUBE_IPOuterBulge_end_z
* TubeX01:TUBE_IPOuterBulge_end_radius
*
*
* History:
* May 2014: FG: original port from Mokka
* Oct 2014 FG: - added class ZDiskPetalsData as interface to reconstruction (initially to
* instantiate gear::FTDParameters )
* - changed rotations and translations to a more natural one (positive sense of rotation, etc.)
* - 'replaced' usage of reflection in original code with individual placements
* in distinct disks on either side of the origin (see comments in code for placements
of
*
* Mokka History:
* - first implementation P. Mora de Freitas (sept 02)
* - fixed geometry overlap -- Adrian Vogel, 2005-12-05
* - implemented new GEAR interface -- K. Harder, T. Pinto Jayawardena 2007-07-31
* - SFtd03: Modified version of SFtd02: Rewritten as a self scaling driver which does not
* make use of a seperate super driver. Steve Aplin (May 2008)
* October 15th 2008, Steve Aplin using description from SiLC Collaboration
* - Fixes a bug in SFtd04.cc which meant that the copper cables on thin
* inside of the cylinder were far to thick (SJA 28/05/09)
* September 7th 2010, Jordi Duarte using mechanical design from IFCA group
* - SFtd06: Modified version of SFtd05 implementing realistic details of the disks
* 4,5,6,7 structure. -- J. Duarte Campderros (Sept. 2010)
* Added realistic description to disks 1,2,3. Changed disk 3 to micro-strips
* technology --- J. Duarte Campderros (Oct. 2010)
* Included the alternative z-offset between petals --|
* Included the use of the GEAR class FTDParameter --| J. Duarte Campderros (July, 2011)
* Modified the placement of the Volumes using the
* G4ReflectionFactory Place methods. Now the volumes in Z
* negatives are specular images from the positives -- J. Duarte Campderros (Sept, 2011)
* - FTD_Simple_Staggered: created to enable development of tracking code while SFtd06 is finalised.
* S.J. Aplin (Nov 2011)
*
* @author: F.Gaede, DESY, May 2014
* @version $Id$
*/
static Ref_t create_element(Detector& theDetector, xml_h e, SensitiveDetector sens) {
// std::cout << " FTD04 - Detector.BuildType = " << theDetector.buildType() << std::endl ;
//------------------------------------------
// See comments starting with '//**' for
// hints on porting issues
//------------------------------------------
xml_det_t x_det = e;
string name = x_det.nameStr();
DetElement ftd( name, x_det.id() ) ;
// --- create an envelope volume and position it into the world ---------------------
Volume envelope = dd4hep::xml::createPlacedEnvelope( theDetector, e , ftd ) ;
dd4hep::xml::setDetectorTypeFlag( e, ftd ) ;
if( theDetector.buildType() == BUILD_ENVELOPE ) return ftd ;
//-----------------------------------------------------------------------------------
PlacedVolume pv;
if (x_det.hasChild(_U(sensitive))) {
xml_dim_t sd_typ = x_det.child(_U(sensitive));
sens.setType(sd_typ.typeStr());
}
else {
sens.setType("tracker");
}
// --- create assembly and DetElement for support and service volumes
Assembly supp_assembly( name + "_support_assembly" ) ;
pv = envelope.placeVolume( supp_assembly ) ;
DetElement suppDE( ftd , name+"_support" , x_det.id() ) ;
suppDE.setPlacement( pv ) ;
//--------------------------------
dd4hep::rec::ZDiskPetalsData* zDiskPetalsData = new ZDiskPetalsData ;
//######################################################################################################################################################################
// code ported from FTD_Simple_Staggered::construct() :
//##################################
double phi1 = 0 ;
double phi2 = 2*M_PI;
//fg: vis attributes defined in xml now
// // Globals and cosmetics definitions
// _VisAttSensitive = new G4VisAttributes(G4Colour(1.,1.,.45));
// //G4VisAttributes *
// _VisAttSupport = new G4VisAttributes(G4Colour(1,.5,.5));
// _VisAttHolePetal = new G4VisAttributes(G4Color(1,.5,.5,1.0));
// G4VisAttributes *VisAttAirDisk = new G4VisAttributes(G4Colour(.5,.3,.8,0.98));
// VisAttAirDisk->SetVisibility(0);
// G4VisAttributes *VisAttAirPetal = new G4VisAttributes(G4Colour(.5,.3,.8,0.98));
// VisAttAirPetal->SetVisibility(0);
// G4VisAttributes *VisAttCyl = new G4VisAttributes(G4Colour(0.45,.2,0.9,.98));
// G4VisAttributes *VisAttCables = new G4VisAttributes(G4Colour(0.,0.9,0.));
// VisAttCables->SetForceWireframe(false);
// PhysicalVolumesPair Phys;
// Get and set the Globals from the surrounding environment TPC ECAL SIT VTX and Beam-Pipe
SetEnvironPar( EnvDetector( theDetector ) );
// Get and set the variables global to the FTD cables_thickness, ftd1_vtx3_distance_z, etc
// Database * db = new Database(env.GetDBName());
SetdbParCommon( x_det );
// Materials definitions
_SiMat = theDetector.material("G4_Si") ; // silicon_2.33gccm");
_KaptonMat = theDetector.material("G4_KAPTON"); //kapton");
_CuMat = theDetector.material("G4_Cu"); //copper");
_AirMat = theDetector.material("G4_AIR" ); //air");
_CarbonFiberMat = theDetector.material("CarbonFiber");
//fg: replace with standard from materials file
// -- PROVISIONAL -- Carbon Fiber definition from database ??
// double density;
// std::string matname, symbol;
// int nel;
// double fractionmass, volumefraction;
// volumefraction = 0.5;
// density = (1.3 + volumefraction / 3 ) * g/cm3;
// fractionmass = 1 - 1.3 * (1 - volumefraction) / (density / (g/cm3));
// _CarbonFiberMat = new Material(matname = "CarbonFiber", density, nel=2);
// _CarbonFiberMat->AddElement(CGAGeometryManager::GetElement("C"), fractionmass);
// _CarbonFiberMat->AddMaterial(CGAGeometryManager::GetMaterial("epoxy"),1.0-fractionmass);
// cout << "CarbonFiber->GetRadlen() = " << _CarbonFiberMat->GetRadlen() / cm << " cm" << endl;
// <-------------------------------------------------------------------------------------------
cout << "FTD_Simple_Staggered:"
<< "\t inner support thickness = " << _dbParCommon.inner_cylinder_total_thickness
<< "\t cables thickness = " << _dbParCommon.cables_thickness
<< "\t 2 x cable shield thickness = " << 2 * _dbParCommon.cable_shield_thickness
<< "\t beamTubeClearance = " << _dbParCommon.beamTubeClearance
<< endl;
// Now we can start to build the disks -------------------------------------------
const double theta = _dbParCommon.petal_half_angle_support;
// Disk parameters
_dbParDisk.ZStartOuterCylinder=0;
_dbParDisk.ZStopOuterCylinder=0;
double OuterCylinderInnerRadius=0;
_dbParDisk.ZStartInnerCylinder=0;
_dbParDisk.ZStopInnerCylinder=0;
double InnerCylinderOuterRadius1=0;
double InnerCylinderOuterRadius2=0;
// db->exec("select * from disks;");
// db->getTuple();
// //... assembling detector
// do {
for(xml_coll_t c( x_det ,_U(disk)); c; ++c) {
xml_comp_t x_disk( c );
XMLHandlerDB db( x_disk ) ;
//...
int disk_number(-1);
// double _inner_radius = 0.0;
// double _outer_radius = 0.0;
// double _z_position = 0.0;
// double _beamTubeRadius = 0.0;
// double _zEnd = 0.0;
// Get and set the parameters disk specific
SetParDisk( db );
disk_number = _dbParDisk.disk_number;
#ifdef ONE_DISK
if (disk_number != ONE_DISK )
{
continue;
}
#endif
switch (disk_number)
{
case 1:
// z defined by distance from end of VTX layer 3
_z_position = ( _glEnv.VXD_layer3_maxZ + _dbParCommon.ftd1_vtx3_distance_z );
// _z_position = disk_number * 100.0 * mm;
// outer r defined by radial difference to SIT layer 1
_outer_radius = ( _glEnv.SIT1_Radius + _dbParCommon.ftd1_sit1_radial_diff );
// beam tube radius at backside of disk
_zEnd = _z_position + _dbParDisk.petal_support_zoffset + 0.5 * _dbParDisk.petal_cp_support_thickness + ( _dbParDisk.double_sided * _dbParDisk.disks_Si_thickness ) ;
// check which part of the beam tube this disk lies above
_beamTubeRadius = (_zEnd < _glEnv.zEnd_IPOuterTube ) ? _glEnv.rEnd_IPOuterTube : _glEnv.rEnd_IPOuterTube + ( (_zEnd - _glEnv.zEnd_IPOuterTube ) * _glEnv.beamTubeTangent );
_inner_radius = ( _beamTubeRadius + _dbParCommon.beamTubeClearance);
// check that there is no overlap with SIT1
if( _z_position <= _glEnv.SIT1_Half_Length_Z && _outer_radius>=_glEnv.SIT1_Radius)
{
cout << "FTD_Simple_Staggered:Stop: Overlap between FTD1 and SIT1" << endl;
cout << "FTD_Simple_Staggered:FTD1 Radius = " << _outer_radius << "SIT1 Radius = " << _glEnv.SIT1_Radius << endl;
exit(1);
}
if( db->fetchDouble("z_position_ReltoTPCLength") != 0.0)
{
cout << "FTD_Simple_Staggered:Stop: The z position of FTD1 is not relative. The relative value will not be used. It should be set to 0.0 in the DB." << endl;
cout << "FTD_Simple_Staggered:Stop: The z position of FTD1 is set by the distance between the centre of the sensitive layer and the max z of VTX layer 3." << endl;
exit(1);
}
break;
case 2:
// z defined relative to TPC half-length: to ensure positioning with SIT set these numbers to the same value in DB
_z_position = (_glEnv.TPC_Ecal_Hcal_barrel_halfZ * db->fetchDouble("z_position_ReltoTPCLength")) ;
// _z_position = disk_number * 100.0 * mm;
// outer r defined by radial difference to SIT layer 1
_outer_radius = _glEnv.SIT1_Radius + _dbParCommon.ftd2_sit1_radial_diff;
// beam tube radius at backside of disk
_zEnd = _z_position + _dbParDisk.petal_support_zoffset + 0.5 * _dbParDisk.petal_cp_support_thickness + ( _dbParDisk.double_sided * _dbParDisk.disks_Si_thickness ) ;
// check which part of the beam tube this disk lies above
_beamTubeRadius = (_zEnd < _glEnv.zEnd_IPOuterTube ) ? _glEnv.rEnd_IPOuterTube : _glEnv.rEnd_IPOuterTube + ( (_zEnd - _glEnv.zEnd_IPOuterTube ) * _glEnv.beamTubeTangent );
_inner_radius = ( _beamTubeRadius + _dbParCommon.beamTubeClearance) ;
//... keep information for inner support cylinder with 0.5mm saftey clearance from inner radius of disks
_dbParDisk.ZStartInnerCylinder = _glEnv.zEnd_IPOuterTube;
InnerCylinderOuterRadius1 = _inner_radius - ( ( _zEnd - _glEnv.zEnd_IPOuterTube ) * _glEnv.beamTubeTangent ) - 0.5 * mm;
// check that there is no overlap with SIT1
if( _z_position <= _glEnv.SIT1_Half_Length_Z && _outer_radius>=_glEnv.SIT1_Radius)
{
cout << "FTD_Simple_Staggered:Stop:Overlap between FTD2 and SIT1" << endl;
cout << "FTD_Simple_Staggered:FTD2 Radius = " << _outer_radius << "SIT1 Radius = " << _glEnv.SIT1_Radius << endl;
exit(1);
}
break;
case 3:
// z defined relative to TPC half-length: to ensure positioning with SIT set these numbers to the same value in DB
_z_position = (_glEnv.TPC_Ecal_Hcal_barrel_halfZ * db->fetchDouble("z_position_ReltoTPCLength")) ;
// _z_position = disk_number * 100.0 * mm;
// outer r defined by radial difference to SIT layer 2
_outer_radius = _glEnv.SIT2_Radius + _dbParCommon.ftd3_sit2_radial_diff;
// beam tube radius at backside of disk
_zEnd = _z_position + _dbParDisk.petal_support_zoffset + 0.5 * _dbParDisk.petal_cp_support_thickness + ( _dbParDisk.double_sided * _dbParDisk.disks_Si_thickness ) ;
// check which part of the beam tube this disk lies above
_beamTubeRadius = (_zEnd < _glEnv.zEnd_IPOuterTube ) ? _glEnv.rEnd_IPOuterTube : _glEnv.rEnd_IPOuterTube + ( (_zEnd - _glEnv.zEnd_IPOuterTube ) * _glEnv.beamTubeTangent );
_inner_radius = _beamTubeRadius + _dbParCommon.beamTubeClearance ;
// check that there is no overlap with SIT1
if( _z_position <= _glEnv.SIT2_Half_Length_Z && _outer_radius>=_glEnv.SIT2_Radius)
{
cout << "FTD_Simple_Staggered:Stop:Overlap between FTD3 and SIT2" << endl;
cout << "FTD_Simple_Staggered:FTD3 Radius = " << _outer_radius << "SIT2 Radius = " << _glEnv.SIT2_Radius << endl;
exit(1);
}
break;
case 4:
case 5:
case 6:
// z defined relative to TPC half-length
_z_position = (_glEnv.TPC_Ecal_Hcal_barrel_halfZ * db->fetchDouble("z_position_ReltoTPCLength")) ;
// _z_position = disk_number * 100.0 * mm;
// outer r defined by gap between TPC inner radius and FTD disks
_outer_radius = _glEnv.TPC_inner_radius - _dbParCommon.ftd4to7_tpc_radial_gap;
// beam tube radius at backside of disk
_zEnd = _z_position + _dbParDisk.petal_support_zoffset + 0.5 * _dbParDisk.petal_cp_support_thickness + ( _dbParDisk.double_sided * _dbParDisk.disks_Si_thickness ) ;
// check which part of the beam tube this disk lies above
_beamTubeRadius = (_zEnd < _glEnv.zEnd_IPOuterTube ) ? _glEnv.rEnd_IPOuterTube : _glEnv.rEnd_IPOuterTube + ( (_zEnd - _glEnv.zEnd_IPOuterTube ) * _glEnv.beamTubeTangent );
_inner_radius = _beamTubeRadius + _dbParCommon.beamTubeClearance ;
// keep the information for outer cylinder
if(disk_number==4)
{
_dbParDisk.ZStartOuterCylinder = _z_position;
}
_dbParDisk.ZStopOuterCylinder = _zEnd;
_dbParDisk.ZStopInnerCylinder = _zEnd;
break;
case 7:
// z defined by distance from front of ECal endcap
_z_position = _glEnv.Ecal_endcap_zmin - _dbParCommon.ftd7_ecal_distance_z;
// _z_position = disk_number * 100.0 * mm;
// outer r defined by gap between TPC inner radius and FTD disks
_outer_radius = _glEnv.TPC_inner_radius - _dbParCommon.ftd4to7_tpc_radial_gap;
// beam tube radius at backside of disk
_zEnd = _z_position + _dbParDisk.petal_support_zoffset + 0.5 * _dbParDisk.petal_cp_support_thickness + ( _dbParDisk.double_sided * _dbParDisk.disks_Si_thickness ) ;
// check which part of the beam tube this disk lies above
_beamTubeRadius = (_zEnd < _glEnv.zEnd_IPOuterTube ) ? _glEnv.rEnd_IPOuterTube : _glEnv.rEnd_IPOuterTube + ( (_zEnd - _glEnv.zEnd_IPOuterTube ) * _glEnv.beamTubeTangent );
_inner_radius = _beamTubeRadius + _dbParCommon.beamTubeClearance ;
// End of Support Structure: 0.5mm clearance from disks
_dbParDisk.ZStopOuterCylinder = _zEnd;
_dbParDisk.ZStopInnerCylinder = _zEnd;
OuterCylinderInnerRadius = _outer_radius + 0.5 * mm;
InnerCylinderOuterRadius2 = _inner_radius - 0.5 * mm;
if( db->fetchDouble("z_position_ReltoTPCLength") != 0.0)
{
cout << "FTD_Simple_Staggered:Stop: The z position of FTD7 is not relative. The relative value will not be used. It should be set to 0.0 in the DB." << endl;
cout << "FTD_Simple_Staggered:Stop: The z position of FTD7 is set by the distance between the centre of the sensitive layer and the min z of the ECal Endcap." << endl;
exit(1);
}
break;
default:
cout << "FTD_Simple_Staggered: Error disk number must be between 1-7: disk number = " << disk_number << endl;
exit(1);
}
cout << "FTD_Simple_Staggered: Disk:" << disk_number
<< "\t z = " << _z_position
<< "\t inner rad = " << _inner_radius
<< "\t outer rad = " << _outer_radius
<< "\t beamtube rad = " << _beamTubeRadius
<< "\t free space = " << (_inner_radius - 0.5 * mm - _dbParCommon.inner_cylinder_total_thickness - (2*_dbParCommon.cable_shield_thickness) - _dbParCommon.cables_thickness) - _beamTubeRadius
<< endl;
/**************************************************************************************
** Begin construction of disks with appropiate parameters **
**************************************************************************************/
//================================== AIR DISK =======================================//
// The air-disk is the container and mother volume of the petals. There will be
// 7x2 air disks copies placed in the world volume.
//
// Check the comments at the beginning of this file for the description of
// each # disk parameter.
//
// Input parameters:
// _inner_radius: inner radius of the whole structure
// _outer_radius: outer radius of the whole structure
// max_half_thickness_disk:
// the maximum thickness of the disk = 2.0 * ( sensitive thickness + support thickness + Zoffset )
// Zoffset=the displacement of the disks in z-direction
//
// // The thickness of the air petal (containing the support and sensors)
// double petalairthickness_half = 0.5 * ( _dbParDisk.petal_cp_support_thickness +
// _dbParDisk.disks_Si_thickness )
// need enough space for double sided
double petalairthickness_half = 0.5 * ( _dbParDisk.petal_cp_support_thickness
+ 2.0*_dbParDisk.disks_Si_thickness ) ;
double max_half_thickness_disk = _dbParDisk.petal_support_zoffset + petalairthickness_half ;
// Tubs *FTDDiskSolid = new Tubs("FTDAirDiskSolid",
// _inner_radius,
// _outer_radius,
// max_half_thickness_disk,
// phi1,
// phi2
// );
Tube FTDDiskSolid( _inner_radius, _outer_radius, max_half_thickness_disk, phi1, phi2 );
// LogicalVolume *FTDDiskLogical = new LogicalVolume(FTDDiskSolid,
// _AirMat,
// "FTDAirDiskLogical",
// 0,
// 0,
// 0);
//fg: Volume FTDDiskLogical( _toString( _dbParDisk.disk_number, "FTDAirDiskLogical_%d" ), FTDDiskSolid, _AirMat ) ;
//fg: replace the logical volume for the disks with two individual ones for the pos. and neg. z axis respectively
//fg: this way we do not need a reflection and can position the petals with different transforms on either side...
Volume FTDDiskLogicalPZ( _toString( _dbParDisk.disk_number, "FTDAirDiskLogicalPZ_%d" ), FTDDiskSolid, _AirMat ) ;
Volume FTDDiskLogicalNZ( _toString( _dbParDisk.disk_number, "FTDAirDiskLogicalNZ_%d" ), FTDDiskSolid, _AirMat ) ;
// FTDDiskLogical->SetVisAttributes(VisAttAirDisk);
// ftd.setVisAttributes(theDetector, "SeeThrough", FTDDiskLogical ) ;
ftd.setVisAttributes(theDetector, "SeeThrough", FTDDiskLogicalPZ ) ;
ftd.setVisAttributes(theDetector, "SeeThrough", FTDDiskLogicalNZ ) ;
// RotationMatrix *rotDiskPositive = new RotationMatrix();
// // Sensors facing the IP)
// rotDiskPositive->rotateY(pi);
// // Re-allocating the local disk frame to the global frame
// rotDiskPositive->rotateZ(-pi/2.0);
// Transform3D transPositive( *rotDiskPositive, Position( 0.,0.,_z_position) );
// // Place the positive copy in the world
// Phys = ReflectionFactory::Instance()->Place( transPositive,
// "FTDAirDisk",
// FTDDiskLogical,
// worldLog,
// false,
// disk_number);
// registerPV( Phys );
///fg RotationZYX rotDiskPositive( -pi/2.0, pi , 0. ) ;
//fg use unrotated air disks...
RotationZYX rotDiskPositive(0,0,0) ;
Transform3D transPositive( rotDiskPositive, Position( 0.,0.,_z_position) );
pv = envelope.placeVolume( FTDDiskLogicalPZ, transPositive ) ;
DetElement diskDEposZ( ftd , _toString( _dbParDisk.disk_number, "FTDDisk_%d_posZ" ) , x_det.id() );
diskDEposZ.setPlacement( pv ) ;
pv.addPhysVolID("layer", disk_number - 1 ).addPhysVolID("side", 1 ) ;
#ifdef DEBUG_VALUES
cout << "===================================================================== " << "\n" <<
"FTDAirDisk:\n" <<
" Inner Radius= " << _inner_radius << "\n" <<
" Outer Radius= " << _outer_radius << "\n" <<
" thickness = " << max_half_thickness_disk*2.0 << "\n" <<
" placed at \n" <<
" x = " << transPositive.Translation().Vect().X() << "\n" <<
" y = " << transPositive.Translation().Vect().Y() << "\n" <<
" z = " << transPositive.Translation().Vect().Z() << "\n" <<
endl;
#endif
// // Place negative copy
#ifndef DEBUG_POSITIVE
// RotationMatrix *rotDiskNegative = new RotationMatrix();
// rotDiskNegative->rotateZ(-pi/2.0);
// Transform3D transNegative( *rotDiskNegative, Position( 0.,0.,-_z_position ) );
// //Specular image
// transNegative = transNegative*ReflectX3D();
// Phys = ReflectionFactory::Instance()->Place( transNegative,
// "FTDAirDisk",
// FTDDiskLogical,
// worldLog,
// false,
// -disk_number);
// registerPV( Phys );
//fg RotationZYX rotDiskNegative( -pi/2.0, 0 , 0. ) ;
//fg use unrotated air disks...
RotationZYX rotDiskNegative(0,0,0) ;
Transform3D transNegative( rotDiskNegative, Position( 0.,0., -_z_position) );
pv = envelope.placeVolume( FTDDiskLogicalNZ, transNegative ) ;
DetElement diskDEnegZ( ftd , _toString( _dbParDisk.disk_number, "FTDDisk_%d_negZ" ) , x_det.id() );
diskDEnegZ.setPlacement( pv ) ;
pv.addPhysVolID("layer", disk_number -1 ).addPhysVolID("side", -1 ) ;
#ifdef DEBUG_VALUES
cout << "===================================================================== " << "\n" <<
"FTDAirDisk:\n" <<
" Inner Radius= " << _inner_radius << "\n" <<
" Outer Radius= " << _outer_radius << "\n" <<
" thickness = " << max_half_thickness_disk*2.0 << "\n" <<
" placed at \n" <<
" x = " << transNegative.Translation().Vect().X() << "\n" <<
" y = " << transNegative.Translation().Vect().Y() << "\n" <<
" z = " << transNegative.Translation().Vect().Z() << "\n" <<
endl;
#endif
#endif
//=END=============================== AIR DISK =================================END=/
//=================================== AIR PETAL =====================================/
// Air container for the petal: the mother of the real support petal and the silicon
// sensors. This air petal will be placed inside the Air Disk,
// generating N rotated copies along the z-axis.
// Input parameters: dxMax _
// -------- | |
// \ / | | |
// XY-Plane \ / | dy YZ-Plane | |
// \__/ | |_|
// dxMin dz
//
// dxMax: given by the database
// dxMin: depends of the _inner_radius of each disk
// dy: heigth, depends of each disk
// dz: thickness of the supports + thickness of Si
// theta: given by the db, semi-angle which defines the trapezoid
// Dimensions for the disk
const double petal_cp_supp_half_dxMin = Getdx( _inner_radius )/2.0;
const double petal_cp_support_dy = Getdy(_inner_radius);
// ------------------------------------------------------------------------
#ifdef DEBUG_VALUES
std::cout << "*** Petal parameters : petal_cp_supp_half_dxMin=" << petal_cp_supp_half_dxMin
<< " _dbParDisk.petal_cp_support_dxMax/2.0 =" << _dbParDisk.petal_cp_support_dxMax/2.0
<< " petal_cp_support_dy/2.0 =" << petal_cp_support_dy/2.0
<< " petalairthickness_half =" << petalairthickness_half << std::endl ;
#endif
Trap FTDPetalAirSolid( petalairthickness_half, //thickness (calculated in the disk zone)
0.0,
0.0,
petal_cp_support_dy/2.0, // dy
petal_cp_supp_half_dxMin, //dxMin
_dbParDisk.petal_cp_support_dxMax/2.0, //dxMax
0.0,
petal_cp_support_dy/2.0, // dy
petal_cp_supp_half_dxMin, // dxMin
_dbParDisk.petal_cp_support_dxMax/2.0, //dxMax
0.0);
Volume FTDPetalAirLogical( _toString( _dbParDisk.disk_number, "FTDPetalAirLogical_%d" ) , FTDPetalAirSolid, _AirMat ) ;
//printVolume( FTDPetalAirLogical ) ;
ftd.setVisAttributes(theDetector, "SeeThrough" , FTDPetalAirLogical ) ;
// Placing N-copies of the air petal inside the air disk. The copies are built using the z-axis as
// the axis of rotation
const int petal_max_number = (int)(360.0*deg/(2.0*theta)) ;
DEVec petVecposZ(petal_max_number) ;
DEVec petVecnegZ(petal_max_number) ;
double zSignPetal0 = 1. ;
for (int i = 0; i < petal_max_number; i++){
#ifdef DEBUG_PETAL
if(i != DEBUG_PETAL ) {
continue;
}
#endif
// Put the petal in the position inside the disk
double petalCdtheta = i*2.0*theta;
//fg: changed this to positve rotation
//fg: the petals at negative z are numbered in positive sense of rotation
// for the ones at positve z, we have to flip around the petal (rotY(pi))
// and then rotate in the negative direction around the new (inverted) z-axis
// -> this really mimicks the reflection of the petal disk:
// changed sense of rotation and flipped petals !!
RotationZ rotPetalNZ( petalCdtheta - pi/2. );
RotationZYX rotPetalPZ( -( petalCdtheta - pi/2. ) , pi , 0. );
int zsign = pow((double)-1,i);
// Petal i=0 parameters for gear
if( i == 0 ) {
_ftdparameters[gearpar::PHI0].push_back(petalCdtheta );
_ftdparameters[gearpar::PETAL0SIGNOFFSET].push_back(zsign);
zSignPetal0 = zsign ;
}
#ifdef DEBUG_PETAL
_ftdparameters[gearpar::PHI0].push_back(0);
_ftdparameters[gearpar::PETAL0SIGNOFFSET].push_back(1);
#endif
//fg: exchanged sin() and cos() in order to have a normal positve sense
// of rotation around z-axis
double dx = (petal_cp_support_dy/2.0 + _inner_radius)*cos( petalCdtheta );
double dy = (petal_cp_support_dy/2.0 + _inner_radius)*sin( petalCdtheta );
double dz = zsign*( _dbParDisk.petal_support_zoffset) ;
Transform3D transPetalPZ( rotPetalPZ, Position( dx, dy, -dz) );
//fg: at negative z we just exchange the sign of the z-offset
dx = (petal_cp_support_dy/2.0 + _inner_radius)*cos( petalCdtheta );
dy = (petal_cp_support_dy/2.0 + _inner_radius)*sin( petalCdtheta );
Transform3D transPetalNZ( rotPetalNZ, Position( dx, dy, dz) );
// Phys = ReflectionFactory::Instance()->Place(
// transPetal,
// "FTDPetalAir",
// FTDPetalAirLogical,
// FTDDiskLogical,
// false,
// i+1);
// registerPV( Phys );
// pv = FTDDiskLogical.placeVolume( FTDPetalAirLogical, transPetal ) ;
// create DetElements for every petal
std::stringstream sspz ; sspz << "ftd_petal_posZ_" << disk_number << "_" << i ;
std::stringstream ssnz ; ssnz << "ftd_petal_negZ_" << disk_number << "_" << i ;
DetElement petalDEposZ( diskDEposZ, sspz.str() , x_det.id() );
DetElement petalDEnegZ( diskDEnegZ, ssnz.str() , x_det.id() );
pv = FTDDiskLogicalPZ.placeVolume( FTDPetalAirLogical, transPetalPZ ) ;
pv.addPhysVolID("module", i ) ;
petalDEposZ.setPlacement( pv ) ;
pv = FTDDiskLogicalNZ.placeVolume( FTDPetalAirLogical, transPetalNZ ) ;
pv.addPhysVolID("module", i ) ;
petalDEnegZ.setPlacement( pv ) ;
petVecposZ[i] = petalDEposZ ;
petVecnegZ[i] = petalDEnegZ ;
#ifdef DEBUG_VALUES
cout << "===================================================================== " << "\n" <<
"FTDPetalAir: " << i << "\n" <<
" Petal Offset = " << zsign*_dbParDisk.petal_support_zoffset <<
" Inner Radius= " << _inner_radius << "\n" <<
" Outer Radius= " << _outer_radius << "\n" <<
" xMax = " << _dbParDisk.petal_cp_support_dxMax << "\n" <<
" xMin = " << 2.0*petal_cp_supp_half_dxMin << "\n" <<
" dy = " << petal_cp_support_dy << "\n" <<
" thickness = " << petalairthickness_half*2.0 << "\n" <<
" placed at (pos z) \n" <<
" x = " << transPetalPZ.Translation().Vect().X() << "\n" <<
" y = " << transPetalPZ.Translation().Vect().Y() << "\n" <<
" z = " << transPetalPZ.Translation().Vect().Z() << "\n" <<
endl;
#endif
} // end petal loop ...
// -------- reconstruction parameters ----------------
dd4hep::rec::ZDiskPetalsData::LayerLayout thisLayer ;
int isDoubleSided = false;
int nSensors = 1;
if( _dbParDisk.sensor_is_pixel != 1 ) {
isDoubleSided = true;
nSensors = 2;
}
thisLayer.typeFlags[ dd4hep::rec::ZDiskPetalsData::SensorType::DoubleSided ] = isDoubleSided ;
thisLayer.typeFlags[ dd4hep::rec::ZDiskPetalsData::SensorType::Pixel ] = _dbParDisk.sensor_is_pixel ;
thisLayer.petalHalfAngle = _dbParCommon.petal_half_angle_support ;
thisLayer.alphaPetal = 0. ; // petals are othogonal to z-axis
thisLayer.zPosition = _z_position ;
thisLayer.petalNumber = petal_max_number ;
thisLayer.sensorsPerPetal = nSensors ;
thisLayer.phi0 = 0. ;
thisLayer.zOffsetSupport = - zSignPetal0 * fabs( _dbParDisk.petal_support_zoffset ) ; // sign of offset is negative (!?)
thisLayer.distanceSupport = _inner_radius ;
thisLayer.thicknessSupport = _dbParDisk.petal_cp_support_thickness ;
thisLayer.widthInnerSupport = 2. * petal_cp_supp_half_dxMin ;
thisLayer.widthOuterSupport = _dbParDisk.petal_cp_support_dxMax ;
thisLayer.lengthSupport = petal_cp_support_dy ;
thisLayer.zOffsetSensitive = zSignPetal0 * ( fabs( _dbParDisk.petal_support_zoffset ) + 0.5 * (_dbParDisk.disks_Si_thickness+_dbParDisk.petal_cp_support_thickness) ) ;
thisLayer.distanceSensitive = _inner_radius ;
thisLayer.thicknessSensitive = _dbParDisk.disks_Si_thickness ;
thisLayer.widthInnerSensitive = 2. * petal_cp_supp_half_dxMin ;
thisLayer.widthOuterSensitive = _dbParDisk.petal_cp_support_dxMax ;
thisLayer.lengthSensitive = petal_cp_support_dy ;
zDiskPetalsData->layers.push_back( thisLayer ) ;
// -------- end reconstruction parameters ----------------
#ifdef DD4HEP_WITH_GEAR // ------------------------ Gear disk parameters
int sensorType = gear::FTDParameters::PIXEL;
int isDoubleSided = false;
int nSensors = 1;
if( _dbParDisk.sensor_is_pixel != 1 ) {
sensorType = gear::FTDParameters::STRIP;
isDoubleSided = true;
nSensors = 2;
}
#ifdef DEBUG_PETAL
_ftdparameters[gearpar::NPETALS].push_back(1);
#else
_ftdparameters[gearpar::NPETALS].push_back(petal_max_number);
#endif
_ftdparameters[gearpar::SENSORTYPE].push_back(sensorType);
_ftdparameters[gearpar::ISDOUBLESIDED].push_back(isDoubleSided);
_ftdparameters[gearpar::NSENSORS].push_back(nSensors);
_ftdparameters[gearpar::ZPOSITION].push_back(_z_position);
_ftdparameters[gearpar::ZOFFSET].push_back(_dbParDisk.petal_support_zoffset);
_ftdparameters[gearpar::ALPHA].push_back(0.0); // staggered design has no tilt
_ftdparameters[gearpar::HALFANGLEPETAL].push_back(_dbParCommon.petal_half_angle_support);
#endif
//=END=============================== AIR PETAL =================================END=/
//=========================== PETALS & SENSORS ==============================/
/******************************************************
** Support, sensors and electronics are built via **
** DoAnPlaceDisk, see the appropiate functions: **
** **
** +---------------------++--------------------+ **
** | Petal Supports || sensors | **
** +---------------------++--------------------+ **
** | petalSupportPixels || pixelSensors | **
** +---------------------++--------------------+ **
** **
** **
** **
******************************************************/
std::map<std::string,double> valuesDict;
valuesDict["petal_cp_supp_half_dxMin"] = petal_cp_supp_half_dxMin;
valuesDict["petal_cp_support_dy"] = petal_cp_support_dy;
valuesDict["_inner_radius"] = _inner_radius;
// DoAndPlaceDisk( theDetector, ftd, sens, valuesDict, FTDPetalAirLogical );
petalSupport(theDetector, ftd, valuesDict, FTDPetalAirLogical ) ;
VolVec volV = petalSensor( theDetector, ftd, sens, valuesDict, FTDPetalAirLogical );
if (x_det.hasAttr(_U(limits))) {
for (auto vol : volV) {
vol.first.setLimitSet(theDetector, x_det.limitsStr());
}
}
//---- meassurement surface vectors
Vector3D u0( -1. , 0. , 0. ) ;
Vector3D v0( 0. , 1. , 0. ) ;
Vector3D n0( 0. , 0. , -1. ) ;
Vector3D u1( -1. , 0. , 0. ) ;
Vector3D v1( 0. , 1. , 0. ) ;
Vector3D n1( 0. , 0. , -1. ) ;
double supp_thick = _dbParDisk.petal_cp_support_thickness ;
double active_silicon_thickness = _dbParDisk.disks_Si_thickness ;
SurfaceType surfType(SurfaceType::Sensitive) ;
if( ! _dbParDisk.sensor_is_pixel ){ // strip sensor
surfType.setProperty( SurfaceType::Measurement1D , true ) ;
// implement stereo angle
double strip_angle = _dbParExReco.strip_angle ;
// choose the rotation here such that u x v = n
u0.fill( -cos( strip_angle ) , sin( strip_angle ) , 0. ) ;
v0.fill( sin( strip_angle ) , cos( strip_angle ) , 0. ) ;
u1.fill( -cos( strip_angle ) , -sin( strip_angle ) , 0. ) ;
v1.fill( -sin( strip_angle ) , cos( strip_angle ) , 0. ) ;
}
// surf0 is used for the first sensor and includes the complete support material - surf1 is used for the second sensor and has only the silicon
VolPlane surf0( volV[0].first , surfType , active_silicon_thickness/2 , active_silicon_thickness/2 + supp_thick, u0,v0,n0 ) ;
VolPlane surf1( volV[1].first , surfType , active_silicon_thickness/2 , active_silicon_thickness/2 , u1,v1,n1 ) ; ;
//----
// create DetElements for every sensor and assign to the petal DEs
// one or two (for double layers ) for positve and negative z each
for (int i = 0; i < petal_max_number; i++){
#ifdef DEBUG_PETAL
if(i != DEBUG_PETAL ) {
continue;
}
#endif
//create DetElements for sensors - one per sensitive petal
std::stringstream sspz ; sspz << "ftd_sensor_posZ_" << disk_number << "_" << i << "_0" ;
std::stringstream ssnz ; ssnz << "ftd_sensor_negZ_" << disk_number << "_" << i << "_0" ;
DetElement sensorDEposZ( petVecposZ[i], sspz.str() , x_det.id() );
DetElement sensorDEnegZ( petVecnegZ[i], ssnz.str() , x_det.id() );
sensorDEposZ.setPlacement( volV[0].second ) ;
sensorDEnegZ.setPlacement( volV[0].second ) ;
volSurfaceList( sensorDEposZ )->push_back( surf0 ) ;
volSurfaceList( sensorDEnegZ )->push_back( surf0 ) ;
if(_dbParDisk.double_sided == 1 ) { // first two disks are single sided pixel
std::stringstream sspz1 ; sspz1 << "ftd_sensor_posZ_" << disk_number << "_" << i << "_1" ;
std::stringstream ssnz1 ; ssnz1 << "ftd_sensor_negZ_" << disk_number << "_" << i << "_1" ;
DetElement sensorDEposZ_2( petVecposZ[i], sspz1.str() , x_det.id() );
DetElement sensorDEnegZ_2( petVecnegZ[i], ssnz1.str() , x_det.id() );
sensorDEposZ_2.setPlacement( volV[1].second ) ;
sensorDEnegZ_2.setPlacement( volV[1].second ) ;
volSurfaceList( sensorDEposZ_2 )->push_back( surf1 ) ;
volSurfaceList( sensorDEnegZ_2 )->push_back( surf1 ) ;
}
}
//=END======================= PETALS, SENSORS & ELECT. ==========================END=/
} //**************** LOOP over disks *******************************
//================================ OUTER CYLINDER ==================================/
#ifndef DEBUG_PETAL
#ifndef ONE_DISK
assert(_dbParDisk.ZStartOuterCylinder>0);
assert(_dbParDisk.ZStopOuterCylinder>0);
double OuterCylinder_half_z = (_dbParDisk.ZStopOuterCylinder-_dbParDisk.ZStartOuterCylinder)/2.;
assert(OuterCylinder_half_z>0);
double OuterCylinder_position = _dbParDisk.ZStartOuterCylinder + OuterCylinder_half_z;
Tube FTDOuterCylinderSolid(OuterCylinderInnerRadius,
OuterCylinderInnerRadius+_dbParCommon.outer_cylinder_total_thickness,
OuterCylinder_half_z,
phi1,
phi2);
Volume FTDOuterCylinderLogical("FTDOuterCylinder", FTDOuterCylinderSolid, _KaptonMat ) ;
ftd.setVisAttributes( theDetector, "FTDCylVis", FTDOuterCylinderLogical ) ;
Transform3D transCylPlus( RotationZYX() , Position(0.,0.,OuterCylinder_position));
Transform3D transCylMinus( RotationZYX(), Position(0.,0.,-OuterCylinder_position));
//fixme: do we need a special transform here ?
// nothing is placed anyways - see below...
// transCylMinus = transCylMinus*ReflectZ3D();
// Phys= ReflectionFactory::Instance()->Place(
// transCylPlus,
// "FTDOuterCylinder",
// FTDOuterCylinderLogical,
// worldLog,
// false,
// 0);
// registerPV( Phys );
//
// Phys= ReflectionFactory::Instance()->Place(
// transCylMinus,
// "FTDOuterCylinder",
// FTDOuterCylinderLogical,
// worldLog,
// false,
// 0);
// registerPV( Phys );
//=END============================ OUTER CYLINDER =============================END==/
//================================ INNER CYLINDER ==================================/
//... Inner cylinder (cone)
assert(_dbParDisk.ZStartInnerCylinder>0);
assert(_dbParDisk.ZStopInnerCylinder>0);
double InnerCylinder_half_z = (_dbParDisk.ZStopInnerCylinder-_dbParDisk.ZStartInnerCylinder)/2.;
assert(InnerCylinder_half_z>0);
//double InnerCylinder_position = _dbParDisk.ZStartInnerCylinder + InnerCylinder_half_z; NOT USED
double InnerCylinderRmin1 = InnerCylinderOuterRadius1 - _dbParCommon.inner_cylinder_total_thickness - (2.0*_dbParCommon.cable_shield_thickness) - _dbParCommon.cables_thickness ;
double InnerCylinderRmax1 = InnerCylinderOuterRadius1;
double InnerCylinderRmin2 = InnerCylinderOuterRadius2 - _dbParCommon.inner_cylinder_total_thickness - (2.0*_dbParCommon.cable_shield_thickness) - _dbParCommon.cables_thickness ;
double InnerCylinderRmax2 = InnerCylinderOuterRadius2;
double cableShieldRmin1 = InnerCylinderRmin1; double cableShieldRmax1 = cableShieldRmin1 + (2.0*_dbParCommon.cable_shield_thickness) + _dbParCommon.cables_thickness ;
double cableShieldRmin2 = InnerCylinderRmin2;
double cableShieldRmax2 = cableShieldRmin2 + (2.0*_dbParCommon.cable_shield_thickness) + _dbParCommon.cables_thickness;
double cablesRmin1 = cableShieldRmin1 + _dbParCommon.cable_shield_thickness;
double cablesRmax1 = cablesRmin1 + _dbParCommon.cables_thickness;
double cablesRmin2 = cableShieldRmin2 + _dbParCommon.cable_shield_thickness;
double cablesRmax2 = cablesRmin2 + _dbParCommon.cables_thickness;
ConeSegment FTDInnerCylinderSolid( InnerCylinder_half_z,
InnerCylinderRmin1,
InnerCylinderRmax1,
InnerCylinderRmin2,
InnerCylinderRmax2,
phi1,
phi2);
Volume FTDInnerCylinderLogical("FTDInnerCylinder", FTDInnerCylinderSolid, _KaptonMat ) ;
ftd.setVisAttributes( theDetector, "FTDCylVis", FTDInnerCylinderLogical ) ;
ConeSegment FTDCableShieldSolid( InnerCylinder_half_z,
cableShieldRmin1,
cableShieldRmax1,
cableShieldRmin2,
cableShieldRmax2,
phi1,
phi2);
Volume FTDCableShieldLogical( "FTDInnerCableShield", FTDCableShieldSolid, _KaptonMat ) ;
ftd.setVisAttributes( theDetector, "FTDCylVis", FTDCableShieldLogical );
ConeSegment FTDCablesSolid( InnerCylinder_half_z,
cablesRmin1,
cablesRmax1,
cablesRmin2,
cablesRmax2,
phi1,
phi2);
Volume FTDCablesLogical("FTDInnerCables", FTDCablesSolid, _CuMat ) ;
ftd.setVisAttributes( theDetector, "FTDCylVis", FTDCablesLogical ) ;
// fg: the placements are all commented out in the Mokka original
// so no outer cylinder is created - do we need one ???
// //... the cables are placed inside the cylinder
// Phys = ReflectionFactory::Instance()->Place(
// Transform3D(),
// "FTDInnerCables",
// FTDCablesLogical,
// FTDCableShieldLogical,
// false,
// 0);
// registerPV( Phys );
//
// Phys = ReflectionFactory::Instance()->Place(
// Transform3D(),
// "FTDInnerCableShield",
// FTDCableShieldLogical,
// FTDInnerCylinderLogical,
// false,
// 0);
// registerPV( Phys );
//
// Phys = ReflectionFactory::Instance()->Place(
// Transform3D(RotationMatrix(),
// Position(0., 0., InnerCylinder_position) ),
// "FTDInnerCylinder",
// FTDInnerCylinderLogical,
// worldLog,
// false,
// 0);
// registerPV( Phys );
//
// Transform3D Tcyl( RotationMatrix(), Position(0.,0.,-InnerCylinder_position) );
// Tcyl = Tcyl*ReflectZ3D();
// Phys = ReflectionFactory::Instance()->Place(
// Tcyl,
// "FTDInnerCylinder",
// FTDInnerCylinderLogical,
// worldLog,
// false,
// 0);
//fg registerPV( Phys );
//=END============================ INNER CYLINDER =============================END==/
#endif
#endif
//######################################################################################################################################################################
zDiskPetalsData->widthStrip = _dbParExReco.strip_width ;
zDiskPetalsData->lengthStrip = _dbParExReco.strip_length ;
zDiskPetalsData->pitchStrip = _dbParExReco.strip_pitch ;
zDiskPetalsData->angleStrip = _dbParExReco.strip_angle ;
ftd.addExtension< ZDiskPetalsData >( zDiskPetalsData ) ;
//--------------------------------------
if ( x_det.hasAttr(_U(combineHits)) ) {
ftd.setCombineHits(x_det.attr<bool>(_U(combineHits)),sens);
}
return ftd;
}
DECLARE_DETELEMENT(FTD_cepc ,create_element)
namespace cepc{
//===================================================================================================================================================================================
//================================ PETAL BUILD FUNCTIONS ======================================/
//fg: obsolete - call the two functions directly
// //***********************************************************************************************
// // Build the support, sensors and electronics, choosing what technology have the current disk
// //
// // Input Parameters:
// // valuesDict: map (name variable, its value) containing some dimension-disk
// // parameters, to be passed to the real building functions
// // mother: Volume where will be placed the volumes are going to
// // build.
// //
// void DoAndPlaceDisk( Detector& theDetector,DetElement det, SensitiveDetector sens, std::map<std::string,double> valuesDict, Volume mother )
// {
// petalSupport(theDetector, det, valuesDict, mother ) ; // support is placed at 0,0,0 withing the petal
// petalSensor( theDetector, det, sens, valuesDict, mother );
//}
//***********************************************************************************************
// Build the petal support. The support is a trapezoid made of foam.
//
// Input Parameters:
// valuesDict: map (name variable, its value) containing some dimension-disk
// parameters, to be passed to the real building functions
// mother: Volume the volumes built are to be placed.
void petalSupport( Detector& theDetector, DetElement ftd, std::map<std::string,double> valuesDict, Volume FTDPetalAirLogical )
{
double petal_cp_supp_half_dxMin = valuesDict["petal_cp_supp_half_dxMin"];
double petal_cp_support_dy = valuesDict["petal_cp_support_dy"];
double _inner_radius_petal = valuesDict["_inner_radius"];
if( _dbParDisk.sensor_is_pixel == 1) {
Trap FTDPetalSupportSolid( _dbParDisk.petal_cp_support_thickness/2.0, //thickness
0.0,
0.0,
petal_cp_support_dy/2.0, // dy
petal_cp_supp_half_dxMin, //dxMin
_dbParDisk.petal_cp_support_dxMax/2.0, //dxMax
0.0,
petal_cp_support_dy/2.0, // dy
petal_cp_supp_half_dxMin, // dxMin
_dbParDisk.petal_cp_support_dxMax/2.0, //dxMax
0.0);
Volume FTDPetalSupportLogical( _toString( _dbParDisk.disk_number, "FTDPetalSupportLogical_%d" ), FTDPetalSupportSolid, _CarbonFiberMat );
//printVolume( FTDPetalSupportLogical ) ;
ftd.setVisAttributes(theDetector, "FTDSupportVis" , FTDPetalSupportLogical ) ;
// Position Ta;
// Ta.setX(0.0);
// Ta.setY(0.0);
// Ta.setZ(0.0);
// PhysicalVolumesPair Phys = ReflectionFactory::Instance()->Place(
// Transform3D(RotationMatrix(),Ta),
// "FTDPetalSupport",
// FTDPetalSupportLogical,
// FTDPetalAirLogical,
// false,
// 0);
// registerPV(Phys);
// PlacedVolume pv =
FTDPetalAirLogical.placeVolume( FTDPetalSupportLogical , Transform3D() ) ;
} else {
Trap FTDPetalSupportCPSolid( _dbParDisk.petal_cp_support_thickness/2.0,//thickness
0.0,
0.0,
petal_cp_support_dy/2.0, // height
petal_cp_supp_half_dxMin,
_dbParDisk.petal_cp_support_dxMax/2.0,
0.0,
petal_cp_support_dy/2.0, // height
petal_cp_supp_half_dxMin,
_dbParDisk.petal_cp_support_dxMax/2.0,
0.0);
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% Holes %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%/
Trap FTDPetalSupportHoleDownSolid = SemiPetalSolid( petal_cp_support_dy, "DOWN", false );
Trap FTDPetalSupportHoleUpSolid = SemiPetalSolid( petal_cp_support_dy, "UP", false );
//fg
//fg // some transformation needed
const double petal_cp_holes_separation = 10.0*mm; // WARNING! HARDCODED...
//fg
//fg // RotationMatrix * idRot = new RotationMatrix;
Position movDown( 0.0, -petal_cp_support_dy/4.0+petal_cp_holes_separation/4.0, 0.0 );
Position movUp( 0.0, petal_cp_support_dy/4.0-petal_cp_holes_separation/4.0, 0.0);
//fg----- SemiPetalSolid does not seem to work - compute hole parameters here instead:
/* recover to FTD_cepc.cc in MokkaC, by fucd
// the space frame width
double spfw = _dbParCommon.support_spaceframe_width ;
double dxmin = petal_cp_supp_half_dxMin*2. ;
double dxmax = _dbParDisk.petal_cp_support_dxMax ;
double ybase = petal_cp_support_dy / ( dxmax / dxmin - 1. ) ;
// compute y_base to use intercept theorem for computing
// the x-widths of the wholes at various y-values
// dxMax _
// ----------- | | |
// \ / | | |
// XY-Plane \ dxMin / | dy YZ-Plane | |
// \_____/ | |_|
// \ / | dz
// \ / | ybase
// v |
double petal_hole_dy = ( petal_cp_support_dy - 3 * spfw ) / 2. ;
double petal_hole_down_dxMin = ( ( ybase + spfw ) / ybase ) * dxmin - 2. * spfw ;
double petal_hole_down_dxMax = ( ( ybase + spfw + petal_hole_dy ) / ybase ) * dxmin - 2. * spfw ;
double petal_hole_up_dxMin = ( ( ybase + spfw *2 + petal_hole_dy ) / ybase ) * dxmin - 2. * spfw ;
double petal_hole_up_dxMax = ( ( ybase + spfw *2 + petal_hole_dy * 2 ) / ybase ) * dxmin - 2. * spfw ;
Trap FTDPetalSupportHoleDownSolid( 2.*_dbParDisk.petal_cp_support_thickness/2.0,//thickness
0.0,
0.0,
petal_hole_dy/2.0, // height
petal_hole_down_dxMin/2.,
petal_hole_down_dxMax/2.,
0.0,
petal_hole_dy/2.0, // height
petal_hole_down_dxMin/2.,
petal_hole_down_dxMax/2.,
0.0) ;
Trap FTDPetalSupportHoleUpSolid( 2.*_dbParDisk.petal_cp_support_thickness/2.0,//thickness
0.0,
0.0,
petal_hole_dy/2.0, // height
petal_hole_up_dxMin/2.,
petal_hole_up_dxMax/2.,
0.0,
petal_hole_dy/2.0, // height
petal_hole_up_dxMin/2.,
petal_hole_up_dxMax/2.,
0.0 ) ;
Position movDown( 0.0, -( petal_hole_dy /2. + spfw / 2. ) , 0.0 );
Position movUp( 0.0, ( petal_hole_dy /2. + spfw / 2. ) , 0.0 );
#ifdef DEBUG_VALUES
std::cout << " *** support holes parameters : "
<< " petal_hole_dy " << petal_hole_dy
<< " petal_hole_down_dxMin " << petal_hole_down_dxMin
<< " petal_hole_down_dxMax " << petal_hole_down_dxMax
<< " petal_hole_up_dxMin " << petal_hole_up_dxMin
<< " petal_hole_up_dxMax " << petal_hole_up_dxMax
<< " y shift: " << ( petal_hole_dy /4. + spfw / 2. ) ;
#endif
//fg----- END: SemiPetalSolid does not seem to work - compute hole parameters here instead:
*/
SubtractionSolid FTDPetalSupportSolid_Prov( FTDPetalSupportCPSolid, FTDPetalSupportHoleDownSolid, movDown ) ;
SubtractionSolid FTDPetalSupportSolid( FTDPetalSupportSolid_Prov, FTDPetalSupportHoleUpSolid, movUp ) ;
//fg: debug stuff - cutting out tubes and boxes...
// Tube tubehole( 0, 20*mm , 2.*_dbParDisk.petal_cp_support_thickness );
// Box tubehole( 20*mm , 20*mm , 2.*_dbParDisk.petal_cp_support_thickness );
// SubtractionSolid FTDPetalSupportSolid_Prov( FTDPetalSupportCPSolid, tubehole , movDown ) ;
// SubtractionSolid FTDPetalSupportSolid( FTDPetalSupportSolid_Prov, tubehole , movUp ) ;
//%END%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%% Holes %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%END%/
// Petal support with two holes substracted
Volume FTDPetalSupportLogical (_toString( _dbParDisk.disk_number, "FTDPetalSupportLogical_%d" ), FTDPetalSupportSolid, _CarbonFiberMat ) ;
//printVolume( FTDPetalSupportLogical ) ;
ftd.setVisAttributes(theDetector, "FTDSupportVis" , FTDPetalSupportLogical ) ;
//ftd.setVisAttributes(theDetector, "Green Vis" , FTDPetalSupportLogical ) ;
// // Placing all together ( support petal boolean ) inside the air petal container
// PhysicalVolumesPair Phys = ReflectionFactory::Instance()->Place(
// Transform3D(),
// "FTDPetalSupport",
// FTDPetalSupportLogical,
// FTDPetalAirLogical,
// false,
// 0);
// registerPV(Phys);
// PlacedVolume pv =
FTDPetalAirLogical.placeVolume( FTDPetalSupportLogical , Transform3D() ) ;
}
//-END--------------------------- Central Part ----------------------------------END-/
#ifdef DEBUG_VALUES
cout << "===================================================================== " << "\n" <<
"FTDPetalSupport:\n" <<
" Inner Radius= " << _inner_radius_petal << "\n" <<
" Outer Radius= " << _outer_radius << "\n" <<
" xMax = " << _dbParDisk.petal_cp_support_dxMax << "\n" <<
" xMin = " << 2.0*petal_cp_supp_half_dxMin << "\n" <<
" dy = " << petal_cp_support_dy << "\n" <<
" thickness = " << _dbParDisk.petal_cp_support_thickness << "\n" <<
// " placed at \n" <<
// " x = " << Ta.getX() << "\n" <<
// " y = " << Ta.getY() << "\n" <<
// " z = " << Ta.getZ() << "\n" <<
endl;
#endif
// Gear Ladder
_ftdparameters[gearpar::SUPPORTRINNER].push_back(_inner_radius_petal);
_ftdparameters[gearpar::SUPPORTLENGTHMIN].push_back(2.0*petal_cp_supp_half_dxMin);
_ftdparameters[gearpar::SUPPORTLENGTHMAX].push_back(_dbParDisk.petal_cp_support_dxMax);
_ftdparameters[gearpar::SUPPORTWIDTH].push_back(petal_cp_support_dy);
_ftdparameters[gearpar::SUPPORTTHICKNESS].push_back(_dbParDisk.petal_cp_support_thickness);
}
//***********************************************************************************************
// Build the petal sensitive. The sensitive volume is a trapezoid made of silicon.
//
// Input Parameters:
// valuesDict: map (name variable, its value) containing some dimension-disk
// parameters, to be passed to the real building functions
// mother: Volume the volumes built are to be placed.
VolVec petalSensor( Detector& theDetector, DetElement ftd, SensitiveDetector sens, std::map<std::string,double> valuesDict, Volume FTDPetalAirLogical ) {
VolVec volV ;
double petal_half_dxMin = valuesDict["petal_cp_supp_half_dxMin"];
double petal_dy = valuesDict["petal_cp_support_dy"];
double _inner_radius_petalSensor = valuesDict["_inner_radius"];
Trap FTDPetalSensitiveSolid( _dbParDisk.disks_Si_thickness/2.0, //thickness
0.0,
0.0,
petal_dy/2.0, // dy
petal_half_dxMin, //dxMin
_dbParDisk.petal_cp_support_dxMax/2.0, //dxMax
0.0,
petal_dy/2.0, // dy
petal_half_dxMin, // dxMin
_dbParDisk.petal_cp_support_dxMax/2.0, //dxMax
0.0);
// Now check
// FIXME: sensitive detectors
// TRKSD_FTD01* sensitive_det = 0 ;
// if ( _dbParDisk.sensor_is_pixel ) {
// sensitive_det = _theFTDSD_pixel;
// }
// else {
// sensitive_det = _theFTDSD_strip;
// }
Volume FTDPetalSensitiveLogical (_toString( _dbParDisk.disk_number , "FTDPetalSensitiveLogical_%d" ) , FTDPetalSensitiveSolid, _SiMat ) ;
//printVolume( FTDPetalSensitiveLogical ) ;
FTDPetalSensitiveLogical.setSensitiveDetector( sens ) ;
//ftd.setVisAttributes( theDetector, "SeeThrough" , FTDPetalSensitiveLogical );
ftd.setVisAttributes( theDetector, "FTDSensitiveVis" , FTDPetalSensitiveLogical );
// front sensor
Position Ta( 0. , 0. , (_dbParDisk.petal_cp_support_thickness + _dbParDisk.disks_Si_thickness)/2.0 ) ;
// PhysicalVolumesPair Phys_front = ReflectionFactory::Instance()->Place(
// Transform3D(RotationMatrix(),Ta),
// "FTDPetalSensitive",
// FTDPetalSensitiveLogical,
// FTDPetalAirLogical,
// false,
// 1);
PlacedVolume pv = FTDPetalAirLogical.placeVolume( FTDPetalSensitiveLogical, Ta) ;
pv.addPhysVolID("sensor", 1 ) ;
volV.push_back( std::make_pair( FTDPetalSensitiveLogical , pv ) ) ;
#ifdef DEBUG_VALUES
cout << "===================================================================== " << "\n" <<
"FTDPetalSensitive:\n" <<
" Inner Radius= " << _inner_radius_petalSensor << "\n" <<
" Outer Radius= " << _outer_radius << "\n" <<
" xMax = " << _dbParDisk.petal_cp_support_dxMax << "\n" <<
" xMin = " << 2.0*petal_half_dxMin << "\n" <<
" dy = " << petal_dy << "\n" <<
" thickness = " << _dbParDisk.disks_Si_thickness << "\n" <<
" placed at\n " <<
" x = " << Ta.X() << "\n" <<
" y = " << Ta.Y() << "\n" <<
" z = " << Ta.Z() << "\n" <<
endl;
#endif
if(_dbParDisk.double_sided == 1 ) { // first two disks are single sided pixel
// rear sensor
Ta.SetZ( -(_dbParDisk.petal_cp_support_thickness + _dbParDisk.disks_Si_thickness)/2.0 );
// PhysicalVolumesPair Phys_rear = ReflectionFactory::Instance()->Place(
// Transform3D(RotationMatrix(),Ta),
// "FTDPetalSensitive",
// FTDPetalSensitiveLogical,
// FTDPetalAirLogical,
// false,
// 2);
pv = FTDPetalAirLogical.placeVolume( FTDPetalSensitiveLogical, Ta ) ;
pv.addPhysVolID("sensor", 2 ) ;
volV.push_back( std::make_pair( FTDPetalSensitiveLogical , pv ) ) ;
// registerPV(Phys_front);
// registerPV(Phys_rear);
#ifdef DEBUG_VALUES
cout << "===================================================================== " << "\n" <<
"FTDPetalSensitive:\n" <<
" Inner Radius= " << _inner_radius_petalSensor << "\n" <<
" Outer Radius= " << _outer_radius << "\n" <<
" xMax = " << _dbParDisk.petal_cp_support_dxMax << "\n" <<
" xMin = " << 2.0*petal_half_dxMin << "\n" <<
" dy = " << petal_dy << "\n" <<
" thickness = " << _dbParDisk.disks_Si_thickness << "\n" <<
" placed at\n " <<
" x = " << Ta.X() << "\n" <<
" y = " << Ta.Y() << "\n" <<
" z = " << Ta.Z() << "\n" <<
endl;
#endif
}
// //================================ SILICON SENSORS ==================================/
// // Sensors build as boxes of silicon. Assemblyblblaa
// //
// //
// double pixel_si_width = 9.9 * mm; //FIXME: From DB
// double pixel_si_length = 7.0 * mm; //FIXME: From DB
// double pixel_si_interspace = 5.0 * um; //FIXME: From DB
//
// Box * FTDPixelSolid = new Box( "FTDPixelSensor",
// pixel_si_length/2.0,
// pixel_si_width/2.0,
// _dbParDisk.disks_Si_thickness/2.0
// );
//
// Volume FTDPixelLogical ( FTDPixelSolid,
// _SiMat,
// "FTDPixelSensor",
// 0,
// 0,
// 0);
//
// FTDPixelLogical->SetVisAttributes( _VisAttSensitive );
// FTDPixelLogical->SetSensitiveDetector(_theFTDSD); //Sensitive
//
// // Defining two (one) rows of pixels per assembly
// std::vector<AssemblyVolume*> pixelsAssemblyRows;
//
// int howManyTotalRows = (int)(petal_cp_support_dy/pixel_si_width);
// // How many rows have in the first assembly (disk 1 = 2, disk 2 =2 );
// // except the first assembly, all the others have two rows per assembly
// int numberRows = 2;
// if( howManyTotalRows % 2 != 0 )
// {
// numberRows = 1;
// }
// int howManyMinPixels = (int)(2.0*petal_cp_supp_half_dxMin/pixel_si_length);
//#ifdef DEBUG_VALUES
// cout << "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ \n" <<
// "Total Pixel rows: " << howManyTotalRows << " ( really done " << howManyTotalRows/2.0 << " assemblies ) \n";
//#endif
//
// Position rowTrans( 0.0, 0.0, 0.0);
// for(int row = 0; row < (howManyTotalRows/2 + howManyTotalRows%2); ++row)
// {
// //Instantiating the assembly
// pixelsAssemblyRows.push_back( new AssemblyVolume() );
// // Number of pixels (lowest row should have 4)
// int nPixel = howManyMinPixels+row;
// // Positioning: note that if there are a odd number of
// // pixels, the center pixel is centered in x=0
// double x_offset = 0.0;
// if( nPixel % 2 == 1 )
// {
// x_offset = pixel_si_length/2.0;
// // Placing the central pixel
// rowTrans.setX( 0.0 );
// for(int j = 0; j < numberRows; ++j)
// {
// rowTrans.setY( pixel_si_width*(1.0/2.0 + j) +pixel_si_interspace );
// pixelsAssemblyRows.back()->AddPlacedVolume( FTDPixelLogical,
// rowTrans, (RotationMatrix*)0 );
// }
// }
// // The others pixels except the central one, if there is
// for(int pixelId = 0 ; pixelId < nPixel/2; ++pixelId)
// {
// rowTrans.setX( x_offset + pixel_si_length/2.0 + pixel_si_interspace + pixelId*pixel_si_length); //pixel_si_offset
// for(int j = 0; j < numberRows; ++j)
// {
// rowTrans.setY( pixel_si_width*(1.0/2.0 + j) + pixel_si_interspace );
// // Assembly built as two (or one) rows of pixels
// pixelsAssemblyRows.back()->AddPlacedVolume( FTDPixelLogical,
// rowTrans, (RotationMatrix*)0 );
// rowTrans.setX( -rowTrans.getX() ) ;
// pixelsAssemblyRows.back()->AddPlacedVolume( FTDPixelLogical,
// rowTrans, (RotationMatrix*)0 );
// }
// }
// // All the others assemblies have two rows
// numberRows = 2;
// }
// //Placing the assemblies inside the air petal, begining from the bottom
// // double dz = _dbParDisk.petal_cp_support_thickness/2.0 + _dbParDisk.kapton_petal_thickness + _dbParDisk.disks_Si_thickness/2.0;
// double dz = _dbParDisk.disks_Si_thickness /2.0;
//
// double dx = 0.0;
// double dy = -petal_cp_support_dy/2.0;
// Position inMotherTrans(dx, dy, dz);
// if( howManyTotalRows % 2 != 0 )
// {
// numberRows = 1;
// }
// for( std::vector<AssemblyVolume*>::iterator assemblyRow = pixelsAssemblyRows.begin();
// assemblyRow != pixelsAssemblyRows.end(); ++assemblyRow )
// {
//#ifdef DEBUG_VALUES
// static int i = 0;
// cout << "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ \n" <<
// " Placement pixels sensors: \n"
// << " Row " << i << ": dx=" << dx << ", dy=" << dy << ", dz=" << dz
// << " -- # pixel: " << (*assemblyRow)->GetInstanceCount() << "\n";
// cout << "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ \n" << endl;
// i++;
//#endif
// (*assemblyRow)->MakeImprint( FTDPetalSupportAirLogical, inMotherTrans, (RotationMatrix*)0 );
// // Ready to put the next one
// dy += 2.0*pixel_si_width;
// inMotherTrans.setY( dy );
// if( numberRows == 1 )
// {
// dy -= pixel_si_width;
// inMotherTrans.setY( dy );
// numberRows = 2;
// }
// }
// // Gear
// int howManyPixelsUp = (int)(_dbParDisk.petal_cp_support_dxMax/pixel_si_length);
_ftdparameters[gearpar::SENSITIVERINNER].push_back(_inner_radius_petalSensor);
_ftdparameters[gearpar::SENSITIVELENGTHMIN].push_back(2.0*petal_half_dxMin);
_ftdparameters[gearpar::SENSITIVELENGTHMAX].push_back(_dbParDisk.petal_cp_support_dxMax);
_ftdparameters[gearpar::SENSITIVEWIDTH].push_back(petal_dy);
_ftdparameters[gearpar::SENSITIVETHICKNESS].push_back(_dbParDisk.disks_Si_thickness);
return volV ;
}
//=END============================ PETAL BUILD FUNCTIONS ==================================END=/
//============================= PETAL DIMENSION FUNCTIONS =====================================/
// Functions to extract relative dimensions of the petals. The mechanical design for the petals
// is made taking as reference one disk (disk 1 for pixels, disk 4 for strips), so the petal
// is parametrized using variables given for the database (or calculates from them). All the
// dimensions of the petal are extracted having the inner radius and outer radius of the disk,
// the top length of the petal and the angle defined by the petal using trigonometry.
//
// (*)outer radius
// dxMax/2 dxMax
// ============ =============
// | // \ /
// dy | (*)<--/ / \ PETAL /
// | / / \ /
// -====/===/--> dxMin/2 ======= dxMin
// | / /
// inner radius |/ /
// -·····/
// | / dy = _outer_radius*cos( arcsin(dxMax/(2*_outer_radius)) ) - _inner_radius
// | / ( a = dxMax/(2*tag(theta)) - _inner_radius - dy )
// a | / dxMin = 2*tan(theta)*( _inner_radius + a )
// |-/ theta
// |/
//
//
// So, changing the inner radius it'll change the dy and dxMin as well, providing the diferents widths
// of the petal, needed to build the sensors, holes, etc...
//------------------------------------------------------------------------------------------
// Get the dy of the petal which corresponds to a given radius
//
// Input Parameters: inner radius
// Output Parameters: dy
double Getdy(const double & innerRadius ){
return _outer_radius*cos( asin(_dbParDisk.petal_cp_support_dxMax/(2.0*_outer_radius)) ) - innerRadius;
}
//------------------------------------------------------------------------------------------
// Get the dxMin of the petal which corresponds to a given radius
//
// Input Parameters: inner radius
// Output Parameters: dxMin
double Getdx( const double & innerRadius ) {
double a = _dbParDisk.petal_cp_support_dxMax/(2.0*tan(_dbParCommon.petal_half_angle_support)) - innerRadius -
Getdy( innerRadius );
return 2.0*(innerRadius + a)*tan(_dbParCommon.petal_half_angle_support);
}
//------------------------------------------------------------------------------------------
// Get the dimensions of the up and down holes or the silicon up or down sensors:
//
// Input parameters:
// petal_cp_support_dy: height of the air petal container
// whereItgoes: "UP" or "DOWN", where is placed
// isSilicon: True of False, define if is the sensor or the holes
//
// Output:
// std::vector<double>* = [ xMin_half, xMax_half, dy_half, thickness_half ]
std::vector<double> GetPetalDimensions( const double& petal_cp_support_dy, const std::string & whereItgoes, const bool isSilicon )
{
const double theta = _dbParCommon.petal_half_angle_support;
double central_separation_y = 10.0*mm/2.0; //HARDCODED _dbParDisk.petal_cp_holes_separation/2.0;
double x_dim = 6.0*mm/cos(theta); //HARDCODED _dbParDisk.petal_cp_holes_width_support/cos(theta);
double y_dimension = 10.0*mm; // HARDCODED _dbParDisk.petal_cp_holes_separation;
double half_thickness = _dbParDisk.petal_cp_support_thickness/2.0;
//Silicon detector or Hole?
if(isSilicon)
{
central_separation_y = 0.0;
const double padUp_Si_dxMax = 118.46*mm;
x_dim = (_dbParDisk.petal_cp_support_dxMax-padUp_Si_dxMax)/2.0; // HARDCODED
//x_dim = (_dbParDisk.petal_cp_support_dxMax-_dbParDisk.padUp_Si_dxMax)/2.0;
y_dimension = y_dimension/2.0;
half_thickness = _dbParDisk.disks_Si_thickness/2.0;
}
double pseudo_radius_up;
double pseudo_radius_down;
// Up or down?
if( whereItgoes == "UP" )
{
pseudo_radius_up = _inner_radius+petal_cp_support_dy - y_dimension;
pseudo_radius_down = _inner_radius+petal_cp_support_dy*_dbParCommon.petal_y_ratio + central_separation_y ;
}
else if( whereItgoes == "DOWN" )
{
pseudo_radius_up = _inner_radius + petal_cp_support_dy*_dbParCommon.petal_y_ratio - central_separation_y;
pseudo_radius_down = _inner_radius + y_dimension;
}
else
{
cout << "FTD_Simple_Staggered: Internal Error: The function SemiPetalSolid is not well called, the " <<
"4th argument must be \"UP\" or \"DOWN\".\n Check the code!!" << endl;
exit(-1);
}
const double xMin_half = (Getdx( pseudo_radius_down ) - x_dim)/2.0;
const double xMax_half = (Getdx( pseudo_radius_up )- x_dim)/2.0;
const double dy = pseudo_radius_up - pseudo_radius_down;
#ifdef DEBUG_VALUES
cout << "+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ \n" <<
" IsSilicon?: " << isSilicon <<
" " << whereItgoes <<
" xMin=" << 2.*xMin_half <<
" xMax=" << 2.0*xMax_half <<
" dy= " << dy << std::endl;
cout << "+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ \n" << endl;
#endif
std::vector<double> dimensions ;
dimensions.push_back( xMin_half );
dimensions.push_back( xMax_half );
dimensions.push_back( dy/2.0 );
dimensions.push_back( half_thickness );
return dimensions;
}
//------------------------------------------------------------------------------------------
// Construction of the up and down holes or the silicon up or down sensors
//
// Input parameters:
// petal_cp_support_dy: height of the air petal container
// whereItgoes: "UP" or "DOWN", where is placed
// isSilicon: True of False, define if is the sensor or the holes
//-------------------------------------------------------------------------------------------------------------------
Trap SemiPetalSolid( const double& petal_cp_support_dy, const std::string& whereItgoes, const bool isSilicon ){
// Get dimensions
const std::vector<double>& dimensions = GetPetalDimensions( petal_cp_support_dy, whereItgoes, isSilicon );
double xMin_half = dimensions[0];
double xMax_half = dimensions[1];
double dy_half = dimensions[2];
double half_thickness = dimensions[3];
return Trap( half_thickness,//thickness
0.0,
0.0,
dy_half, // height
xMin_half,
xMax_half,
0.0,
dy_half, // height
xMin_half,
xMax_half,
0.0 ) ;
// return FTDSemiPetalSolid ;
}
//=END========================= PETAL DIMENSION FUNCTIONS =================================END=/
//fixme: registering sensitive ...
// //*********************************************************************************************
// // Register two ftd sensitive detectors, one for the pixel disks and one for the strip disks
// void RegisterSDs( Database * db )
// {
// // Getting parameters disk-specific
// db->exec("select * from disks;");
// db->getTuple();
// double minDiskThickness (MAXFLOAT);
// do
// {
// _dbParDisk.disks_Si_thickness = db->fetchDouble("disk_si_thickness") ;
// if(minDiskThickness>_dbParDisk.disks_Si_thickness)
// {
// minDiskThickness = _dbParDisk.disks_Si_thickness;
// }
// } while(db->getTuple()!=NULL);
// this->_theFTDSD_pixel = new TRKSD_FTD01( "FTD_PIXEL", minDiskThickness * 340 * keV/mm * 0.2,true);
// RegisterSensitiveDetector(_theFTDSD_pixel);
// this->_theFTDSD_strip = new TRKSD_FTD01( "FTD_STRIP", minDiskThickness * 340 * keV/mm * 0.2,true);
// RegisterSensitiveDetector(_theFTDSD_strip);
// }
// void registerPV(const PhysicalVolumesPair & pvPair )
// {
// if( pvPair.first != 0 )
// {
// _registerPV.push_back( pvPair.first );
// }
// if( pvPair.second != 0 )
// {
// _registerPV.push_back( pvPair.second );
// }
// }
// //================================ GEAR STUFF FUNCTIONS ====================================/
#ifdef DD4HEP_WITH_GEAR
//fixme: seems to be never called in Mokka class (maybe outside ? )
void GearSetup()
{
//--- Added carbon fiber.
// TODO: It is needed some other changes??
// October, 2010, J.Duarte
double Si_RadLen, Si_dEdx;
double Kapton_RadLen, Kapton_dEdx;
double CarbonFiber_RadLen, CarbonFiber_dEdx;
double Cu_RadLen, Cu_dEdx;
Si_RadLen = _SiMat->GetRadlen();
Kapton_RadLen = _KaptonMat->GetRadlen();
Cu_RadLen = _CuMat->GetRadlen();
CarbonFiber_RadLen = _CarbonFiberMat->GetRadlen();
//... Looping over bins in the DEDX table to obtain the mip DEDX
//... From energy 0.0001MeV to 1000MeV in steps of 10 (See GetdEdx function)
Si_dEdx=GetdEdx( _SiMat );
Kapton_dEdx=GetdEdx(_KaptonMat);
CarbonFiber_dEdx = GetdEdx(_CarbonFiberMat);
Cu_dEdx=GetdEdx( _CuMat );
// Parameters for FTD
gear::GearMgr* gearMgr = MokkaGear::getMgr() ;
gear::FTDParametersImpl* ftdParam = new gear::FTDParametersImpl();
// Write gearParameters to GearMgr
for(unsigned int layer = 0; layer < _ftdparameters[gearpar::NPETALS].size(); layer++)
{
// Extract all the param
int nPetals = (int)_ftdparameters[gearpar::NPETALS].at(layer);
int nSensors = (int) _ftdparameters[gearpar::NSENSORS].at(layer);
bool isDoubleSided = (bool)_ftdparameters[gearpar::ISDOUBLESIDED].at(layer);
int sensorType = (int)_ftdparameters[gearpar::SENSORTYPE].at(layer);
double phalfangle = _ftdparameters[gearpar::HALFANGLEPETAL].at(layer);
double phi0 = _ftdparameters[gearpar::PHI0].at(layer);
// Correct the sign: axis of the trapezoids built inside a ref. with Z --> -Z
double signoffset = - _ftdparameters[gearpar::PETAL0SIGNOFFSET].at(layer);
double alpha = _ftdparameters[gearpar::ALPHA].at(layer);
double zposition = _ftdparameters[gearpar::ZPOSITION].at(layer);
double zoffset = _ftdparameters[gearpar::ZOFFSET].at(layer);
double suprtRin = _ftdparameters[gearpar::SUPPORTRINNER].at(layer);
double suprtThic = _ftdparameters[gearpar::SUPPORTTHICKNESS].at(layer);
double suprtLMin = _ftdparameters[gearpar::SUPPORTLENGTHMIN].at(layer);
double suprtLMax = _ftdparameters[gearpar::SUPPORTLENGTHMAX].at(layer);
double suprtW = _ftdparameters[gearpar::SUPPORTWIDTH].at(layer);
//double suprtRL = _ftdparameters[gearpar::SUPPORTRADLENGTH].at(layer); FIXME
double suprtRL = Si_RadLen;
double sensitRin = _ftdparameters[gearpar::SENSITIVERINNER].at(layer);
double sensitThic = _ftdparameters[gearpar::SENSITIVETHICKNESS].at(layer);
double sensitLMin = _ftdparameters[gearpar::SENSITIVELENGTHMIN].at(layer);
double sensitLMax = _ftdparameters[gearpar::SENSITIVELENGTHMAX].at(layer);
double sensitW = _ftdparameters[gearpar::SENSITIVEWIDTH].at(layer);
//double sensitRL = _ftdparameters[gearpar::SENSITIVERADLENGTH].at(layer); //FIXME
double sensitRL = Si_RadLen;
ftdParam->addLayer( nPetals, nSensors, isDoubleSided, sensorType, phalfangle, phi0, alpha,zposition, zoffset, signoffset,
suprtRin, suprtThic,
suprtLMin, suprtLMax,
suprtW, suprtRL,
sensitRin, sensitThic,
sensitLMin, sensitLMax,
sensitW, sensitRL ) ;
}
// Add the extended_reconstruction_parameters
ftdParam->setDoubleVal("strip_width", _dbParExReco.strip_width );
ftdParam->setDoubleVal("strip_length",_dbParExReco.strip_length);
ftdParam->setDoubleVal("strip_pitch", _dbParExReco.strip_pitch );
ftdParam->setDoubleVal("strip_angle", _dbParExReco.strip_angle );
gearMgr->setFTDParameters(ftdParam);
}
#endif
}
......@@ -77,9 +77,13 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
//PlacedVolume pv;
sens.setType("tracker");
if (x_det.hasChild(_U(sensitive))) {
xml_dim_t sd_typ = x_det.child(_U(sensitive));
sens.setType(sd_typ.typeStr());
}
else {
sens.setType("tracker");
}
dd4hep::rec::ZPlanarData* zPlanarData = new ZPlanarData ;
......@@ -297,7 +301,7 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
dd4hep::Volume setSenLogical( dd4hep:: _toString( layer_id,"SET_SenLogical_%02d"), setSenSolid,sensitiveMat ) ;
setSenLogical.setSensitiveDetector(sens);
if (x_det.hasAttr(_U(limits))) setSenLogical.setLimitSet(theDetector, x_det.limitsStr());
//====== create the meassurement surface ===================
......@@ -456,6 +460,10 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
set.setVisAttributes( theDetector, x_det.visStr(), envelope );
if ( x_det.hasAttr(_U(combineHits)) ) {
set.setCombineHits(x_det.attr<bool>(_U(combineHits)),sens);
}
return set;
}
......
......@@ -84,9 +84,13 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
dd4hep::PlacedVolume pv;
sens.setType("tracker");
if (x_det.hasChild(_U(sensitive))) {
xml_dim_t sd_typ = x_det.child(_U(sensitive));
sens.setType(sd_typ.typeStr());
}
else {
sens.setType("tracker");
}
dd4hep::rec::ZPlanarData* zPlanarData = new dd4hep::rec::ZPlanarData ;
......@@ -126,7 +130,11 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
dd4hep::Material sensitiveMat = theDetector.material(db->fetchString("sensitive_mat"));
dd4hep::Material supportMat = theDetector.material(db->fetchString("support_mat"));
db = XMLHandlerDB( x_det.child( _Unicode( display ) ) ) ;
std::string ladderVis = db->fetchString("ladder");
std::string supportVis = db->fetchString("support");
std::string sensEnvVis = db->fetchString("sens_env");
std::string sensVis = db->fetchString("sens");
// // // setup the encoder
// // UTIL::BitField64 encoder( LCTrackerCellID::encoding_string() ) ;
......@@ -286,7 +294,7 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
layer_geom.ladder_width / 2.0,
layer_geom.half_z);
dd4hep::Volume sitLadderLogical( dd4hep::_toString( layer_id,"SIT_LadderLogical_%02d"), sitLadderSolid, air ) ;
dd4hep::Volume sitLadderLogical( name + dd4hep::_toString( layer_id,"_LadderLogical_%02d"), sitLadderSolid, air ) ;
// now create an envelope volume to represent the sensitive area, which will be divided up into individual sensors
......@@ -295,7 +303,7 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
layer_geom.half_z);
//fixme: material ??? Volume sitSenEnvelopeLogical( _toString( layer_id,"SIT_SenEnvelopeLogical_%02d"), sitSenEnvelopeSolid, sensitiveMat ) ;
dd4hep::Volume sitSenEnvelopeLogical( dd4hep::_toString( layer_id,"SIT_SenEnvelopeLogical_%02d"),
dd4hep::Volume sitSenEnvelopeLogical( name + dd4hep::_toString( layer_id,"_SenEnvelopeLogical_%02d"),
sitSenEnvelopeSolid, air ) ;
// create the sensor volumes and place them in the senstive envelope volume
......@@ -304,10 +312,10 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
layer_geom.ladder_width / 2.0,
(layer_geom.sensor_length / 2.0 ) - 1.e-06 * dd4hep::mm ); // added tolerance to avoid false overlap detection
dd4hep::Volume sitSenLogical( dd4hep::_toString( layer_id,"SIT_SenLogical_%02d"), sitSenSolid,sensitiveMat ) ;
dd4hep::Volume sitSenLogical( name + dd4hep::_toString( layer_id,"_SenLogical_%02d"), sitSenSolid,sensitiveMat ) ;
sitSenLogical.setSensitiveDetector(sens);
if (x_det.hasAttr(_U(limits))) sitSenLogical.setLimitSet(theDetector, x_det.limitsStr());
//====== create the meassurement surface ===================
dd4hep::rec::Vector3D u,v,n ;
......@@ -371,10 +379,10 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
pvV[isensor] = pv ;
}
sit.setVisAttributes(theDetector, "SeeThrough", sitLadderLogical ) ;
sit.setVisAttributes(theDetector, "SeeThrough", sitSenEnvelopeLogical ) ;
sit.setVisAttributes(theDetector, ladderVis, sitLadderLogical ) ;
sit.setVisAttributes(theDetector, sensEnvVis, sitSenEnvelopeLogical ) ;
sit.setVisAttributes(theDetector, "BlueVis", sitSenLogical ) ;
sit.setVisAttributes(theDetector, sensVis, sitSenLogical ) ;
// encoder.reset() ; // reset to 0
......@@ -398,10 +406,10 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
layer_geom.ladder_width / 2.0,
layer_geom.half_z);
Volume sitSupLogical( _toString( layer_id,"SIT_SupLogical_%02d"), sitSupSolid, supportMat ) ;
Volume sitSupLogical( name + _toString( layer_id,"_SupLogical_%02d"), sitSupSolid, supportMat ) ;
sit.setVisAttributes(theDetector, "RedVis", sitSupLogical ) ;
sit.setVisAttributes(theDetector, supportVis, sitSupLogical ) ;
pv = sitLadderLogical.placeVolume( sitSupLogical, Transform3D( RotationY( 0.),
......@@ -472,6 +480,10 @@ static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4h
//--------------------------------------
sit.setVisAttributes( theDetector, x_det.visStr(), envelope );
if ( x_det.hasAttr(_U(combineHits)) ) {
sit.setCombineHits(x_det.attr<bool>(_U(combineHits)),sens);
}
return sit;
}
......
//====================================================================
// lcgeo - LC detector models in DD4hep
//--------------------------------------------------------------------
// F.Gaede, DESY
// $Id$
//====================================================================
#include "DD4hep/DetFactoryHelper.h"
#include "DD4hep/DD4hepUnits.h"
#include "DD4hep/DetType.h"
#include "DDRec/Surface.h"
#include "DDRec/DetectorData.h"
#include "XML/Utilities.h"
#include "XMLHandlerDB.h"
#include <cmath>
using namespace std;
using dd4hep::Box;
using dd4hep::DetElement;
using dd4hep::Position;
using dd4hep::RotationY;
using dd4hep::RotationZYX;
using dd4hep::Transform3D;
using dd4hep::Volume;
using dd4hep::_toString;
using dd4hep::rec::volSurfaceList;
using dd4hep::rec::ZPlanarData;
/** helper struct */
struct SIT_Layer {
int n_ladders;
int n_sensors_per_ladder;
double sensor_length;
double half_z;
double sensitive_inner_radius ;
double support_inner_radius ;
double ladder_width ;
double ladder_dphi ;
};
//std::vector<SIT_Layer> _SIT_Layers;
// /** helper struct */
// struct extended_reconstruction_parameters {
// double sensor_length_mm;
// double strip_width_mm;
// double strip_length_mm;
// double strip_pitch_mm;
// double strip_angle_deg;
// };
//extended_reconstruction_parameters _e_r_p;
/** Construction of the SIT detector, ported from Mokka driver SIT_Simple_Planar.cc
*
* Mokka History:
* Feb 7th 2011, Steve Aplin - original version
*
* @author: F.Gaede, DESY, Jan 2014
*/
static dd4hep::Ref_t create_element(dd4hep::Detector& theDetector, xml_h e, dd4hep::SensitiveDetector sens) {
//------------------------------------------
// See comments starting with '//**' for
// hints on porting issues
//------------------------------------------
xml_det_t x_det = e;
string name = x_det.nameStr();
dd4hep::DetElement sit( name, x_det.id() ) ;
// --- create an envelope volume and position it into the world ---------------------
dd4hep::Volume envelope = dd4hep::xml::createPlacedEnvelope( theDetector, e , sit ) ;
dd4hep::xml::setDetectorTypeFlag( e, sit ) ;
if( theDetector.buildType() == dd4hep::BUILD_ENVELOPE ) return sit ;
//-----------------------------------------------------------------------------------
dd4hep::PlacedVolume pv;
if (x_det.hasChild(_U(sensitive))) {
xml_dim_t sd_typ = x_det.child(_U(sensitive));
sens.setType(sd_typ.typeStr());
}
else {
sens.setType("tracker");
}
dd4hep::rec::ZPlanarData* zPlanarData = new dd4hep::rec::ZPlanarData ;
//######################################################################################################################################################################
// code ported from SIT_Simple_Planar::construct() :
//##################################
// extended_reconstruction_parameters _e_r_p;
// *********************
// Read and Store the Extended Reconstruction Parameters which are passed directly through to gear. Note others may be added below
// db->exec("select * from extended_reconstruction_parameters;");
// db->getTuple();
XMLHandlerDB db = XMLHandlerDB( x_det.child( _Unicode( reconstruction ) ) ) ;
zPlanarData->widthStrip = db->fetchDouble("strip_width") ;
zPlanarData->lengthStrip = db->fetchDouble("strip_length") ;
zPlanarData->pitchStrip = db->fetchDouble("strip_pitch") ;
zPlanarData->angleStrip = db->fetchDouble("strip_angle") ;
double strip_angle = zPlanarData->angleStrip ;
// *********************
//... db common_parameters
// // db->exec("select * from global;");
// // db->getTuple();
db = XMLHandlerDB( x_det.child( _Unicode( global ) ) ) ;
// Sensitive Thickness
double sensitive_thickness = db->fetchDouble("sensitive_thickness") ;
// Support Thickness
double support_thickness = db->fetchDouble("support_thickness") ;
// Sensor Length
double sensor_length = db->fetchDouble("sensor_length") ;
dd4hep::Material air = theDetector.air() ;
dd4hep::Material sensitiveMat = theDetector.material(db->fetchString("sensitive_mat"));
dd4hep::Material supportMat = theDetector.material(db->fetchString("support_mat"));
// // // setup the encoder
// // UTIL::BitField64 encoder( LCTrackerCellID::encoding_string() ) ;
// // encoder.reset() ; // reset to 0
// // encoder[LCTrackerCellID::subdet()] = ILDDetID::NOTUSED ;
// // encoder[LCTrackerCellID::side()] = 0 ;
// // encoder[LCTrackerCellID::layer()] = 0 ;
// // encoder[LCTrackerCellID::module()] = 0 ;
// // encoder[LCTrackerCellID::sensor()] = 0 ;
// // int cellID0 = encoder.lowWord() ;
//... The SIT Sensitive detector
//unused: double sensitive_threshold_KeV = db->fetchDouble("sensitive_threshold_KeV") ;
//FIXME: the SD ...
// // _theSITSD =
// // new TRKSD02("SIT",
// // _sensitive_thickness * mm
// // * sensitive_threshold_KeV ,
// // 10.0 * MeV);
// // RegisterSensitiveDetector(_theSITSD);
for(xml_coll_t c( x_det ,_U(layer)); c; ++c) {
xml_comp_t x_layer( c );
db = XMLHandlerDB( x_layer ) ;
int layer_id = db->fetchInt("layer_id");
double half_z(0);
double sensitive_radius(0);
double sensitive_inner_radius(0);
double support_radius(0);
int n_sensors_per_ladder(0) ;
int n_ladders(0) ;
double ladder_width(0) ;
double ladder_clearance(0) ;
int faces_IP(0) ;
int is_SIT1(0) ;
int is_SIT2(0) ;
sensitive_radius = db->fetchDouble("sensitive_radius") ;
n_sensors_per_ladder = db->fetchInt("n_sensors_per_ladder") ;
half_z = (n_sensors_per_ladder *sensor_length) / 2.0 ;
n_ladders = db->fetchInt("n_ladders") ;
faces_IP = db->fetchInt("faces_IP") ;
is_SIT1 = db->fetchInt("is_SIT1") ;
is_SIT2 = db->fetchInt("is_SIT2") ;
ladder_clearance = db->fetchDouble("ladder_clearance") ;
// create assembly and DetElement for the layer
std::string layerName = dd4hep::_toString( layer_id , "layer_%d" );
dd4hep::Assembly layer_assembly( layerName ) ;
pv = envelope.placeVolume( layer_assembly ) ;
dd4hep::DetElement layerDE( sit , layerName , x_det.id() );
layerDE.setPlacement( pv ) ;
const double ladder_dphi = ( dd4hep::twopi / n_ladders ) ;
sensitive_inner_radius = sensitive_radius - 0.5 *sensitive_thickness;
ladder_width = 2*(tan(ladder_dphi*0.5)*sensitive_inner_radius - ladder_clearance) ;
// double inner_most_radius = 0.0;
if( faces_IP == 1 ){ // support is on the outside
support_radius = sensitive_radius + (0.5 *sensitive_thickness) ;
ladder_width = 2*(tan(ladder_dphi*0.5)*sensitive_inner_radius - ladder_clearance) ;
// inner_most_radius = sensitive_inner_radius;
}
else{ // support is on the inside
support_radius = sensitive_radius - (0.5 *sensitive_thickness) -support_thickness;
ladder_width = 2*(tan(ladder_dphi*0.5)*support_radius - ladder_clearance) ;
// inner_most_radius = support_radius;
}
//FIXME: GEAR....
// std::ostringstream ossradius;
// std::ostringstream osshalfz;
// ossradius << inner_most_radius / mm;
// osshalfz << half_z / mm;
// if(is_SIT1 == 1){
// (*Control::globalModelParameters)["SIT1_Radius"] = ossradius.str();
// (*Control::globalModelParameters)["SIT1_Half_Length_Z"] = osshalfz.str();
// }
// if(is_SIT2 == 1){
// (*Control::globalModelParameters)["SIT2_Radius"] = ossradius.str();
// (*Control::globalModelParameters)["SIT2_Half_Length_Z"] = osshalfz.str();
// }
dd4hep::rec::ZPlanarData::LayerLayout thisLayer ;
thisLayer.sensorsPerLadder = n_sensors_per_ladder ;
thisLayer.lengthSensor = sensor_length ;
thisLayer.distanceSupport = support_radius;
thisLayer.offsetSupport = 0. ;
thisLayer.thicknessSupport = support_thickness ;
thisLayer.zHalfSupport = half_z ;
thisLayer.widthSupport = ladder_width ;
thisLayer.distanceSensitive = sensitive_radius - 0.5 *sensitive_thickness;
thisLayer.offsetSensitive = 0. ;
thisLayer.thicknessSensitive = sensitive_thickness ;
thisLayer.zHalfSensitive = half_z ;
thisLayer.widthSensitive = ladder_width ;
thisLayer.ladderNumber = n_ladders;
thisLayer.phi0 = 0. ;
zPlanarData->layers.push_back( thisLayer ) ;
SIT_Layer layer_geom ;
layer_geom.n_ladders = n_ladders;
layer_geom.sensor_length =sensor_length;
layer_geom.n_sensors_per_ladder = n_sensors_per_ladder;
layer_geom.half_z = half_z ;
layer_geom.sensitive_inner_radius = sensitive_radius - 0.5 *sensitive_thickness;
layer_geom.support_inner_radius = support_radius;
layer_geom.ladder_width = ladder_width ;
layer_geom.ladder_dphi = ladder_dphi;
std::vector<SIT_Layer>SIT_Layers;
SIT_Layers.push_back(layer_geom) ;
std::cout << "SIT_Simple_Planar: Layer:" << layer_id
<< "\t half length = " << layer_geom.half_z
<< "\t sensor length = " << layer_geom.sensor_length
<< "\t n sensors per ladder = " << layer_geom.n_sensors_per_ladder
<< "\t min r sensitive = " << layer_geom.sensitive_inner_radius
<< "\t min r support = " << layer_geom.support_inner_radius
<< "\t n ladders = " << layer_geom.n_ladders
<< "\t ladder width = " << layer_geom.ladder_width
<< "\t ladder clearance = " << ladder_clearance
<< "\t ladder dphi = " << ladder_dphi
<< "\t sensitive mat = " <<sensitiveMat->GetName()
<< "\t support mat = " <<supportMat->GetName()
<< "\t faces_IP = " << faces_IP
<< "\t is_SIT1 = " << is_SIT1
<< "\t is_SIT2 = " << is_SIT2
<< std::endl;
// std::stringstream name_base;
// name_base << "SIT";
// std::stringstream name_enum;
// name_enum << layer_id;
// create an enclosing ladder volume that will be placed in the world volume for every ladder
dd4hep::Box sitLadderSolid( (sensitive_thickness +support_thickness ) / 2.0 ,
layer_geom.ladder_width / 2.0,
layer_geom.half_z);
dd4hep::Volume sitLadderLogical( dd4hep::_toString( layer_id,"SIT_LadderLogical_%02d"), sitLadderSolid, air ) ;
// now create an envelope volume to represent the sensitive area, which will be divided up into individual sensors
dd4hep::Box sitSenEnvelopeSolid( (sensitive_thickness ) / 2.0 ,
layer_geom.ladder_width / 2.0,
layer_geom.half_z);
//fixme: material ??? Volume sitSenEnvelopeLogical( _toString( layer_id,"SIT_SenEnvelopeLogical_%02d"), sitSenEnvelopeSolid, sensitiveMat ) ;
dd4hep::Volume sitSenEnvelopeLogical( dd4hep::_toString( layer_id,"SIT_SenEnvelopeLogical_%02d"),
sitSenEnvelopeSolid, air ) ;
// create the sensor volumes and place them in the senstive envelope volume
dd4hep::Box sitSenSolid( (sensitive_thickness ) / 2.0 ,
layer_geom.ladder_width / 2.0,
(layer_geom.sensor_length / 2.0 ) - 1.e-06 * dd4hep::mm ); // added tolerance to avoid false overlap detection
dd4hep::Volume sitSenLogical( dd4hep::_toString( layer_id,"SIT_SenLogical_%02d"), sitSenSolid,sensitiveMat ) ;
sitSenLogical.setSensitiveDetector(sens);
if (x_det.hasAttr(_U(limits))) sitSenLogical.setLimitSet(theDetector, x_det.limitsStr());
//====== create the meassurement surface ===================
dd4hep::rec::Vector3D u,v,n ;
if( faces_IP == 0 ){
n.fill( -1. , 0. , 0. ) ;
// implement stereo angle
u.fill( 0. , -cos( strip_angle ) , -sin( strip_angle ) ) ;
v.fill( 0. , -sin( strip_angle ) , cos( strip_angle ) ) ;
} else {
n.fill( 1. , 0. , 0. ) ;
// implement stereo angle
u.fill( 0. , cos( strip_angle ) , sin( strip_angle ) ) ;
v.fill( 0. , -sin( strip_angle ) , cos( strip_angle ) ) ;
}
double inner_thick = sensitive_thickness / 2.0 ;
double outer_thick = sensitive_thickness / 2.0 ;
if( faces_IP ){
outer_thick += support_thickness ;
} else {
inner_thick += support_thickness ;
}
dd4hep::rec::VolPlane surf( sitSenLogical ,
dd4hep::rec::SurfaceType(dd4hep::rec::SurfaceType::Sensitive,
dd4hep::rec::SurfaceType::Measurement1D),
inner_thick, outer_thick , u,v,n ) ; //,o ) ;
// vector of sensor placements - needed for DetElements in ladder loop below
std::vector<dd4hep::PlacedVolume> pvV( layer_geom.n_sensors_per_ladder ) ;
//============================================================
for (int isensor=0; isensor < layer_geom.n_sensors_per_ladder ; ++isensor) {
// encoder.reset() ; // reset to 0
// encoder[LCTrackerCellID::subdet()] = ILDDetID::NOTUSED ;
// encoder[LCTrackerCellID::sensor()] = isensor+1;
// cellID0 = encoder.lowWord() ;
double xpos = 0.0;
double ypos = 0.0;
double zpos = -layer_geom.half_z + (0.5*layer_geom.sensor_length) + (isensor*layer_geom.sensor_length) ;
pv = sitSenEnvelopeLogical.placeVolume( sitSenLogical,
Transform3D( RotationY(0.) ,
Position( xpos, ypos, zpos) ) );
pv.addPhysVolID("sensor", isensor ) ;
//fixme: what is the correct numbering convention ?
// pv.addPhysVolID("sensor", isensor + 1 ) ;
pvV[isensor] = pv ;
}
sit.setVisAttributes(theDetector, "SeeThrough", sitLadderLogical ) ;
sit.setVisAttributes(theDetector, "SeeThrough", sitSenEnvelopeLogical ) ;
sit.setVisAttributes(theDetector, "BlueVis", sitSenLogical ) ;
// encoder.reset() ; // reset to 0
// encoder[LCTrackerCellID::subdet()] = ILDDetID::NOTUSED ;
// encoder[LCTrackerCellID::layer()] = layer_id ;
// cellID0 = encoder.lowWord() ;
pv = sitLadderLogical.placeVolume( sitSenEnvelopeLogical , Transform3D( RotationY( 0.),
Position( (-(sensitive_thickness +support_thickness ) / 2.0 + ( sensitive_thickness / 2.0) ), 0.,0.) ) );
// pv = sitSenEnvelopeLogical.placeVolume( sitLadderLogical, Transform3D( RotationY( 0.),
// Position( (-(sensitive_thickness +support_thickness ) / 2.0 + ( sensitive_thickness / 2.0) ), 0.,0.) ) );
//fixme: needed ?? pv.addPhysVolID("layer", layer_id ) ;
// create support volume which will be placed in the enclosing ladder volume together with the senstive envelope volume
Box sitSupSolid( (support_thickness ) / 2.0 ,
layer_geom.ladder_width / 2.0,
layer_geom.half_z);
Volume sitSupLogical( _toString( layer_id,"SIT_SupLogical_%02d"), sitSupSolid, supportMat ) ;
sit.setVisAttributes(theDetector, "RedVis", sitSupLogical ) ;
pv = sitLadderLogical.placeVolume( sitSupLogical, Transform3D( RotationY( 0.),
Position( (-(sensitive_thickness +support_thickness ) / 2.0 +sensitive_thickness + ( support_thickness / 2.0) ), 0.,0.) ) );
for( int i = 0 ; i < n_ladders ; ++i ){
std::stringstream ladder_enum; ladder_enum << "sit_ladder_" << layer_id << "_" << i;
DetElement ladderDE( layerDE , ladder_enum.str() , x_det.id() );
for (int isensor=0; isensor < layer_geom.n_sensors_per_ladder ; ++isensor) {
std::stringstream sensor_ss ; sensor_ss << ladder_enum.str() << "_" << isensor ;
DetElement sensorDE( ladderDE, sensor_ss.str() , x_det.id() );
sensorDE.setPlacement( pvV[isensor] ) ;
volSurfaceList( sensorDE )->push_back( surf ) ;
}
// RotationMatrix *rot = new RotationMatrix();
// rot->rotateZ( i * -ladder_dphi );
// // rotate by 180 degrees around z if facing away from the IP
// if( faces_IP == 0 ) rot->rotateZ( 180 * deg );
// encoder[LCTrackerCellID::subdet()] = ILDDetID::SIT ;
// encoder[LCTrackerCellID::layer()] = layer_id ;
// encoder[LCTrackerCellID::module()] = i + 1 ;
// cellID0 = encoder.lowWord() ;
float dr = ( (sensitive_thickness +support_thickness ) / 2.0 ) - (sensitive_thickness / 2.0 ) ;
// double phi_rot = i * -ladder_dphi ;
double phi_rot = i * ladder_dphi ;
if( faces_IP == 0 ) {
dr = -dr;
phi_rot += M_PI ;
}
pv = layer_assembly.placeVolume( sitLadderLogical, Transform3D( RotationZYX( phi_rot, 0. , 0. ),
Position( (sensitive_radius+dr) * cos(i * ladder_dphi),
(sensitive_radius+dr) * sin(i * ladder_dphi),
0. ) ) ) ;
pv.addPhysVolID("layer", layer_id ).addPhysVolID("module", i ) ;
//fixme: what is the correct numbering convention ?
//pv.addPhysVolID("layer", layer_id ).addPhysVolID("module", i+1 ) ;
ladderDE.setPlacement( pv ) ;
}
}
cout << "SIT_Simple_Planar done.\n" << endl;
//######################################################################################################################################################################
sit.addExtension< ZPlanarData >( zPlanarData ) ;
//--------------------------------------
sit.setVisAttributes( theDetector, x_det.visStr(), envelope );
if ( x_det.hasAttr(_U(combineHits)) ) {
sit.setCombineHits(x_det.attr<bool>(_U(combineHits)),sens);
}
return sit;
}
DECLARE_DETELEMENT(SIT_Simple_Planar,create_element)
......@@ -26,7 +26,7 @@ using dd4hep::rec::SurfaceType;
using dd4hep::rec::volSurfaceList;
using dd4hep::rec::VolPlane;
using dd4hep::rec::FixedPadSizeTPCData;
using dd4hep::rec::ConicalSupportData;
/** Construction of TPC detector, ported from Mokka driver TPC10.cc
* Mokka History:
* - modified version of TPC driver by Ties Behnke
......@@ -68,7 +68,13 @@ static Ref_t create_element(Detector& theDetector, xml_h e, SensitiveDetector se
PlacedVolume pv;
sens.setType("tracker");
if (x_det.hasChild(_U(sensitive))) {
xml_dim_t sd_typ = x_det.child(_U(sensitive));
sens.setType(sd_typ.typeStr());
}
else {
sens.setType("tracker");
}
std::cout << " ** building TPC10_geo in lcgeo " << lcgeo::versionString() << std::endl ;
......@@ -476,7 +482,10 @@ Material endplate_MaterialMix = theDetector.material( "TPC_endplate_mix" ) ;
lowerlayerLog.setSensitiveDetector(sens);
upperlayerLog.setSensitiveDetector(sens);
if (x_det.hasAttr(_U(limits))) {
lowerlayerLog.setLimitSet(theDetector, x_det.limitsStr());
upperlayerLog.setLimitSet(theDetector, x_det.limitsStr());
}
#else
// create just one volume per pad ring
......@@ -506,7 +515,9 @@ Material endplate_MaterialMix = theDetector.material( "TPC_endplate_mix" ) ;
layerDEbwd.setPlacement( pv ) ;
layerLog.setSensitiveDetector(sens);
if (x_det.hasAttr(_U(limits))) {
layerLog.setLimitSet(theDetector, x_det.limitsStr());
}
#endif
}
......@@ -620,9 +631,27 @@ Material endplate_MaterialMix = theDetector.material( "TPC_endplate_mix" ) ;
tpcData->driftLength = dz_Sensitive + dz_Cathode/2.0; // SJA: cathode has to be added as the sensitive region does not start at 0.00
tpcData->zMinReadout = dz_Cathode/2.0;
// tpcData.z_anode = dzTotal - dz_Endplate; // the edge of the readout terminating the drift volume
tpc.addExtension< FixedPadSizeTPCData >( tpcData ) ;
ConicalSupportData* supportData = new ConicalSupportData;
ConicalSupportData::Section section0;
section0.rInner = rMin_GasVolume;
section0.rOuter = rMax_GasVolume;
section0.zPos = dz_GasVolume - dz_Readout;
ConicalSupportData::Section section1;
section1.rInner = rMin_GasVolume;
section1.rOuter = rMax_GasVolume;
section1.zPos = dz_GasVolume;
ConicalSupportData::Section section2;
section2.rInner = rInner;
section2.rOuter = rOuter;
section2.zPos = dz_GasVolume + dz_Endplate;
supportData->sections.push_back(section0);
supportData->sections.push_back(section1);
supportData->sections.push_back(section2);
tpc.addExtension< FixedPadSizeTPCData >( tpcData ) ;
tpc.addExtension< ConicalSupportData > (supportData);
//######################################################################################################################################################################
......
......@@ -74,7 +74,13 @@ static Ref_t create_element(Detector& theDetector, xml_h e, SensitiveDetector se
//-----------------------------------------------------------------------------------
sens.setType("tracker");
if (x_det.hasChild(_U(sensitive))) {
xml_dim_t sd_typ = x_det.child(_U(sensitive));
sens.setType(sd_typ.typeStr());
}
else {
sens.setType("tracker");
}
// --- create assembly and DetElement for support and service volumes
......@@ -1071,7 +1077,7 @@ static Ref_t create_element(Detector& theDetector, xml_h e, SensitiveDetector se
vxd.setVisAttributes(theDetector, "BlueVis" , SiActiveLayerLogical ) ;
SiActiveLayerLogical.setSensitiveDetector(sens);
if (x_det.hasAttr(_U(limits))) SiActiveLayerLogical.setLimitSet(theDetector, x_det.limitsStr());
//====== create the meassurement surface ===================
Vector3D u( 1. , 0. , 0. ) ;
......@@ -1582,10 +1588,12 @@ static Ref_t create_element(Detector& theDetector, xml_h e, SensitiveDetector se
//--------------------------------------
vxd.setVisAttributes( theDetector, x_det.visStr(), envelope );
if ( x_det.hasAttr(_U(combineHits)) ) {
vxd.setCombineHits(x_det.attr<bool>(_U(combineHits)),sens);
}
return vxd;
}
DECLARE_DETELEMENT(VXD04,create_element)
......@@ -3,3 +3,101 @@
# CEPC Reference Detector (CRD)
################################################################################
gaudi_add_module(DetCRD
SOURCES src/Calorimeter/CRDEcal_v01.cpp
src/Calorimeter/LongCrystalBarBarrelCalorimeter32Polygon_v01.cpp
src/Calorimeter/LongCrystalBarBarrelCalorimeter32Polygon_v02.cpp
src/Calorimeter/LongCrystalBarEndcapCalorimeter_v01.cpp
src/Calorimeter/LongCrystalBarEndcapCalorimeter_v02.cpp
src/Calorimeter/LongCrystalBarEndcapCalorimeter_v03.cpp
src/Calorimeter/LongCrystalBarEndcapCalorimeter_v04.cpp
src/Calorimeter/CRDEcal_Short_v02.cpp
src/Calorimeter/CRDEcal_Endcap_Short_v01.cpp
src/Calorimeter/RotatedPolyhedraBarrelCalorimeter_v01_geo.cpp
src/Calorimeter/RotatedCrystalCalorimeter_v01_geo.cpp
src/Calorimeter/Lumical_v01_geo.cpp
src/Other/Lumical_v01_geo_beampipe.cpp
src/Other/CRDBeamPipe_v01_geo.cpp
src/Muon/Muon_Barrel_v01_04.cpp
src/Muon/Muon_Endcap_v01_02.cpp
src/Tracker/SiTrackerSkewRing_v01_geo.cpp
src/Tracker/ITK_EndCap_v01.cpp
src/Tracker/SiTrackerStitching_v01_geo.cpp
src/Tracker/SiTrackerStaggeredLadder_v01_geo.cpp
src/Tracker/SiTrackerStaggeredLadder_v02_geo.cpp
src/Tracker/SiTrackerStaggeredLadder_v03_geo.cpp
src/Tracker/SiTrackerComposite_v01_geo.cpp
src/Tracker/SiTrackerComposite_v02_geo.cpp
src/Tracker/SiTrackerComposite_v03_geo.cpp
src/Tracker/TPC_Simple_o1_v01.cpp
src/Tracker/TPC_ModularEndcap_o1_v01.cpp
src/Tracker/SiTracker_itkbarrel_v01_geo.cpp
src/Tracker/SiTracker_itkbarrel_v02_geo.cpp
src/Tracker/SiTracker_otkbarrel_v01_geo.cpp
src/Tracker/SiTracker_otkbarrel_v02_geo.cpp
src/Tracker/SiTracker_otkendcap_v02_geo.cpp
src/Tracker/SiTracker_otkendcap_v01_geo.cpp
src/Tracker/SiTracker_otkbarrel_v02_geo.cpp
src/Tracker/SiTracker_otkendcap_v02_geo.cpp
src/Other/ParaffinEndcap_v01.cpp
src/Other/ConcreteWall_v01.cpp
LINK ${DD4hep_COMPONENT_LIBRARIES}
DetIdentifier
)
set(LIBRARY_OUTPUT_PATH ${CMAKE_LIBRARY_OUTPUT_DIRECTORY})
message(STATUS "LIBRARY_OUTPUT_PATH -> ${LIBRARY_OUTPUT_PATH}")
dd4hep_generate_rootmap(DetCRD)
install(TARGETS DetCRD
EXPORT CEPCSWTargets
RUNTIME DESTINATION "${CMAKE_INSTALL_BINDIR}" COMPONENT bin
LIBRARY DESTINATION "${CMAKE_INSTALL_LIBDIR}" COMPONENT shlib
COMPONENT dev)
################################################################################
# Add tests
################################################################################
foreach(detoption TDR_o1_v01 TDR_o1_v02)
add_test(
NAME Test_${detoption}_Sim
COMMAND gaudirun.py Detector/DetCRD/scripts/${detoption}/sim.py
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
)
add_test(
NAME Test_${detoption}_Rec
COMMAND gaudirun.py Detector/DetCRD/scripts/${detoption}/tracking.py
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
)
add_test(
NAME Test_${detoption}_DD4hep2TGeo
COMMAND geoConverter -compact2tgeo
-input Detector/DetCRD/compact/${detoption}/${detoption}.xml
-output ${detoption}.tgeo.root
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
)
endforeach()
add_test(
NAME Test_TDR_o1_v01_CaloDigi
COMMAND gaudirun.py Detector/DetCRD/scripts/TDR_o1_v01/calodigi.py
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
)
add_test(
NAME Test_TDR_o1_v01_PFA
COMMAND gaudirun.py Detector/DetCRD/scripts/TDR_o1_v01/rec.py
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
)
foreach(detoption TDR_o1_v01)
add_test(
NAME Test_${detoption}_Geo
COMMAND checkOverlaps -c Detector/DetCRD/compact/${detoption}/${detoption}.xml -t 0.001
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}
)
endforeach()
<lccdd>
<info name="CRD" title="CRD Beam pipe" author="Chengdong Fu" url="no" status="development" version="1.0">
<comment>A beampipe for CRD</comment>
</info>
<display>
<vis name="TubeVis" alpha="0.1" r="1.0" g="0.7" b="0.5" showDaughters="true" visible="true"/>
<vis name="VacVis" alpha="1.0" r="0.0" g="0.0" b="0.0" showDaughters="true" visible="false"/>
</display>
<define>
<constant name="ForkAsymThickness" value="BeamPipe_Dnstream_inner_radius+BeamPipe_Cu_thickness-BeamPipe_Upstream_inner_radius"/>
<constant name="BeamPipe_QD0_zmax" value="3950*mm"/>
<constant name="BeamPipe_QF1_zmin" value="4450*mm"/>
<constant name="BeamPipe_QF1_zmax" value="5910*mm"/>
<constant name="BeamPipe_QF1_inner_radius" value="20.5*mm"/>
<constant name="BeamPipe_Iron_thickness" value="2.5*mm"/>
</define>
<detectors>
<detector name="BeamPipe" type="CRDBeamPipe_v01" vis="VacVis">
<parameter crossingangle="CrossingAngle" />
<envelope>
<shape type="Assembly"/>
</envelope>
<section type ="Center" name="IPInnerTube" zStart="0" zEnd="BeamPipe_CentralBe_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Central_inner_radius" vis="VacVis"/>
<layer material="G4_Be" thickness="BeamPipe_Be_inner_thickness" vis="TubeVis"/>
<layer material="G4_PARAFFIN" thickness="BeamPipe_Cooling_thickness" vis="GrayVis"/>
<layer material="G4_Be" thickness="BeamPipe_Be_outer_thickness" vis="TubeVis"/>
</section>
<section type="Center" name="IPAl" zStart="BeamPipe_CentralBe_zmax" zEnd="BeamPipe_CentralAl_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Central_inner_radius" vis="VacVis"/>
<layer material="G4_Al" thickness="BeamPipe_Al_thickness" vis="TubeVis"/>
</section>
<section type="Center" name="ExpandPipe" zStart="BeamPipe_CentralAl_zmax" zEnd="BeamPipe_ConeAl_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Central_inner_radius" thicknessEnd="BeamPipe_Expanded_inner_radius" vis="VacVis"/>
<layer material="G4_Al" thickness="BeamPipe_Al_thickness" thicknessEnd="BeamPipe_Al_thickness" vis="TubeVis"/>
</section>
<section type="Center" name="ThickPipe" zStart="BeamPipe_ConeAl_zmax" zEnd="BeamPipe_LinkerAl_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Expanded_inner_radius" vis="VacVis"/>
<layer material="G4_Al" thickness="BeamPipe_Al_thickness" vis="TubeVis"/>
</section>
<section type="CenterSide" name="OutsideLink" zStart="BeamPipe_LinkerAl_zmax" zEnd="BeamPipe_LinkerCu_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Expanded_inner_radius" vis="VacVis"/>
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="FatWaist" name="Waist" zStart="BeamPipe_LinkerCu_zmax" zEnd="BeamPipe_Waist_zmax" rStart="BeamPipe_Expanded_inner_radius" size="BeamPipe_Crotch_hole_height">
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="CrotchAsymUp" name="Fork" zStart="BeamPipe_Waist_zmax" zEnd="BeamPipe_Crotch_zmax"
rStart="BeamPipe_Expanded_inner_radius" rEnd="BeamPipe_Upstream_inner_radius" size="BeamPipe_Crotch_hole_height">
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" thicknessEnd="ForkAsymThickness" vis="TubeVis"/>
</section>
<section type="CrotchAsymDn" name="Fork" zStart="BeamPipe_Waist_zmax" zEnd="BeamPipe_Crotch_zmax"
rStart="BeamPipe_Expanded_inner_radius" rEnd="BeamPipe_Dnstream_inner_radius" size="BeamPipe_Crotch_hole_height">
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="FlareLegUp" name="FirstDoublePipe" zStart="BeamPipe_Crotch_zmax" zEnd="BeamPipe_FirstSeparated_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Upstream_inner_radius" thicknessEnd="BeamPipe_Dnstream_inner_radius" vis="VacVis"/>
<layer material="G4_Cu" thickness="ForkAsymThickness" thicknessEnd="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="FlareLegDn" name="FirstDoublePipe" zStart="BeamPipe_Crotch_zmax" zEnd="BeamPipe_FirstSeparated_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Dnstream_inner_radius" vis="VacVis"/>
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="Legs" name="QD0Link" zStart="BeamPipe_FirstSeparated_zmax" zEnd="BeamPipe_SecondSeparated_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Dnstream_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
</section>
<section type="Legs" name="QD0" zStart="BeamPipe_SecondSeparated_zmax" zEnd="BeamPipe_QD0_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Dnstream_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
<layer material="G4_Cu" thickness="3.5*mm" vis="TubeVis"/>
<layer material="superconductor" thickness="6.0*mm" vis="MagentaVis"/>
<layer material="stainless_steel" thickness="8.0*mm" vis="ShellVis"/>
</section>
<section type="Legs" name="QF1Link" zStart="BeamPipe_QD0_zmax" zEnd="BeamPipe_QF1_zmin" rStart="0">
<layer material="beam" thickness="BeamPipe_Dnstream_inner_radius" thicknessEnd="BeamPipe_QF1_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
</section>
<section type="Legs" name="QF1" zStart="BeamPipe_QF1_zmin" zEnd="BeamPipe_QF1_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_QF1_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
<layer material="G4_Cu" thickness="3.0*mm" vis="TubeVis"/>
<layer material="superconductor" thickness="6.0*mm" vis="MagentaVis"/>
<layer material="stainless_steel" thickness="8.0*mm" vis="ShellVis"/>
</section>
<section type="Legs" name="Farest" zStart="BeamPipe_QF1_zmax" zEnd="BeamPipe_end_z" rStart="0">
<layer material="beam" thickness="BeamPipe_QF1_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
</section>
<!-- Magnets and their cooling, support -->
<section type="CenterSide" name="Magnet_1" zStart="1160*mm" zEnd="1900*mm" rStart="90*mm">
<layer material="superconductor" thickness="20*mm" vis="MagentaVis"/>
</section>
<section type="CenterSide" name="Magnet_2" zStart="1930*mm" zEnd="3964*mm" rStart="120*mm">
<layer material="superconductor" thickness="10*mm" vis="MagentaVis"/>
</section>
<section type="CenterSide" name="Magnet_3" zStart="3970*mm" zEnd="7000*mm" rStart="185*mm">
<layer material="superconductor" thickness="10*mm" vis="MagentaVis"/>
</section>
<section type="CenterSide" name="MagnetShell_1" zStart="970*mm" zEnd="1110*mm" rStart="31*mm">
<layer material="stainless_steel" thickness="1.5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_2" zStart="1110*mm" zEnd="1115*mm" rStart="50.0*mm">
<layer material="stainless_steel" thickness="91.25*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_3" zStart="1115*mm" zEnd="1900*mm" rStart="130.75*mm" rEnd="175*mm">
<layer material="stainless_steel" thickness="10.5*mm" thicknessEnd="65*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_4" zStart="1900*mm" zEnd="3800*mm" rStart="175*mm">
<layer material="stainless_steel" thickness="65*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_5" zStart="3800*mm" zEnd="3910*mm" rStart="175*mm">
<layer material="stainless_steel" thickness="135*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_6" zStart="3910*mm" zEnd="7160*mm" rStart="240*mm">
<layer material="stainless_steel" thickness="70*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_1" zStart="1130*mm" zEnd="1135*mm" rStart="75*mm">
<layer material="stainless_steel" thickness="50*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_2i" zStart="1135*mm" zEnd="1925*mm" rStart="75*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_2o" zStart="1135*mm" zEnd="1900*mm" rStart="120*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_3l" zStart="1900*mm" zEnd="1905*mm" rStart="120*mm">
<layer material="stainless_steel" thickness="25*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_3r" zStart="1925*mm" zEnd="1930*mm" rStart="75*mm">
<layer material="stainless_steel" thickness="35*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_4i" zStart="1930*mm" zEnd="4000*mm" rStart="105*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_4o" zStart="1905*mm" zEnd="3940*mm" rStart="140*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_5l" zStart="3940*mm" zEnd="3945*mm" rStart="140*mm">
<layer material="stainless_steel" thickness="70*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_5r" zStart="4000*mm" zEnd="4005*mm" rStart="105*mm">
<layer material="stainless_steel" thickness="70*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_6i" zStart="4005*mm" zEnd="7050*mm" rStart="170*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_6o" zStart="3945*mm" zEnd="7050*mm" rStart="205*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_7" zStart="7050*mm" zEnd="7055*mm" rStart="170*mm">
<layer material="stainless_steel" thickness="40*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_1l" zStart="1135*mm" zEnd="1160*mm" rStart="80*mm">
<layer material="lN2" thickness="40*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_1i" zStart="1160*mm" zEnd="1900*mm" rStart="80*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_1o" zStart="1160*mm" zEnd="1900*mm" rStart="110*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_1r" zStart="1900*mm" zEnd="1925*mm" rStart="80*mm">
<layer material="lN2" thickness="40*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2l" zStart="1905*mm" zEnd="1930*mm" rStart="120*mm">
<layer material="lN2" thickness="20*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2i" zStart="1925*mm" zEnd="3964*mm" rStart="110*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2o" zStart="1930*mm" zEnd="3945*mm" rStart="130*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2r1" zStart="3964*mm" zEnd="4000*mm" rStart="110*mm">
<layer material="lN2" thickness="65*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2r2" zStart="3945*mm" zEnd="3964*mm" rStart="130*mm">
<layer material="lN2" thickness="45*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_3l" zStart="3945*mm" zEnd="3970*mm" rStart="175*mm">
<layer material="lN2" thickness="30*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_3i" zStart="3970*mm" zEnd="7000*mm" rStart="175*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_3o" zStart="3970*mm" zEnd="7000*mm" rStart="195*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_3r" zStart="7000*mm" zEnd="7050*mm" rStart="175*mm">
<layer material="lN2" thickness="30*mm" vis="BlueVis"/>
</section>
</detector>
</detectors>
</lccdd>
<lccdd>
<info name="CRD" title="CRD Beam pipe" author="Chengdong Fu" url="no" status="development" version="1.0">
<comment>A beampipe for CRD</comment>
</info>
<display>
<vis name="TubeVis" alpha="0.1" r="1.0" g="0.7" b="0.5" showDaughters="true" visible="true"/>
<vis name="VacVis" alpha="1.0" r="0.0" g="0.0" b="0.0" showDaughters="true" visible="false"/>
</display>
<define>
<!--only needed for asymetry double pipe-->
<!--constant name="ForkAsymThickness" value="BeamPipe_Dnstream_inner_radius+BeamPipe_Cu_thickness-BeamPipe_Upstream_inner_radius"/-->
<constant name="BeamPipe_QD0_zmax" value="3950*mm"/>
<constant name="BeamPipe_QF1_zmin" value="4450*mm"/>
<constant name="BeamPipe_QF1_zmax" value="5910*mm"/>
<constant name="BeamPipe_QF1_inner_radius" value="20.5*mm"/>
<constant name="BeamPipe_Iron_thickness" value="2.5*mm"/>
</define>
<detectors>
<detector name="BeamPipe" type="CRDBeamPipe_v01" vis="VacVis">
<parameter crossingangle="CrossingAngle" />
<envelope>
<shape type="Assembly"/>
</envelope>
<section type ="Center" name="IPInnerTube" zStart="0" zEnd="BeamPipe_CentralBe_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Central_inner_radius" vis="VacVis"/>
<layer material="G4_Be" thickness="BeamPipe_Be_inner_thickness" vis="TubeVis"/>
<layer material="G4_PARAFFIN" thickness="BeamPipe_Cooling_thickness" vis="GrayVis"/>
<layer material="G4_Be" thickness="BeamPipe_Be_outer_thickness" vis="TubeVis"/>
</section>
<section type="Center" name="IPAl" zStart="BeamPipe_CentralBe_zmax" zEnd="BeamPipe_CentralAl_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Central_inner_radius" vis="VacVis"/>
<layer material="G4_Al" thickness="BeamPipe_Al_thickness" vis="TubeVis"/>
</section>
<section type="Waist" name="Waist1st" zStart="BeamPipe_CentralAl_zmax" zEnd="BeamPipe_ExpandAl_zmax" rStart="BeamPipe_Central_inner_radius" size="BeamPipe_FirstExpand_width">
<layer material="G4_Al" thickness="BeamPipe_Al_thickness" vis="TubeVis"/>
</section>
<section type="Runway" name="Waist2nd" zStart="BeamPipe_ExpandAl_zmax" zEnd="BeamPipe_Linker_zmin" rStart="BeamPipe_Central_inner_radius" size="BeamPipe_FirstExpand_width">
<layer material="G4_Al" thickness="BeamPipe_Al_thickness" vis="TubeVis"/>
</section>
<section type="Runway" name="Waist3rd" zStart="BeamPipe_Linker_zmin" zEnd="BeamPipe_Linker_zmax" rStart="BeamPipe_Central_inner_radius" size="BeamPipe_FirstExpand_width">
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="Runway" name="Waist4th" zStart="BeamPipe_Linker_zmax" zEnd="BeamPipe_Waist_zmax" rStart="BeamPipe_Central_inner_radius" size="BeamPipe_FirstExpand_width"
shift="BeamPipe_SecondExpand_width-BeamPipe_FirstExpand_width">
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="Crotch" name="Fork" zStart="BeamPipe_Waist_zmax" zEnd="BeamPipe_Crotch_zmax"
rStart="BeamPipe_Central_inner_radius" rEnd="BeamPipe_Central_inner_radius" size="BeamPipe_SecondExpand_width">
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="Legs" name="FirstDoublePipe" zStart="BeamPipe_Crotch_zmax" zEnd="BeamPipe_FirstSeparated_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Fork_inner_radius" vis="VacVis"/>
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="Legs" name="BeforeMask" zStart="BeamPipe_FirstSeparated_zmax" zEnd="BeamPipe_Mask_zmin" rStart="0">
<layer material="beam" thickness="BeamPipe_Fork_inner_radius" vis="VacVis"/>
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="Legs" name="Mask" zStart="BeamPipe_Mask_zmin" zEnd="BeamPipe_Mask_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Mask_inner_radius" vis="VacVis"/>
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness+BeamPipe_Fork_inner_radius-BeamPipe_Mask_inner_radius" vis="TubeVis"/>
</section>
<section type="Legs" name="SecondDoublePipe" zStart="BeamPipe_Mask_zmax" zEnd="BeamPipe_SecondSeparated_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Fork_inner_radius" vis="VacVis"/>
<layer material="G4_Cu" thickness="BeamPipe_Cu_thickness" vis="TubeVis"/>
</section>
<section type="Legs" name="QD0" zStart="BeamPipe_SecondSeparated_zmax" zEnd="BeamPipe_QD0_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_Fork_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
<layer material="G4_Cu" thickness="3.5*mm" vis="TubeVis"/>
<layer material="superconductor" thickness="6.0*mm" vis="MagentaVis"/>
<layer material="stainless_steel" thickness="8.0*mm" vis="ShellVis"/>
</section>
<section type="Legs" name="QF1Linker" zStart="BeamPipe_QD0_zmax" zEnd="BeamPipe_QF1_zmin" rStart="0">
<layer material="beam" thickness="BeamPipe_Fork_inner_radius" thicknessEnd="BeamPipe_QF1_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
</section>
<section type="Legs" name="QF1" zStart="BeamPipe_QF1_zmin" zEnd="BeamPipe_QF1_zmax" rStart="0">
<layer material="beam" thickness="BeamPipe_QF1_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
<layer material="G4_Cu" thickness="3.0*mm" vis="TubeVis"/>
<layer material="superconductor" thickness="6.0*mm" vis="MagentaVis"/>
<layer material="stainless_steel" thickness="8.0*mm" vis="ShellVis"/>
</section>
<section type="Legs" name="Farest" zStart="BeamPipe_QF1_zmax" zEnd="BeamPipe_end_z" rStart="0">
<layer material="beam" thickness="BeamPipe_QF1_inner_radius" vis="VacVis"/>
<layer material="stainless_steel" thickness="BeamPipe_Iron_thickness" vis="TubeVis"/>
</section>
<!-- Magnets and their cooling, support -->
<section type="CenterSide" name="Magnet_1" zStart="1160*mm" zEnd="1900*mm" rStart="90*mm">
<layer material="superconductor" thickness="20*mm" vis="MagentaVis"/>
</section>
<section type="CenterSide" name="Magnet_2" zStart="1930*mm" zEnd="3964*mm" rStart="120*mm">
<layer material="superconductor" thickness="10*mm" vis="MagentaVis"/>
</section>
<section type="CenterSide" name="Magnet_3" zStart="3970*mm" zEnd="7000*mm" rStart="185*mm">
<layer material="superconductor" thickness="10*mm" vis="MagentaVis"/>
</section>
<!--TO DO: overlap with Lumical-->
<!--section type="CenterSide" name="MagnetShell_1" zStart="970*mm" zEnd="1110*mm" rStart="33*mm">
<layer material="stainless_steel" thickness="1.5*mm" vis="ShellVis"/>
</section-->
<section type="CenterSide" name="MagnetShell_2" zStart="1110*mm" zEnd="1115*mm" rStart="50.0*mm">
<layer material="stainless_steel" thickness="91.25*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_3" zStart="1115*mm" zEnd="1900*mm" rStart="130.75*mm" rEnd="175*mm">
<layer material="stainless_steel" thickness="10.5*mm" thicknessEnd="65*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_4" zStart="1900*mm" zEnd="3800*mm" rStart="175*mm">
<layer material="stainless_steel" thickness="65*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_5" zStart="3800*mm" zEnd="3910*mm" rStart="175*mm">
<layer material="stainless_steel" thickness="135*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetShell_6" zStart="3910*mm" zEnd="7160*mm" rStart="240*mm">
<layer material="stainless_steel" thickness="70*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_1" zStart="1130*mm" zEnd="1135*mm" rStart="75*mm">
<layer material="stainless_steel" thickness="50*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_2i" zStart="1135*mm" zEnd="1925*mm" rStart="75*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_2o" zStart="1135*mm" zEnd="1900*mm" rStart="120*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_3l" zStart="1900*mm" zEnd="1905*mm" rStart="120*mm">
<layer material="stainless_steel" thickness="25*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_3r" zStart="1925*mm" zEnd="1930*mm" rStart="75*mm">
<layer material="stainless_steel" thickness="35*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_4i" zStart="1930*mm" zEnd="4000*mm" rStart="105*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_4o" zStart="1905*mm" zEnd="3940*mm" rStart="140*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_5l" zStart="3940*mm" zEnd="3945*mm" rStart="140*mm">
<layer material="stainless_steel" thickness="70*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_5r" zStart="4000*mm" zEnd="4005*mm" rStart="105*mm">
<layer material="stainless_steel" thickness="70*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_6i" zStart="4005*mm" zEnd="7050*mm" rStart="170*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_6o" zStart="3945*mm" zEnd="7050*mm" rStart="205*mm">
<layer material="stainless_steel" thickness="5*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetSupport_7" zStart="7050*mm" zEnd="7055*mm" rStart="170*mm">
<layer material="stainless_steel" thickness="40*mm" vis="ShellVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_1l" zStart="1135*mm" zEnd="1160*mm" rStart="80*mm">
<layer material="lN2" thickness="40*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_1i" zStart="1160*mm" zEnd="1900*mm" rStart="80*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_1o" zStart="1160*mm" zEnd="1900*mm" rStart="110*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_1r" zStart="1900*mm" zEnd="1925*mm" rStart="80*mm">
<layer material="lN2" thickness="40*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2l" zStart="1905*mm" zEnd="1930*mm" rStart="120*mm">
<layer material="lN2" thickness="20*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2i" zStart="1925*mm" zEnd="3964*mm" rStart="110*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2o" zStart="1930*mm" zEnd="3945*mm" rStart="130*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2r1" zStart="3964*mm" zEnd="4000*mm" rStart="110*mm">
<layer material="lN2" thickness="65*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_2r2" zStart="3945*mm" zEnd="3964*mm" rStart="130*mm">
<layer material="lN2" thickness="45*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_3l" zStart="3945*mm" zEnd="3970*mm" rStart="175*mm">
<layer material="lN2" thickness="30*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_3i" zStart="3970*mm" zEnd="7000*mm" rStart="175*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_3o" zStart="3970*mm" zEnd="7000*mm" rStart="195*mm">
<layer material="lN2" thickness="10*mm" vis="BlueVis"/>
</section>
<section type="CenterSide" name="MagnetCooling_3r" zStart="7000*mm" zEnd="7050*mm" rStart="175*mm">
<layer material="lN2" thickness="30*mm" vis="BlueVis"/>
</section>
</detector>
</detectors>
</lccdd>
<lccdd>
<detectors>
<detector name="Coil" type="DD4hep_Solenoid_o1_v01" id="DetID_COIL" insideTrackingVolume="false" readout="COILCollection">
<envelope>
<shape type="Tube" rmin="Solenoid_inner_radius" rmax="Solenoid_outer_radius" dz="Solenoid_half_length" material="Vacuum"/>
</envelope>
<type_flags type=" DetType_SUPPORT + DetType_COIL " />
<!-- slice can put as sensitive (tracker type), currently without sensitive, so COILCollection is null -->
<layer id="0" inner_r="Solenoid_inner_radius" outer_z="Solenoid_half_length" vis="SeeThrough">
<slice material="g10" thickness="3*mm" vis="SOLVis"/>
<slice material="Vacuum" thickness="6*mm" vis="Invisible"/>
<slice material="G4_Al" thickness="6*mm" vis="SOLVis"/>
</layer>
<layer id="1" inner_r="SolenoidCoil_radius" outer_z="Solenoid_half_length" vis="SeeThrough">
<slice material="G4_Al" thickness="55*mm" vis="SOLVis"/>
</layer>
<layer id="2" inner_r="Solenoid_outer_radius-27*mm" outer_z="Solenoid_half_length" vis="SeeThrough">
<slice material="G4_Al" thickness="6*mm" vis="SOLVis"/>
<slice material="Vacuum" thickness="6*mm" vis="Invisible"/>
<slice material="G4_Al" thickness="15*mm" vis="SOLVis"/>
</layer>
</detector>
</detectors>
<readouts>
<readout name="COILCollection">
<id>system:5,side:-2,layer:9,slice:8,sensor:8,barrelside:-2</id>
</readout>
</readouts>
</lccdd>
<?xml version="1.0" encoding="UTF-8"?>
<lccdd>
<define>
<constant name="concrete_position_z" value="592.5*cm"/>
<constant name="concrete_hole_rmin" value="65*cm"/>
<constant name="concrete_wall_size" value="520*cm"/>
<constant name="concrete_wall_hz" value="50*cm"/>
</define>
<detectors>
<detector name="ConcreteWall" type="ConcreteWall_v01" vis="VisibleBrown" material="Concrete">
<!-- Use cm as unit if you want to use Pandora for reconstruction -->
<position x="0" y="0" z="concrete_position_z"/>
<dimensions rmax="concrete_wall_size" rmin="concrete_hole_rmin" dz="concrete_wall_hz"/>
</detector>
</detectors>
</lccdd>
<?xml version="1.0" encoding="UTF-8"?>
<lccdd>
<info name="DriftChamber"
title="Test with Drift Chamber"
author="Tao Lin"
url="http://github.com/cepc/CEPCSW"
status="development"
version="v0">
<comment>Test with Drift Chamber</comment>
</info>
<define>
<constant name="DC_layer_number" value="100"/>
<constant name="Alpha" value="12*deg"/>
<constant name="Gas_radius_min" value="DC_rbegin+DC_inner_wall_thickness+DC_safe_distance"/>
<constant name="Gas_half_length" value="DC_half_length-DC_Endcap_dz-DC_safe_distance"/>
<constant name="Gas_length" value="Gas_half_length*2"/>
<constant name="DC_cell_width" value="10*mm"/>
<constant name="DC_inner_wall_radius_min" value="DC_rbegin"/>
<constant name="DC_inner_wall_radius_max" value="DC_rbegin+DC_inner_wall_thickness"/>
<constant name="DC_Endcap_rmin" value="DC_rbegin"/>
<constant name="DC_Endcap_rmax" value="DC_rend"/>
<constant name="DC_construct_wire" value="1"/>
<constant name="DC_layer_width" value="9.57687*mm"/>
</define>
<limits>
<limitset name="DC_limits">
<limit name="step_length_max" particles="*" value="0.1" unit="mm" />
</limitset>
</limits>
<regions>
<region name="DriftChamberRegion">
</region>
</regions>
<detectors>
<detector id="DetID_DC" name="DriftChamber" type="DriftChamber" readout="DriftChamberHitsCollection" vis="DCVis" sensitive="true" region="DriftChamberRegion" limits="DC_limits">
<material name="Air"/>
<chamber id="0" material="GasHe_90Isob_10"/>
<side material="CarbonFiber"/>
<envelope vis="SeeThrough">
<shape type="BooleanShape" operation="Union" material="Air">
<shape type="Tube" rmin="DC_rbegin" rmax="DC_rend" dz="DC_half_length" />
</shape>
</envelope>
<module id="0" name="SignalWire" type="Tube" rmin="0*mm" rmax="0.01*mm" vis="RedVis">
<tubs name="W" type="Tube" rmin="0*mm" rmax="0.007*mm" material="Tungsten"/>
<tubs name="Au" type="Tube" rmin="0.007*mm" rmax="0.01*mm" material="Gold"/>
</module>
<module id="1" name="FieldWire" type="Tube" rmin="0*mm" rmax="0.02*mm" vis="GreenVis">
<tubs name="Al" type="Tube" rmin="0*mm" rmax="0.017*mm" material="Aluminum"/>
<tubs name="Ag" type="Tube" rmin="0.017*mm" rmax="0.02*mm" material="Silver"/>
</module>
<type_flags type="DetType_TRACKER + DetType_BARREL + DetType_GASEOUS + DetType_WIRE"/>
<!-- Use cm as unit if you want to use Pandora for reconstruction -->
<sensitive type="SimpleDriftChamber"/>
</detector>
</detectors>
<readouts>
<readout name="DriftChamberHitsCollection">
<segmentation type="GridDriftChamber" cell_size="DC_cell_width" detector_length="Gas_length" identifier_phi="cellID" layerID="layer" DC_rbegin="DC_rbegin" DC_rend="DC_rend" layer_width="DC_layer_width"/>
<id>system:5,layer:7:9,chamber:8,cellID:32:16</id>
</readout>
</readouts>
</lccdd>
<?xml version="1.0" encoding="UTF-8"?>
<lccdd>
<info name="DriftChamber"
title="Test with Drift Chamber"
author="Tao Lin"
url="http://github.com/cepc/CEPCSW"
status="development"
version="v0">
<comment>Test with Drift Chamber</comment>
</info>
<define>
<constant name="DC_layer_number" value="55"/>
<constant name="Alpha" value="12*deg"/>
<constant name="Gas_radius_min" value="DC_rbegin+DC_inner_wall_thickness+DC_safe_distance"/>
<constant name="Gas_half_length" value="DC_half_length-DC_Endcap_dz-DC_safe_distance"/>
<constant name="Gas_length" value="Gas_half_length*2"/>
<constant name="DC_cell_width" value="18*mm"/>
<constant name="DC_inner_wall_radius_min" value="DC_rbegin"/>
<constant name="DC_inner_wall_radius_max" value="DC_rbegin+DC_inner_wall_thickness"/>
<constant name="DC_Endcap_rmin" value="DC_rbegin"/>
<constant name="DC_Endcap_rmax" value="DC_rend"/>
<constant name="DC_construct_wire" value="0"/>
<constant name="DC_layer_width" value="18*mm"/>
</define>
<limits>
<limitset name="DC_limits">
<limit name="step_length_max" particles="*" value="0.1" unit="mm" />
</limitset>
</limits>
<regions>
<region name="DriftChamberRegion">
</region>
</regions>
<detectors>
<detector id="DetID_DC" name="DriftChamber" type="DriftChamber" readout="DriftChamberHitsCollection" vis="DCVis" sensitive="true" limits="DC_limits">
<material name="Air"/>
<chamber id="0" material="GasHe_90Isob_10"/>
<side material="CarbonFiber"/>
<envelope vis="SeeThrough">
<shape type="BooleanShape" operation="Union" material="Air">
<shape type="Tube" rmin="DC_rbegin" rmax="DC_rend" dz="DC_half_length" />
</shape>
</envelope>
<module id="0" name="SignalWire" type="Tube" rmin="0*mm" rmax="0.01*mm" vis="RedVis">
<tubs name="W" type="Tube" rmin="0*mm" rmax="0.007*mm" material="Tungsten"/>
<tubs name="Au" type="Tube" rmin="0.007*mm" rmax="0.01*mm" material="Gold"/>
</module>
<module id="1" name="FieldWire" type="Tube" rmin="0*mm" rmax="0.02*mm" vis="GreenVis">
<tubs name="Al" type="Tube" rmin="0*mm" rmax="0.017*mm" material="Aluminum"/>
<tubs name="Ag" type="Tube" rmin="0.017*mm" rmax="0.02*mm" material="Silver"/>
</module>
<type_flags type="DetType_TRACKER + DetType_BARREL + DetType_GASEOUS + DetType_WIRE"/>
<!-- Use cm as unit if you want to use Pandora for reconstruction -->
<sensitive type="SimpleDriftChamber"/>
</detector>
</detectors>
<readouts>
<readout name="DriftChamberHitsCollection">
<segmentation type="GridDriftChamber" cell_size="DC_cell_width" detector_length="Gas_length" identifier_phi="cellID" layerID="layer" DC_rbegin="DC_rbegin" DC_rend="DC_rend" layer_width="DC_layer_width"/>
<id>system:5,layer:7:9,chamber:8,cellID:32:16</id>
</readout>
</readouts>
</lccdd>
<?xml version="1.0" encoding="UTF-8"?>
<lccdd>
<info name="DriftChamber"
title="Test with Drift Chamber"
author="Tao Lin"
url="http://github.com/cepc/CEPCSW"
status="development"
version="v0">
<comment>Test with Drift Chamber</comment>
</info>
<define>
<constant name="DC_layer_number" value="66"/>
<constant name="Alpha" value="12*deg"/>
<constant name="Gas_radius_min" value="DC_rbegin+DC_inner_wall_thickness+DC_safe_distance"/>
<constant name="Gas_half_length" value="DC_half_length-DC_Endcap_dz-DC_safe_distance"/>
<constant name="Gas_length" value="Gas_half_length*2"/>
<constant name="DC_cell_width" value="18*mm"/>
<constant name="DC_inner_wall_radius_min" value="DC_rbegin"/>
<constant name="DC_inner_wall_radius_max" value="DC_rbegin+DC_inner_wall_thickness"/>
<constant name="DC_Endcap_rmin" value="DC_rbegin"/>
<constant name="DC_Endcap_rmax" value="DC_rend"/>
<constant name="DC_construct_wire" value="0"/>
<constant name="DC_layer_width" value="18*mm"/>
</define>
<limits>
<limitset name="DC_limits">
<limit name="step_length_max" particles="*" value="0.1" unit="mm" />
</limitset>
</limits>
<regions>
<region name="DriftChamberRegion">
</region>
</regions>
<detectors>
<detector id="DetID_DC" name="DriftChamber" type="DriftChamber" readout="DriftChamberHitsCollection" vis="DCVis" sensitive="true" limits="DC_limits">
<material name="Air"/>
<chamber id="0" material="GasHe_90Isob_10"/>
<side material="CarbonFiber"/>
<envelope vis="SeeThrough">
<shape type="BooleanShape" operation="Union" material="Air">
<shape type="Tube" rmin="DC_rbegin" rmax="DC_rend" dz="DC_half_length" />
</shape>
</envelope>
<module id="0" name="SignalWire" type="Tube" rmin="0*mm" rmax="0.01*mm" vis="RedVis">
<tubs name="W" type="Tube" rmin="0*mm" rmax="0.007*mm" material="Tungsten"/>
<tubs name="Au" type="Tube" rmin="0.007*mm" rmax="0.01*mm" material="Gold"/>
</module>
<module id="1" name="FieldWire" type="Tube" rmin="0*mm" rmax="0.03*mm" vis="GreenVis">
<tubs name="Al" type="Tube" rmin="0*mm" rmax="0.027*mm" material="Aluminum"/>
<tubs name="Ag" type="Tube" rmin="0.027*mm" rmax="0.03*mm" material="Silver"/>
</module>
<type_flags type="DetType_TRACKER + DetType_BARREL + DetType_GASEOUS + DetType_WIRE"/>
<!-- Use cm as unit if you want to use Pandora for reconstruction -->
<sensitive type="SimpleDriftChamber"/>
</detector>
</detectors>
<readouts>
<readout name="DriftChamberHitsCollection">
<segmentation type="GridDriftChamber" cell_size="DC_cell_width" detector_length="Gas_length" identifier_phi="cellID" layerID="layer" DC_rbegin="DC_rbegin" DC_rend="DC_rend" layer_width="DC_layer_width"/>
<id>system:5,layer:7:9,chamber:8,cellID:32:16</id>
</readout>
</readouts>
</lccdd>
<?xml version="1.0" encoding="UTF-8"?>
<lccdd>
<info name="DriftChamber"
title="Test with Drift Chamber"
author="Tao Lin"
url="http://github.com/cepc/CEPCSW"
status="development"
version="v0">
<comment>Test with Drift Chamber</comment>
</info>
<define>
<!-- SDT -->
<constant name="SDT_radius_min" value="DC_inner_radius"/>
<constant name="SDT_radius_max" value="DC_outer_radius"/>
<constant name="SDT_half_length" value="MainTracker_half_length"/>
<constant name="DC_length" value="DC_half_length*2"/>
<constant name="SDT_length" value="SDT_half_length*2"/>
<constant name="SDT_chamber_radius_min" value="DC_chamber_layer_rbegin-DC_safe_distance"/>
<constant name="SDT_chamber_radius_max" value="DC_chamber_layer_rend+DC_chamber_safe_distance+DC_safe_distance"/>
<constant name="SDT_chamber_half_length" value="DC_half_length"/>
<constant name="SDT_chamber_layer_width" value="10*mm"/>
<constant name="SDT_chamber_cell_width" value="10*mm"/>
<constant name="Alpha" value="12*deg"/>
<constant name="SDT_chamber_inner_wall_radius_min" value="SDT_chamber_radius_min-SDT_inner_wall_thickness"/>
<constant name="SDT_chamber_inner_wall_radius_max" value="SDT_chamber_radius_min"/>
<constant name="SDT_chamber_outer_wall_radius_min" value="SDT_chamber_radius_max"/>
<constant name="SDT_chamber_outer_wall_radius_max" value="SDT_chamber_radius_max+SDT_outer_wall_thickness"/>
<constant name="DC_Endcap_rmin" value="SDT_radius_min"/>
<constant name="DC_Endcap_rmax" value="SDT_radius_max"/>
</define>
<limits>
<limitset name="DC_limits">
<limit name="step_length_max" particles="*" value="0.1" unit="mm" />
</limitset>
</limits>
<regions>
<region name="DriftChamberRegion">
<limitsetref name="DC_limits"/>
</region>
</regions>
<detectors>
<detector id="DetID_DC" name="DriftChamber_Stero" type="DriftChamber_Stero" readout="DriftChamberHitsCollection" vis="DCVis" sensitive="true" insideTrackingVolume="true" limits="DC_limits">
<material name="Air"/>
<chamber id="0" material="GasHe_90Isob_10"/>
<side material="CarbonFiber"/>
<envelope vis="SeeThrough">
<shape type="BooleanShape" operation="Union" material="Air">
<shape type="Tube" rmin="SDT_radius_min" rmax="SDT_radius_max" dz="SDT_half_length" />
</shape>
</envelope>
<module id="0" name="SignalWire" type="Tube" rmin="0*mm" rmax="0.01*mm" vis="RedVis">
<tubs name="W" type="Tube" rmin="0*mm" rmax="0.007*mm" material="Tungsten"/>
<tubs name="Au" type="Tube" rmin="0.007*mm" rmax="0.01*mm" material="Gold"/>
</module>
<module id="1" name="FieldWire" type="Tube" rmin="0*mm" rmax="0.02*mm" vis="GreenVis">
<tubs name="Al" type="Tube" rmin="0*mm" rmax="0.017*mm" material="Aluminum"/>
<tubs name="Ag" type="Tube" rmin="0.017*mm" rmax="0.02*mm" material="Silver"/>
</module>
<type_flags type="DetType_TRACKER + DetType_BARREL + DetType_GASEOUS + DetType_WIRE"/>
<!-- Use cm as unit if you want to use Pandora for reconstruction -->
<sensitive type="SimpleDriftChamber"/>
</detector>
</detectors>
<readouts>
<readout name="DriftChamberHitsCollection">
<segmentation type="GridDriftChamber" cell_size="SDT_chamber_cell_width" detector_length="DC_length" identifier_phi="cellID" DC_rbegin="DC_chamber_layer_rbegin" DC_rend="DC_chamber_layer_rend" DC_rmin="SDT_chamber_radius_min" DC_rmax="SDT_chamber_radius_max" safe_distance="DC_safe_distance" layerID="layer" layer_width="SDT_chamber_layer_width"/>
<id>system:5,layer:7:9,chamber:8,cellID:32:16</id>
</readout>
</readouts>
</lccdd>
<?xml version="1.0" encoding="UTF-8"?>
<lccdd xmlns:compact="http://www.lcsim.org/schemas/compact/1.0"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xs:noNamespaceSchemaLocation="http://www.lcsim.org/schemas/compact/1.0/compact.xsd">
<info name="DriftChamber"
title="Test with Drift Chamber"
author="Tao Lin"
url="http://github.com/cepc/CEPCSW"
status="development"
version="v0">
<comment>Test with Drift Chamber</comment>
</info>
<define>
<!-- SDT -->
<constant name="SDT_radius_min" value="DC_inner_radius"/>
<constant name="SDT_radius_max" value="DC_outer_radius"/>
<constant name="SDT_half_length" value="MainTracker_half_length"/>
<constant name="DC_length" value="DC_half_length*2"/>
<constant name="SDT_length" value="SDT_half_length*2"/>
<constant name="SDT_chamber_radius_min" value="DC_chamber_layer_rbegin-DC_safe_distance"/>
<constant name="SDT_chamber_radius_max" value="DC_chamber_layer_rend+DC_safe_distance"/>
<constant name="SDT_chamber_half_length" value="DC_half_length"/>
<constant name="SDT_chamber_layer_width" value="10*mm"/>
<constant name="SDT_chamber_cell_width" value="10*mm"/>
<constant name="Alpha" value="0*deg"/>
<constant name="SDT_chamber_inner_wall_radius_min" value="SDT_chamber_radius_min-SDT_inner_wall_thickness"/>
<constant name="SDT_chamber_inner_wall_radius_max" value="SDT_chamber_radius_min"/>
<constant name="SDT_chamber_outer_wall_radius_min" value="SDT_chamber_radius_max"/>
<constant name="SDT_chamber_outer_wall_radius_max" value="SDT_chamber_radius_max+SDT_outer_wall_thickness"/>
<constant name="DC_Endcap_rmin" value="SDT_radius_min"/>
<constant name="DC_Endcap_rmax" value="SDT_radius_max"/>
</define>
<limits>
<limitset name="DC_limits">
<limit name="step_length_max" particles="*" value="0.1" unit="mm" />
</limitset>
</limits>
<regions>
<region name="DriftChamberRegion">
</region>
</regions>
<detectors>
<detector id="DetID_DC" name="DriftChamber" type="DriftChamber" readout="DriftChamberHitsCollection" vis="DCVis" sensitive="true" region="DriftChamberRegion" limits="DC_limits">
<material name="Air"/>
<chamber id="0" material="GasHe_90Isob_10"/>
<side material="CarbonFiber"/>
<envelope vis="SeeThrough">
<shape type="BooleanShape" operation="Union" material="Air">
<shape type="Tube" rmin="SDT_radius_min" rmax="SDT_radius_max" dz="SDT_half_length" />
</shape>
</envelope>
<module id="0" name="SignalWire" type="Tube" rmin="0*mm" rmax="0.01*mm" vis="RedVis">
<tubs name="W" type="Tube" rmin="0*mm" rmax="0.007*mm" material="Tungsten"/>
<tubs name="Au" type="Tube" rmin="0.007*mm" rmax="0.01*mm" material="Gold"/>
</module>
<module id="1" name="FieldWire" type="Tube" rmin="0*mm" rmax="0.02*mm" vis="GreenVis">
<tubs name="Al" type="Tube" rmin="0*mm" rmax="0.017*mm" material="Aluminum"/>
<tubs name="Ag" type="Tube" rmin="0.017*mm" rmax="0.02*mm" material="Silver"/>
</module>
<type_flags type="DetType_TRACKER + DetType_BARREL + DetType_GASEOUS + DetType_WIRE"/>
<!-- Use cm as unit if you want to use Pandora for reconstruction -->
<sensitive type="SimpleDriftChamber"/>
</detector>
</detectors>
<readouts>
<readout name="DriftChamberHitsCollection">
<segmentation type="GridDriftChamber" cell_size="SDT_chamber_cell_width" detector_length="DC_length" identifier_phi="cellID" DC_rbegin="DC_chamber_layer_rbegin" DC_rend="DC_chamber_layer_rend" DC_rmin="SDT_chamber_radius_min" DC_rmax="SDT_chamber_radius_max" safe_distance="DC_safe_distance" layerID="layer" layer_width="SDT_chamber_layer_width"/>
<!-- <id>system:8,chamber:1,layer:8,cellID:16</id> -->
<id>system:5,layer:7:9,chamber:8,cellID:32:16</id>
</readout>
</readouts>
</lccdd>
<?xml version="1.0" encoding="UTF-8"?>
<lccdd xmlns:compact="http://www.lcsim.org/schemas/compact/1.0"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xs:noNamespaceSchemaLocation="http://www.lcsim.org/schemas/compact/1.0/compact.xsd">
<info name="DriftChamber"
title="Test with Drift Chamber"
author="Tao Lin"
url="http://github.com/cepc/CEPCSW"
status="development"
version="v0">
<comment>Test with Drift Chamber</comment>
</info>
<define>
<!-- SDT -->
<constant name="SDT_radius_min" value="DC_inner_radius"/>
<constant name="SDT_radius_max" value="DC_outer_radius"/>
<constant name="SDT_half_length" value="MainTracker_half_length"/>
<constant name="DC_length" value="DC_half_length*2"/>
<constant name="SDT_length" value="SDT_half_length*2"/>
<constant name="SDT_chamber_radius_min" value="DC_chamber_layer_rbegin-DC_safe_distance"/>
<constant name="SDT_chamber_radius_max" value="DC_chamber_layer_rend+DC_safe_distance"/>
<constant name="SDT_chamber_half_length" value="DC_half_length"/>
<constant name="SDT_chamber_layer_width" value="10*mm"/>
<constant name="SDT_chamber_cell_width" value="10*mm"/>
<constant name="Alpha" value="0*deg"/>
<constant name="SDT_chamber_inner_wall_radius_min" value="SDT_chamber_radius_min-SDT_inner_wall_thickness"/>
<constant name="SDT_chamber_inner_wall_radius_max" value="SDT_chamber_radius_min"/>
<constant name="SDT_chamber_outer_wall_radius_min" value="SDT_chamber_radius_max"/>
<constant name="SDT_chamber_outer_wall_radius_max" value="SDT_chamber_radius_max+SDT_outer_wall_thickness"/>
<constant name="DC_Endcap_rmin" value="SDT_radius_min"/>
<constant name="DC_Endcap_rmax" value="SDT_radius_max"/>
</define>
<limits>
<limitset name="DC_limits">
<limit name="step_length_max" particles="*" value="10" unit="mm" />
</limitset>
</limits>
<regions>
<region name="DriftChamberRegion">
<limitsetref name="DC_limits"/>
</region>
</regions>
<detectors>
<detector id="DetID_DC" name="DriftChamber" type="DriftChamber" readout="DriftChamberHitsCollection" vis="DCVis" sensitive="true" insideTrackingVolume="true" limits="DC_limits">
<material name="Air"/>
<chamber id="0" material="GasHe_90Isob_10"/>
<side material="CarbonFiber"/>
<envelope>
<shape type="BooleanShape" operation="Union" material="Air">
<shape type="Tube" rmin="SDT_radius_min" rmax="SDT_radius_max" dz="SDT_half_length" />
</shape>
</envelope>
<module id="0" name="SignalWire" type="Tube" rmin="0*mm" rmax="0.01*mm" vis="RedVis">
<tubs name="W" type="Tube" rmin="0*mm" rmax="0.007*mm" material="Tungsten"/>
<tubs name="Au" type="Tube" rmin="0.007*mm" rmax="0.01*mm" material="Gold"/>
</module>
<module id="1" name="FieldWire" type="Tube" rmin="0*mm" rmax="0.02*mm" vis="GreenVis">
<tubs name="Al" type="Tube" rmin="0*mm" rmax="0.017*mm" material="Aluminum"/>
<tubs name="Ag" type="Tube" rmin="0.017*mm" rmax="0.02*mm" material="Silver"/>
</module>
<type_flags type="DetType_TRACKER + DetType_BARREL + DetType_GASEOUS + DetType_WIRE"/>
<!-- Use cm as unit if you want to use Pandora for reconstruction -->
<sensitive type="SimpleDriftChamber"/>
</detector>
</detectors>
<readouts>
<readout name="DriftChamberHitsCollection">
<segmentation type="GridDriftChamber" cell_size="SDT_chamber_cell_width" detector_length="DC_length" identifier_phi="cellID" DC_rbegin="DC_chamber_layer_rbegin" DC_rend="DC_chamber_layer_rend" DC_rmin="SDT_chamber_radius_min" DC_rmax="SDT_chamber_radius_max" safe_distance="DC_safe_distance" layerID="layer" layer_width="SDT_chamber_layer_width"/>
<!-- <id>system:8,chamber:1,layer:8,cellID:16</id> -->
<id>system:5,layer:7:9,chamber:8,cellID:32:16</id>
</readout>
</readouts>
</lccdd>
<?xml version="1.0" encoding="UTF-8"?>
<lccdd>
<define>
<constant name="ecalbarrel_inner_radius" value="Ecal_barrel_inner_radius"/>
<constant name="ecalbarrel_outer_radius" value="Ecal_barrel_outer_radius"/>
<!--<constant name="ecalbarrel_thickness" value="Ecal_barrel_thickness"/>-->
<constant name="ecalbarrel_thickness" value="28.5*cm"/>
<constant name="ecalbarrel_zlength" value="Ecal_barrel_half_length*2"/>
<constant name="Nmodule" value="32"/>
<constant name="Nblock_z" value="15"/>
<constant name="module_rotation" value="12*degree"/>
<constant name="crystal_r" value="4.1*cm"/>
<constant name="crystal_phi" value="1*cm"/>
<constant name="crystal_z_barrel" value="1*cm"/>
<constant name="esr_thickness_barrel" value="0.1*mm"/>
<constant name="sipm_r" value="0.8*mm"/>
<constant name="sipm_phi" value="3*mm"/>
<constant name="sipm_z_barrel" value="3*mm"/>
<constant name="pcb_thickness_barrel" value="2.2*mm"/>
<constant name="cu_thickness_barrel" value="1*mm"/>
<constant name="fibre_thickness_barrel" value="0.1*mm"/>
<constant name="collection_width" value="300*mm"/>
<constant name="collection_thickness" value="10*mm"/>
<constant name="boundary_safety_barrel" value="1*nm"/>
</define>
<regions>
<region name="EcalBarrelRegion">
</region>
</regions>
<detectors>
<detector id="DetID_ECAL"
name="EcalBarrel"
type="CRDEcalBarrel_Short_v02"
readout="EcalBarrelCollection"
vis="Invisible"
sensitive="true"
region="EcalBarrelRegion">
<!-- Use cm as unit if you want to use Pandora for reconstruction -->
<material name="G4_BGO"/>
</detector>
</detectors>
<readouts>
<readout name="EcalBarrelCollection">
<segmentation type="NoSegmentation"/>
<!--segmentation type="CartesianGridXYZ"
grid_size_x="1*cm"
grid_size_y="1*cm"
grid_size_z="1*cm"/-->
<id>system:5,module:5,stave:4,layer:5,phi:6,z:6</id>
</readout>
</readouts>
</lccdd>