diff --git a/CMakeLists.txt b/CMakeLists.txt index efcc5b6b8e4578448f3cb87a1f1df0f91d8db012..4ece9e6f2354abaffca924fd075bdcce7eed1de0 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -27,6 +27,7 @@ if(NOT CMAKE_CXX_STANDARD MATCHES "14|17") message(FATAL_ERROR "Unsupported C++ standard: ${CMAKE_CXX_STANDARD}") endif() +list(PREPEND CMAKE_MODULE_PATH "${PROJECT_SOURCE_DIR}/cmake") # (Find*.cmake) include(cmake/CEPCSWDependencies.cmake) add_subdirectory(Analysis) diff --git a/Detector/DetCEPCv4/CMakeLists.txt b/Detector/DetCEPCv4/CMakeLists.txt index af544b5a525f85518960a57f679f8d0923a442f7..c273799ff5c77a71140dafd9ba011b56a4b28f15 100644 --- a/Detector/DetCEPCv4/CMakeLists.txt +++ b/Detector/DetCEPCv4/CMakeLists.txt @@ -31,8 +31,11 @@ gaudi_add_module(DetCEPCv4 src/calorimeter/SHcalRpc01_Barrel.cpp src/calorimeter/SHcalRpc01_Endcaps.cpp src/calorimeter/SHcalRpc01_EndcapRing.cpp + src/calorimeter/Yoke05_Barrel.cpp + src/calorimeter/Yoke05_Endcaps.cpp src/other/BoxSupport_o1_v01_geo.cpp src/other/TubeSupport_o1_v01_geo.cpp + src/other/SCoil02_geo.cpp LINK ${DD4hep_COMPONENT_LIBRARIES} ) diff --git a/Detector/DetCEPCv4/compact/Beampipe_o1_v01_01.xml b/Detector/DetCEPCv4/compact/Beampipe_o1_v01_01.xml index a7ce385d21fae40fed2481ed1e541f7123c2d59f..6dd10eac88c04dbc8d619271715e2ae4e55f4f52 100644 --- a/Detector/DetCEPCv4/compact/Beampipe_o1_v01_01.xml +++ b/Detector/DetCEPCv4/compact/Beampipe_o1_v01_01.xml @@ -160,12 +160,12 @@ <type_flags type="DetType_SUPPORT + DetType_BEAMPIPE "/> <section start="TUBE_QD0_Lstar-20*mm" end="TUBE_QD0_Lstar+TUBE_QD0_cryostat_length" - rMin="235.*mm" rMax="250.*mm" + rMin="170.*mm" rMax="185.*mm" material="stainless_steel" name="qd0_cryostat"/> <section start="TUBE_QD0_Lstar-20*mm" end="TUBE_QD0_Lstar+TUBE_QD0_cryostat_length" - rMin="235.*mm" rMax="250.*mm" + rMin="205.*mm" rMax="210.*mm" material="stainless_steel" name="qd0_cryostat_wall"/> @@ -183,7 +183,7 @@ </detector> -<detector name="QD0_support" type="BoxSupport_o1_v01" vis="BeamPipeVis" id="ILDDetID_NOTUSED" reflect="true"> +<detector name="QD0_support" type="TubeSupport_o1_v01" vis="BeamPipeVis" id="ILDDetID_NOTUSED" reflect="true"> <envelope vis="BlueVis"> <shape type="Assembly"/> @@ -191,18 +191,19 @@ <type_flags type="DetType_SUPPORT + DetType_BEAMPIPE "/> - <section start="TUBE_QD0_Lstar+20*mm" end="TUBE_QD0_Lstar+TUBE_QD0_cryostat_length" - rMin="275.*mm" rMax="300*mm" + <section start="TUBE_QD0_Lstar-20*mm" end="TUBE_QD0_Lstar+TUBE_QD0_cryostat_length" + rMin="240.*mm" rMax="310*mm" material="stainless_steel" name="qd0_support"/> - <section start="Ecal_endcap_zmin" end="Ecal_endcap_zmin+Ecal_barrel_thickness" + <!--section start="Ecal_endcap_zmin" end="Ecal_endcap_zmin+Ecal_barrel_thickness" rMin="EcalEndcapRing_outer_radius + 2*env_safety" rMax="EcalEndcap_inner_radius - 2*env_safety" material="stainless_steel" - name="forward_support_tube"/> + name="forward_support_tube"/--> - <section start="top_LHCal_min_z + top_LHCal_thickness+10*mm" end="BeamCal_min_z + top_BeamCal_thickness+4600*mm" - rMin="305*mm" rMax="325*mm" + <!--section start="top_LHCal_min_z + top_LHCal_thickness+10*mm" end="BeamCal_min_z + top_BeamCal_thickness+4600*mm"--> + <section start="top_LHCal_min_z + top_LHCal_thickness+10*mm" end="TUBE_QD0_Lstar-20*mm" + rMin="175*mm" rMax="240*mm" material="stainless_steel" name="forward_support_tube"/> diff --git a/Detector/DetCEPCv4/compact/CepC_v4-onlyTracker.xml b/Detector/DetCEPCv4/compact/CepC_v4-onlyTracker.xml index 7610072d6cd18984b431d1d0837a4e34f65b92a1..bf5aace81f5fd37f6616f77d19d0bf1a29ec2318 100644 --- a/Detector/DetCEPCv4/compact/CepC_v4-onlyTracker.xml +++ b/Detector/DetCEPCv4/compact/CepC_v4-onlyTracker.xml @@ -78,7 +78,7 @@ <fields> <field name="GlobalSolenoid" type="solenoid" inner_field="Field_nominal_value" - outer_field="outerField_nominal_value" + outer_field="Field_outer_nominal_value" zmax="TPC_Ecal_Hcal_barrel_halfZ + Coil_extra_size" outer_radius="Hcal_outer_radius + Coil_thickness/2"> </field> diff --git a/Detector/DetCEPCv4/compact/CepC_v4.xml b/Detector/DetCEPCv4/compact/CepC_v4.xml index 356e5bea0f1a29bc3112ebbc44e6232e5165351d..105a00712d512d1c7788aeece1bde77c6e406608 100644 --- a/Detector/DetCEPCv4/compact/CepC_v4.xml +++ b/Detector/DetCEPCv4/compact/CepC_v4.xml @@ -67,14 +67,14 @@ <include ref="SHcalRpc01_Barrel_01.xml"/> <include ref="SHcalRpc01_Endcaps_01.xml"/> <include ref="SHcalRpc01_EndcapRing_01.xml"/> - <!--include ref="Yoke05_Barrel.xml"/> + <include ref="Yoke05_Barrel.xml"/> <include ref="Yoke05_Endcaps.xml"/> - <include ref="LumiCal.xml"/--> + <!--include ref="LumiCal.xml"/--> <!--include ref="LHCal01.xml"/> <include ref="BeamCal08.xml"/--> - <!--include ref="coil03.xml"/--> + <include ref="coil03.xml"/> <!--include ref="SServices00.xml"/--> <plugins> <plugin name="DD4hepVolumeManager"/> @@ -83,4 +83,20 @@ <!--include ref="Field_Solenoid_Map_s_4.0T.xml"/> <include ref="Field_AntiDID_Map_s.xml"/> <include ref="Field_FwdMagnets_Ideal_1000GeV.xml"/--> + <fields> + <field name="InnerSolenoid" type="solenoid" + inner_field="Field_nominal_value" + outer_field="0" + zmax="Coil_half_length" + inner_radius="Hcal_outer_radius+Coil_thickness/2" + outer_radius="Yoke_barrel_inner_radius"> + </field> + <field name="OuterSolenoid" type="solenoid" + inner_field="0" + outer_field="Field_outer_nominal_value" + zmax="Coil_half_length" + inner_radius="Yoke_barrel_inner_radius" + outer_radius="Yoke_barrel_inner_radius+Field_outer_thickness"> + </field> + </fields> </lccdd> diff --git a/Detector/DetCEPCv4/compact/SHcalRpc01_EndcapRing_01.xml b/Detector/DetCEPCv4/compact/SHcalRpc01_EndcapRing_01.xml index 824b932c8276357fe5373d57c78780f462aca381..ab41b9af64cb63b92de5c198e83f90867caedc78 100644 --- a/Detector/DetCEPCv4/compact/SHcalRpc01_EndcapRing_01.xml +++ b/Detector/DetCEPCv4/compact/SHcalRpc01_EndcapRing_01.xml @@ -9,7 +9,7 @@ <shape type="Box" dx="HcalEndcapRing_outer_radius + 2.0*env_safety" dy="HcalEndcapRing_outer_radius + 2.0*env_safety" dz="HcalEndcapRing_max_z + 2.0*env_safety"/> <shape type="PolyhedraRegular" numsides="Hcal_ring_inner_symmetry" rmin="HcalEndcapRing_inner_radius - env_safety" - rmax="HcalEndcapRing_outer_radius + env_safety" dz="2.0*HcalEndcapRing_max_z + env_safety" material="Air"/> + rmax="HcalEndcapRing_outer_radius*cos(pi/Hcal_ring_outer_symmetry) + env_safety" dz="2.0*HcalEndcapRing_max_z + env_safety" material="Air"/> <rotation x="0" y="0" z="90*deg-180*deg/Hcal_ring_inner_symmetry"/> </shape> <shape type="Box" dx="HcalEndcapRing_outer_radius + 2.0*env_safety" dy="HcalEndcapRing_outer_radius + 2.0*env_safety" diff --git a/Detector/DetCEPCv4/compact/Yoke05_Barrel.xml b/Detector/DetCEPCv4/compact/Yoke05_Barrel.xml index 00c8d26420b532947ee63a14c43542c267b8f352..a742d756fe940d5eaddbca7ce4c62af6cdc735c7 100644 --- a/Detector/DetCEPCv4/compact/Yoke05_Barrel.xml +++ b/Detector/DetCEPCv4/compact/Yoke05_Barrel.xml @@ -1,13 +1,11 @@ <!-- comment>Calorimeters</comment --> <lccdd> <detectors> - <detector name="YokeBarrel" type="Yoke05_Barrel" id="ILDDetID_YOKE" readout="YokeBarrelCollection" vis="YellowVis" insideTrackingVolume="false" buildType="BUILD_ENVELOPE"> + <detector name="YokeBarrel" type="Yoke05_Barrel" id="ILDDetID_YOKE" readout="MuonBarrelCollection" vis="YellowVis" insideTrackingVolume="false" buildType="BUILD_ENVELOPE"> <envelope vis="ILD_YOKEVis"> <shape type="BooleanShape" operation="Intersection" material="Air" > - <shape type="Box" dx="Yoke_outer_radius + env_safety" dy="Yoke_outer_radius + env_safety" - dz="Yoke_half_length + env_safety"/> <!--Box defined the coordinate system--> - <shape type="PolyhedraRegular" numsides="Yoke_symmetry" rmin="Yoke_inner_radius" - rmax="Yoke_outer_radius" dz="2.0*Yoke_half_length" material = "Air" /> + <shape type="Box" dx="Yoke_outer_radius + env_safety" dy="Yoke_outer_radius + env_safety" dz="Yoke_half_length + env_safety"/> <!--Box defined the coordinate system--> + <shape type="PolyhedraRegular" numsides="Yoke_symmetry" rmin="Yoke_inner_radius" rmax="Yoke_outer_radius" dz="2.0*Yoke_half_length" material = "Air" /> <rotation x="0*deg" y="0*deg" z="90*deg-180*deg/Yoke_symmetry"/> </shape> </envelope> @@ -28,7 +26,7 @@ </detectors> <readouts> - <readout name="YokeBarrelCollection"> + <readout name="MuonBarrelCollection"> <segmentation type="CartesianGridXZ" grid_size_x="Yoke_cells_size" grid_size_z="Yoke_cells_size"/> <id>system:5,module:3,stave:4,tower:3,layer:6,x:32:-16,z:-16</id> </readout> diff --git a/Detector/DetCEPCv4/compact/Yoke05_Endcaps.xml b/Detector/DetCEPCv4/compact/Yoke05_Endcaps.xml index 6115d54d883e03bb70002cba6ae92bd9314621cd..74b85fdd0b2b37da1c03715a33397dfd0c10220f 100644 --- a/Detector/DetCEPCv4/compact/Yoke05_Endcaps.xml +++ b/Detector/DetCEPCv4/compact/Yoke05_Endcaps.xml @@ -1,8 +1,7 @@ <!-- comment>Calorimeters</comment --> <lccdd> <detectors> - <detector name="YokeEndcap" type="Yoke05_Endcaps" id="ILDDetID_YOKE_ENDCAP" readout="YokeEndcapsCollection" vis="YellowVis" insideTrackingVolume="false" > - + <detector name="YokeEndcap" type="Yoke05_Endcaps" id="ILDDetID_YOKE_ENDCAP" readout="MuonEndcapsCollection" vis="YellowVis" insideTrackingVolume="false" > <envelope vis="ILD_YOKEVis"> <shape type="BooleanShape" operation="Subtraction" material="Air"> <shape type="BooleanShape" operation="Subtraction" material="Air"> @@ -16,7 +15,7 @@ <shape type="Box" dx="YokeEndcap_outer_radius + 1.5*env_safety" dy="YokeEndcap_outer_radius + 1.5*env_safety" dz="YokeEndcapPlug_min_z - env_safety"/> </shape> - <shape type="PolyhedraRegular" numsides="YokeEndcapPlug_symmetry" rmin="YokeEndcapPlug_outer_radius + env_safety" + <shape type="PolyhedraRegular" numsides="YokeEndcapPlug_symmetry" rmin="YokeEndcapPlug_outer_radius*cos(pi/Hcal_ring_outer_symmetry) + env_safety" rmax="YokeEndcap_outer_radius + 2.0*env_safety" dz="2.*YokeEndcap_min_z - env_safety" /> <rotation x="0*deg" y="0*deg" z="90*deg-180*deg/YokeEndcapPlug_symmetry"/> </shape> @@ -24,7 +23,7 @@ <type_flags type=" DetType_CALORIMETER + DetType_ENDCAP + DetType_MUON " /> - <dimensions numsides="12" rmin="Yoke_inner_radius" z="Yoke_barrel_halfZ" /> + <dimensions numsides="Yoke_symmetry" rmin="Yoke_inner_radius" z="Yoke_barrel_halfZ" /> <material name="Iron"/> <layer repeat="12" vis="SeeThrough"> <slice material = "Air" thickness = "15.0*mm" vis="YellowVis" /> @@ -35,7 +34,7 @@ </detectors> <readouts> - <readout name="YokeEndcapsCollection"> + <readout name="MuonEndcapsCollection"> <segmentation type="CartesianGridXY" grid_size_x="Yoke_cells_size" grid_size_y="Yoke_cells_size"/> <id>system:5,module:3,stave:4,tower:3,layer:6,x:32:-16,y:-16</id> </readout> diff --git a/Detector/DetCEPCv4/compact/coil03.xml b/Detector/DetCEPCv4/compact/coil03.xml index 3f176d2827f53c0cab3790f2c0d5dc0e494a94fd..1714b455ed9e32198a57890bae6ac28141d75c81 100644 --- a/Detector/DetCEPCv4/compact/coil03.xml +++ b/Detector/DetCEPCv4/compact/coil03.xml @@ -2,29 +2,29 @@ Coil parameters for ILD_o1_v5 --> <lccdd> -<detectors> - -<detector name="Coil" type="SCoil02" vis="CoilVis" id="ILDDetID_COIL" insideTrackingVolume="false" sensitive="no"> - + <detectors> + <detector name="Coil" type="SCoil02" vis="ILD_COILVis" id="ILDDetID_COIL" insideTrackingVolume="false" readout="COILCollection"> <!-- fg: taken from SCoil02.cc::PreLoadScriptAction() : there the variable Hcal_R_max was used, which was set from Hcal_module_radius in the SHcal driver - here we simply use the value Hcal_outer_radius defined in ILD_l1_v01 -> now (03/2015) done in main compact file ILD_l1_v01.xml --> - - <envelope vis="ILD_COILVis"> - <shape type="Tube" rmin="Coil_inner_radius" rmax="Coil_outer_radius" - dz="Coil_half_length" material="Air"/> - </envelope> - - <type_flags type=" DetType_SUPPORT + DetType_COIL " /> - - <!--fg: for now only a simple aluminum cylinder is created inside the envelope --> - <tube rmin="Coil_inner_radius+env_safety" rmax="Coil_outer_radius-env_safety" - dz="Coil_half_length-env_safety" material="G4_Al"/> - -</detector> - -</detectors> + <envelope vis="SeeThrough"> + <shape type="Tube" rmin="Coil_inner_radius" rmax="Coil_outer_radius" dz="Coil_half_length" material="Air"/> + </envelope> + + <type_flags type=" DetType_SUPPORT + DetType_COIL " /> + + <!--fg: for now only a simple aluminum cylinder is created inside the envelope --> + <tube rmin="Coil_inner_radius" rmax="Coil_outer_radius" dz="Coil_half_length" material="G4_Al"/> + + </detector> + </detectors> + + <readouts> + <readout name="COILCollection"> + <id>system:5,side:-2,layer:9,module:8,sensor:8,barrelside:-2</id> + </readout> + </readouts> </lccdd> diff --git a/Detector/DetCEPCv4/compact/envelope_defs.xml b/Detector/DetCEPCv4/compact/envelope_defs.xml index 5b900a1b04eb2078bbab7e3eca2d67e4a1474bef..0c6db07312a2a10377732356d2033892c35f78f3 100644 --- a/Detector/DetCEPCv4/compact/envelope_defs.xml +++ b/Detector/DetCEPCv4/compact/envelope_defs.xml @@ -94,7 +94,7 @@ <constant name="Hcal_inner_radius" value="Ecal_outer_radius+Hcal_Ecal_gap"/> <!--constant name="Hcal_outer_radius" value="(Hcal_inner_radius+Hcal_barrel_thickness)/cos(pi/Hcal_outer_symmetry)"/--> <!-- cos(pi/16) --> - <constant name="Hcal_outer_radius" value="3144.43*mm"/> + <constant name="Hcal_outer_radius" value="3144.43*mm + 0.00244676*mm"/> <constant name="Hcal_half_length" value="TPC_Ecal_Hcal_barrel_halfZ"/> <constant name="Hcal_inner_symmetry" value="Ecal_Hcal_symmetry"/> @@ -120,7 +120,8 @@ <constant name="Coil_outer_radius" value="Hcal_outer_radius+Hcal_Coil_additional_gap+Coil_thickness"/> <constant name="Coil_half_length" value="TPC_Ecal_Hcal_barrel_halfZ+Coil_extra_size"/> - <constant name="Yoke_inner_radius" value="Coil_outer_radius+top_Hcal_Yoke_gap"/> + <!--constant name="Yoke_inner_radius" value="Hcal_outer_radius+top_Hcal_Yoke_gap"/--><!--two ways to obtain Yoke_inner_radius--> + <constant name="Yoke_inner_radius" value="Coil_outer_radius+Coil_Yoke_radial_clearance"/> <constant name="Yoke_outer_radius" value="Yoke_inner_radius+top_Yoke_thickness"/> <constant name="Yoke_half_length" value="top_Yoke_half_length"/> <constant name="Yoke_symmetry" value="top_Yoke_symmetry"/> diff --git a/Detector/DetCEPCv4/compact/top_defs.xml b/Detector/DetCEPCv4/compact/top_defs.xml index 6b09c8a30df471c5354ff6227666c350894fe20d..021f80a852b9e20e8cd3fa1aad6b8a04f1882f2c 100644 --- a/Detector/DetCEPCv4/compact/top_defs.xml +++ b/Detector/DetCEPCv4/compact/top_defs.xml @@ -10,8 +10,8 @@ <constant name="CepC_Main_Crossing_Angle" value="33*mrad"/> <!-- the field inside and outside the solenoid --> - <constant name="outerField_nominal_value" value="-1.33716*tesla"/> - + <constant name="Field_outer_nominal_value" value="-1.33716*tesla"/> + <constant name="Field_outer_thickness" value="2550*mm"/> <!-- VXD --> <constant name="top_VXD_inner_radius" value="15*mm "/> @@ -58,7 +58,7 @@ <constant name="Ecal_EC_Ring_gap" value="10*mm"/> <!-- HCAL --> - <constant name="Hcal_barrel_thickness" value="1086.43*mm"/> + <!--constant name="Hcal_barrel_thickness" value="1086.43*mm"/--> <constant name="Hcal_Coil_additional_gap" value="29.5*mm"/> <!--constant name="Hcal_outer_symmetry" value="16"/--> <constant name="Hcal_outer_symmetry" value="8"/> @@ -81,8 +81,9 @@ <constant name="top_Yoke_inner_radius" value="4424.0*mm"/> <constant name="top_Yoke_outer_radius" value="7725.0*mm"/> --> - <constant name="top_Hcal_Yoke_gap" value="300*mm"/> - <constant name="top_Yoke_thickness" value="2550*mm"/> + <constant name="Coil_Yoke_radial_clearance" value="250*mm"/> + <constant name="top_Hcal_Yoke_gap" value="Hcal_Coil_additional_gap+Coil_thickness+Coil_Yoke_radial_clearance"/> + <constant name="top_Yoke_thickness" value="3241*mm"/> <constant name="top_Yoke_half_length" value="4047.0*mm"/> <constant name="Yoke_Z_start_endcaps" value="4072.0*mm"/> diff --git a/Detector/DetCEPCv4/compact/yoke_defs.xml b/Detector/DetCEPCv4/compact/yoke_defs.xml index 59672a5a558a68871b9693ab6504643de54342a4..f299a2820ab91fb5b26e13fd947a4d6c57ec64b7 100644 --- a/Detector/DetCEPCv4/compact/yoke_defs.xml +++ b/Detector/DetCEPCv4/compact/yoke_defs.xml @@ -1,6 +1,7 @@ <define> <constant name="Yoke_cells_size" value="30*mm"/> <constant name="Yoke_barrel_inner_radius" value="Yoke_inner_radius"/> + <constant name="Hcal_Yoke_plug_gap" value="45*mm"/> </define> diff --git a/Detector/DetCEPCv4/src/calorimeter/SHcalRpc01_Endcaps.cpp b/Detector/DetCEPCv4/src/calorimeter/SHcalRpc01_Endcaps.cpp index abe42b6588278d3ba043656bd109f89922693527..e55eb4722038d9f9879659d71f407b0e79313df1 100644 --- a/Detector/DetCEPCv4/src/calorimeter/SHcalRpc01_Endcaps.cpp +++ b/Detector/DetCEPCv4/src/calorimeter/SHcalRpc01_Endcaps.cpp @@ -82,6 +82,7 @@ static Ref_t create_detector(Detector& theDetector, xml_h element, SensitiveDete double Hcal_stave_gaps = theDetector.constant<double>("Hcal_stave_gaps"); int Hcal_nlayers = theDetector.constant<int>("Hcal_endcap_nlayers"); double Hcal_start_z = theDetector.constant<double>("Hcal_endcap_zmin"); + double Hcal_end_z = theDetector.constant<double>("HcalEndcap_max_z"); double Hcal_back_plate_thickness = theDetector.constant<double>("Hcal_back_plate_thickness"); double Hcal_lateral_plate_thickness = theDetector.constant<double>("Hcal_lateral_structure_thickness"); double Hcal_endcap_center_box_size = theDetector.constant<double>("Hcal_endcap_center_box_size"); @@ -102,6 +103,11 @@ static Ref_t create_detector(Detector& theDetector, xml_h element, SensitiveDete int numSide = Hcal_endcap_outer_symmetry; double Hcal_endcap_thickness = Hcal_nlayers*layerThickness + Hcal_back_plate_thickness; double Hcal_endcap_rmax = Hcal_outer_radius * cos(pi/numSide); + cout << " module thickness = " << Hcal_endcap_thickness << endl; + if(Hcal_end_z!=Hcal_start_z+Hcal_endcap_thickness){ + cout << "Hcal_end_z input != Hcal_start_z + Hcal_endcap_thickness: " << "Hcal_end_z=" << Hcal_end_z + << " but Hcal_start_z=" << Hcal_start_z << " and calculate as " << Hcal_start_z+Hcal_endcap_thickness << endl; + } LayeredCalorimeterData* caloData = new LayeredCalorimeterData; caloData->layoutType = LayeredCalorimeterData::EndcapLayout; diff --git a/Detector/DetCEPCv4/src/calorimeter/Yoke05_Barrel.cpp b/Detector/DetCEPCv4/src/calorimeter/Yoke05_Barrel.cpp new file mode 100644 index 0000000000000000000000000000000000000000..7eac4ee59c8628447dd56d335e800d47cf2b5b9a --- /dev/null +++ b/Detector/DetCEPCv4/src/calorimeter/Yoke05_Barrel.cpp @@ -0,0 +1,429 @@ +//==================================================================== +// lcgeo - LC detector models in DD4hep +//-------------------------------------------------------------------- +// DD4hep Geometry driver for YokeBarrel +// Ported from Mokka +//-------------------------------------------------------------------- +// S.Lu, DESY +// $Id$ +//==================================================================== +// ********************************************************* +// * Mokka * +// * -- A Detailed Geant 4 Simulation for the ILC -- * +// * * +// * polywww.in2p3.fr/geant4/tesla/www/mokka/mokka.html * +// ********************************************************* +// +// $Id$ +// $Name: $ +// +// History: +// - first implementation P. Mora de Freitas (May 2001) +// - selectable symmetry, self-scaling, removed pole tips +// - Adrian Vogel, 2006-03-17 +// - muon system plus +// instrumented pole tip back for TESLA models +// - Predrag Krstonosic , 2006-08-30 +// - added barrelEndcapGap, gear parameters, made barrel +// and endcap same thickness, made plug insensitive, +// - F.Gaede, DESY 2008-10-04 +// + +#include "DD4hep/DetFactoryHelper.h" +#include "DD4hep/DetType.h" +#include "XML/Layering.h" +#include "TGeoTrd2.h" +#include "XML/Utilities.h" +#include "DDRec/DetectorData.h" + +using namespace std; + +using dd4hep::BUILD_ENVELOPE; +using dd4hep::Box; +using dd4hep::DetElement; +using dd4hep::DetType; +using dd4hep::Detector; +using dd4hep::Layering; +using dd4hep::Material; +using dd4hep::PlacedVolume; +using dd4hep::PolyhedraRegular; +using dd4hep::Position; +using dd4hep::Readout; +using dd4hep::Ref_t; +using dd4hep::Rotation3D; +using dd4hep::RotationZYX; +using dd4hep::Segmentation; +using dd4hep::SensitiveDetector; +using dd4hep::Transform3D; +using dd4hep::Volume; +using dd4hep::_toString; + +using dd4hep::rec::LayeredCalorimeterData; + +#define VERBOSE 1 + +// workaround for DD4hep v00-14 (and older) +#ifndef DD4HEP_VERSION_GE +#define DD4HEP_VERSION_GE(a,b) 0 +#endif + +static Ref_t create_detector(Detector& theDetector, xml_h element, SensitiveDetector sens) { + static double tolerance = 0e0; + + xml_det_t x_det = element; + string det_name = x_det.nameStr(); + Layering layering (element); + + xml_comp_t x_dim = x_det.dimensions(); + int nsides = x_dim.numsides(); + + Material air = theDetector.air(); + + xml_comp_t x_staves = x_det.staves(); + Material yokeMaterial = theDetector.material(x_staves.materialStr()); + + //unused: Material env_mat = theDetector.material(x_dim.materialStr()); + + xml_comp_t env_pos = x_det.position(); + xml_comp_t env_rot = x_det.rotation(); + + Position pos(env_pos.x(),env_pos.y(),env_pos.z()); + RotationZYX rotZYX(env_rot.z(),env_rot.y(),env_rot.x()); + + Transform3D tr(rotZYX,pos); + + int det_id = x_det.id(); + DetElement sdet (det_name,det_id); + + // --- create an envelope volume and position it into the world --------------------- + + Volume envelope = dd4hep::xml::createPlacedEnvelope( theDetector, element , sdet ) ; + + dd4hep::xml::setDetectorTypeFlag( element, sdet ) ; + + if( theDetector.buildType() == BUILD_ENVELOPE ) return sdet ; + + //----------------------------------------------------------------------------------- + + sens.setType("calorimeter"); + + +//==================================================================== +// +// Read all the constant from ILD_o1_v05.xml +// Use them to build Yoke05Barrel +// +//==================================================================== + double Yoke_barrel_inner_radius = theDetector.constant<double>("Yoke_barrel_inner_radius"); + //double Yoke_thickness = theDetector.constant<double>("Yoke_thickness"); + //double Yoke_Barrel_Half_Z = theDetector.constant<double>("Yoke_Barrel_Half_Z"); + double Yoke_Z_start_endcaps = theDetector.constant<double>("Yoke_Z_start_endcaps"); + //double Yoke_cells_size = theDetector.constant<double>("Yoke_cells_size"); + + //Database *db = new Database(env.GetDBName()); + //db->exec("SELECT * FROM `yoke`;"); + //db->getTuple(); + ////... Geometry parameters from the environment and from the database + //symmetry = db->fetchInt("symmetry"); + //const G4double rInnerBarrel = + // env.GetParameterAsDouble("Yoke_barrel_inner_radius"); + //const G4double rInnerEndcap = + // env.GetParameterAsDouble("Yoke_endcap_inner_radius"); + //const G4double zStartEndcap = + // env.GetParameterAsDouble("Yoke_Z_start_endcaps"); + // + //db->exec("SELECT * FROM `muon`;"); + //db->getTuple(); + //iron_thickness = db->fetchDouble("iron_thickness"); + //G4double gap_thickness = db->fetchDouble("layer_thickness"); + //number_of_layers = db->fetchInt("number_of_layers"); + //G4double yokeBarrelEndcapGap = db->fetchInt("barrel_endcap_gap"); + //G4double cell_dim_x = db->fetchDouble("cell_size"); + //G4double cell_dim_z = db->fetchDouble("cell_size"); + //G4double chamber_thickness = 10*mm; + + double yokeBarrelEndcapGap = 2.5;// ?? theDetector.constant<double>("barrel_endcap_gap"); //25.0*mm + + +//==================================================================== +// +// general calculated parameters +// +//==================================================================== + + //port from Mokka Yoke05, the following parameters used by Yoke05 + int symmetry = nsides; + double rInnerBarrel = Yoke_barrel_inner_radius; + double zStartEndcap = Yoke_Z_start_endcaps; // has been updated to 4072.0*mm by driver SCoil02 + + //TODO: put all magic numbers into ILD_o1_v05.xml file. + double gap_thickness = 4.0; + double iron_thickness = 10.0; //10.0 cm + int number_of_layers = 10; + + //... Barrel parameters: + //... tolerance 1 mm + double yokeBarrelThickness = gap_thickness + + number_of_layers*(iron_thickness + gap_thickness) + + 3*(5.6*iron_thickness + gap_thickness) + + 0.1; // the tolerance 1 mm + + double rOuterBarrel = rInnerBarrel + yokeBarrelThickness; + double z_halfBarrel = zStartEndcap - yokeBarrelEndcapGap; + + + // In this release the number of modules is fixed to 3 + double Yoke_Barrel_module_dim_z = 2.0*(zStartEndcap-yokeBarrelEndcapGap)/3.0 ; + + //double Yoke_cell_dim_x = Yoke_cells_size; + //double Yoke_cell_dim_z = Yoke_Barrel_module_dim_z / floor (Yoke_Barrel_module_dim_z/Yoke_cell_dim_x); + + cout<<" Build the yoke within this dimension "<<endl; + cout << " ...Yoke db: symmetry " << symmetry <<endl; + cout << " ...Yoke db: rInnerBarrel " << rInnerBarrel <<endl; + cout << " ...Yoke db: zStartEndcap " << zStartEndcap <<endl; + + cout << " ...Muon db: iron_thickness " << iron_thickness <<endl; + cout << " ...Muon db: gap_thickness " << gap_thickness <<endl; + cout << " ...Muon db: number_of_layers " << number_of_layers <<endl; + + cout << " ...Muon par: yokeBarrelThickness " << yokeBarrelThickness <<endl; + cout << " ...Muon par: Barrel_half_z " << z_halfBarrel <<endl; + + Readout readout = sens.readout(); + Segmentation seg = readout.segmentation(); + + std::vector<double> cellSizeVector = seg.segmentation()->cellDimensions(0); //Assume uniform cell sizes, provide dummy cellID + double cell_sizeX = cellSizeVector[0]; + double cell_sizeY = cellSizeVector[1]; + + //========== fill data for reconstruction ============================ + LayeredCalorimeterData* caloData = new LayeredCalorimeterData ; + caloData->layoutType = LayeredCalorimeterData::BarrelLayout ; + caloData->inner_symmetry = symmetry ; + caloData->outer_symmetry = symmetry ; + caloData->phi0 = 0 ; // also hardcoded below + + /// extent of the calorimeter in the r-z-plane [ rmin, rmax, zmin, zmax ] in mm. + caloData->extent[0] = rInnerBarrel ; + caloData->extent[1] = rOuterBarrel ; + caloData->extent[2] = 0. ; + caloData->extent[3] = z_halfBarrel ; + + +// ========= Create Yoke Barrel module ==================================== + PolyhedraRegular YokeBarrelSolid( symmetry, M_PI/2.0-M_PI/symmetry, rInnerBarrel, rOuterBarrel, Yoke_Barrel_module_dim_z); + + Volume mod_vol(det_name+"_module", YokeBarrelSolid, yokeMaterial); + //Volume mod_vol(det_name+"_module", YokeBarrelSolid, air); + + mod_vol.setVisAttributes(theDetector.visAttributes(x_det.visStr())); + + +//==================================================================== +// Build chamber volume +//==================================================================== + //double gap_thickness = db->fetchDouble("layer_thickness"); + + //-------------------- start loop over Yoke layers ---------------------- + // Loop over the sets of layer elements in the detector. + + double nRadiationLengths=0.; + double nInteractionLengths=0.; + double thickness_sum=0; + + int l_num = 1; + for(xml_coll_t li(x_det,_U(layer)); li; ++li) { + xml_comp_t x_layer = li; + int repeat = x_layer.repeat(); + + // Loop over number of repeats for this layer. + for (int i=0; i<repeat; i++) { + //if(i>11) continue; + string l_name = _toString(l_num,"layer%d"); + //double l_thickness = layering.layer(l_num-1)->thickness(); // Layer's thickness. + double l_thickness = layering.layer(i)->thickness(); // Layer's thickness. + + //double gap_thickness = l_thickness; + //double iron_thickness = 10.0; //10.0 cm + + double radius_low = rInnerBarrel+ 0.05 + i*gap_thickness + i*iron_thickness; + //rInnerBarrel+ 0.5*mm + i*gap_thickness + i*iron_thickness; + //double radius_mid = radius_low+0.5*gap_thickness; + //double radius_sensitive = radius_mid; + + if( i>=10 ) radius_low = rInnerBarrel + 0.05 + i*gap_thickness + (i+(i-10)*4.6)*iron_thickness; + //{ radius_low = + // rInnerBarrel + 0.5*mm + i*gap_thickness + // + (i+(i-10)*4.6)*iron_thickness; + //radius_mid = radius_low+0.5*gap_thickness; + //radius_sensitive = radius_mid; + //} + + //... safety margines of 0.1 mm for x,y of chambers + //double dx = radius_low*tan(Angle2)-0.1*mm; + //double dy = (zStartEndcap-yokeBarrelEndcapGap)/3.0-0.1*mm; + + double Angle2 = M_PI/symmetry; + double dx = radius_low*tan(Angle2)-0.01; + double dy = (zStartEndcap-yokeBarrelEndcapGap)/3.0-0.01; + //Box ChamberSolid(dx,gap_thickness/2.,dy); + //Volume ChamberLog("muonSci",ChamberSolid,air); + + LayeredCalorimeterData::Layer caloLayer ; + caloLayer.cellSize0 = cell_sizeX; + caloLayer.cellSize1 = cell_sizeY; + + Box ChamberSolid(dx,l_thickness/2.0, dy); + Volume ChamberLog(det_name+"_"+l_name,ChamberSolid,air); + DetElement layer(l_name, det_id); + + ChamberLog.setVisAttributes(theDetector.visAttributes(x_layer.visStr())); + + // Loop over the sublayers or slices for this layer. + int s_num = 1; + double s_pos_y = -(l_thickness / 2); + + + + //-------------------------------------------------------------------------------- + // Build Layer, Sensitive Scintilator in the middle, and Air tolorance at two sides + //-------------------------------------------------------------------------------- + double radiator_thickness = 0.05; // Yoke05 Barrel: No radiator before first sensitive layer. + if ( i>0 ) radiator_thickness = gap_thickness + iron_thickness - l_thickness; + if ( i>=10 ) radiator_thickness = gap_thickness + 5.6*iron_thickness - l_thickness; + + nRadiationLengths = radiator_thickness/(yokeMaterial.radLength()); + nInteractionLengths = radiator_thickness/(yokeMaterial.intLength()); + thickness_sum = radiator_thickness; + + + for(xml_coll_t si(x_layer,_U(slice)); si; ++si) { + xml_comp_t x_slice = si; + string s_name = _toString(s_num,"slice%d"); + double s_thickness = x_slice.thickness(); + Material slice_material = theDetector.material(x_slice.materialStr()); + + s_pos_y += s_thickness/2.; + + double slab_dim_x = dx-tolerance; + double slab_dim_y = s_thickness/2.; + double slab_dim_z = dy-tolerance; + + Box s_box(slab_dim_x,slab_dim_y,slab_dim_z); + Volume s_vol(det_name+"_"+l_name+"_"+s_name,s_box,slice_material); + DetElement slice(layer,s_name,det_id); + + nRadiationLengths += s_thickness/(2.*slice_material.radLength()); + nInteractionLengths += s_thickness/(2.*slice_material.intLength()); + thickness_sum += s_thickness/2; + + if ( x_slice.isSensitive() ) { + s_vol.setSensitiveDetector(sens); + std::cout << " ...Barrel i, position: " << i << " " << radius_low + l_thickness/2.0 + s_pos_y << std::endl; +#if DD4HEP_VERSION_GE( 0, 15 ) + //Store "inner" quantities + caloLayer.inner_nRadiationLengths = nRadiationLengths; + caloLayer.inner_nInteractionLengths = nInteractionLengths; + caloLayer.inner_thickness = thickness_sum; + //Store scintillator thickness + caloLayer.sensitive_thickness = s_thickness; +#endif + //Reset counters to measure "outside" quantitites + nRadiationLengths=0.; + nInteractionLengths=0.; + thickness_sum = 0.; + } + + nRadiationLengths += s_thickness/(2.*slice_material.radLength()); + nInteractionLengths += s_thickness/(2.*slice_material.intLength()); + thickness_sum += s_thickness/2; + + // Set region, limitset, and vis. + s_vol.setAttributes(theDetector,x_slice.regionStr(),x_slice.limitsStr(),x_slice.visStr()); + + Position s_pos(0,s_pos_y,0); // Position of the layer. + PlacedVolume s_phv = ChamberLog.placeVolume(s_vol,s_pos); + slice.setPlacement(s_phv); + + // Increment x position for next slice. + s_pos_y += s_thickness/2.; + + ++s_num; + + } + +#if DD4HEP_VERSION_GE( 0, 15 ) + //Store "outer" quantities + caloLayer.outer_nRadiationLengths = nRadiationLengths; + caloLayer.outer_nInteractionLengths = nInteractionLengths; + caloLayer.outer_thickness = thickness_sum; +#endif + + ++l_num; + + + + double phirot = 0; + + for(int j=0;j<symmetry;j++) + { + double Y = radius_low + l_thickness/2.0; + Position xyzVec(-Y*sin(phirot), Y*cos(phirot), 0); + + RotationZYX rot(phirot,0,0); + Rotation3D rot3D(rot); + + Transform3D tran3D(rot3D,xyzVec); + PlacedVolume layer_phv = mod_vol.placeVolume(ChamberLog,tran3D); + layer_phv.addPhysVolID("layer", l_num).addPhysVolID("stave",j+1); + string stave_name = _toString(j+1,"stave%d"); + string stave_layer_name = stave_name+_toString(l_num,"layer%d"); + DetElement stave(stave_layer_name,det_id);; + stave.setPlacement(layer_phv); + sdet.add(stave); + phirot -= M_PI/symmetry*2.0; + + } + + //----------------------------------------------------------------------------------------- + + + caloLayer.distance = radius_low - radiator_thickness ; + caloLayer.absorberThickness = radiator_thickness ; + + caloData->layers.push_back( caloLayer ) ; + + //----------------------------------------------------------------------------------------- + + } + + } + + +//==================================================================== +// Place Yoke05 Barrel stave module into the world volume +//==================================================================== + + for (int module_id = 1; module_id < 4; module_id++) + { + double module_z_offset = (module_id-2) * Yoke_Barrel_module_dim_z; + + Position mpos(0,0,module_z_offset); + + PlacedVolume m_phv = envelope.placeVolume(mod_vol,mpos); + m_phv.addPhysVolID("module",module_id).addPhysVolID("system", det_id); + m_phv.addPhysVolID("tower", 1);// Not used + string m_name = _toString(module_id,"module%d"); + DetElement sd (m_name,det_id); + sd.setPlacement(m_phv); + sdet.add(sd); + + } + + sdet.addExtension< LayeredCalorimeterData >( caloData ) ; + + return sdet; +} + +DECLARE_DETELEMENT(Yoke05_Barrel,create_detector) diff --git a/Detector/DetCEPCv4/src/calorimeter/Yoke05_Endcaps.cpp b/Detector/DetCEPCv4/src/calorimeter/Yoke05_Endcaps.cpp new file mode 100644 index 0000000000000000000000000000000000000000..d77dc101a79c1e251766b5e52b9907f89bd105e7 --- /dev/null +++ b/Detector/DetCEPCv4/src/calorimeter/Yoke05_Endcaps.cpp @@ -0,0 +1,412 @@ +//==================================================================== +// lcgeo - LC detector models in DD4hep +//-------------------------------------------------------------------- +// DD4hep Geometry driver for YokeEndcaps +// Ported from Mokka +//-------------------------------------------------------------------- +// S.Lu, DESY +// $Id$ +//==================================================================== +// ********************************************************* +// * Mokka * +// * -- A Detailed Geant 4 Simulation for the ILC -- * +// * * +// * polywww.in2p3.fr/geant4/tesla/www/mokka/mokka.html * +// ********************************************************* +// +// $Id$ +// $Name: $ +// +// History: +// - first implementation P. Mora de Freitas (May 2001) +// - selectable symmetry, self-scaling, removed pole tips +// - Adrian Vogel, 2006-03-17 +// - muon system plus +// instrumented pole tip back for TESLA models +// - Predrag Krstonosic , 2006-08-30 +// - added barrelEndcapGap, gear parameters, made barrel +// and endcap same thickness, made plug insensitive, +// - F.Gaede, DESY 2008-10-04 +// + +#include "DD4hep/DetFactoryHelper.h" +#include "DD4hep/DetType.h" +#include "XML/Layering.h" +#include "XML/Utilities.h" +#include "DDRec/DetectorData.h" + +using namespace std; + +using dd4hep::BUILD_ENVELOPE; +using dd4hep::DetElement; +using dd4hep::DetType; +using dd4hep::Detector; +using dd4hep::Layering; +using dd4hep::Material; +using dd4hep::PlacedVolume; +using dd4hep::PolyhedraRegular; +using dd4hep::Position; +using dd4hep::Readout; +using dd4hep::Ref_t; +using dd4hep::Rotation3D; +using dd4hep::RotationZYX; +using dd4hep::Segmentation; +using dd4hep::SensitiveDetector; +using dd4hep::Transform3D; +using dd4hep::Volume; +using dd4hep::_toString; + +using dd4hep::rec::LayeredCalorimeterData; + +#define VERBOSE 1 + +// workaround for DD4hep v00-14 (and older) +#ifndef DD4HEP_VERSION_GE +#define DD4HEP_VERSION_GE(a,b) 0 +#endif + +static Ref_t create_detector(Detector& theDetector, xml_h element, SensitiveDetector sens) { + double tolerance = 0.1; + + xml_det_t x_det = element; + string det_name = x_det.nameStr(); + Layering layering (element); + + xml_comp_t x_dim = x_det.dimensions(); + int nsides = x_dim.numsides(); + + Material air = theDetector.air(); + //unused: Material vacuum = theDetector.vacuum(); + + Material yokeMaterial = theDetector.material(x_det.materialStr());; + + int det_id = x_det.id(); + DetElement sdet (det_name,det_id); + + // --- create an envelope volume and position it into the world --------------------- + + Volume envelope = dd4hep::xml::createPlacedEnvelope( theDetector, element , sdet ) ; + + dd4hep::xml::setDetectorTypeFlag( element, sdet ) ; + + if( theDetector.buildType() == BUILD_ENVELOPE ) return sdet ; + + //----------------------------------------------------------------------------------- + + sens.setType("calorimeter"); + + +//==================================================================== +// +// Read all the constant from ILD_o1_v05.xml +// Use them to build Yoke05Endcaps +// +//==================================================================== + double Yoke_barrel_inner_radius = theDetector.constant<double>("Yoke_barrel_inner_radius"); + double Yoke_endcap_inner_radius = theDetector.constant<double>("Yoke_endcap_inner_radius"); + double Yoke_Z_start_endcaps = theDetector.constant<double>("Yoke_Z_start_endcaps"); + double HCAL_R_max = theDetector.constant<double>("Hcal_outer_radius"); + //double Yoke_cells_size = theDetector.constant<double>("Yoke_cells_size"); + + double yokeBarrelEndcapGap = 2.5;// ?? theDetector.constant<double>("barrel_endcap_gap"); //25.0*mm + + +//==================================================================== +// +// general calculated parameters +// +//==================================================================== + + //port from Mokka Yoke05, the following parameters used by Yoke05 + int symmetry = nsides; + double rInnerBarrel = Yoke_barrel_inner_radius; + double zStartEndcap = Yoke_Z_start_endcaps; // has been updated to 4072.0*mm by driver SCoil02 + + //TODO: put all magic numbers into ILD_o1_v05.xml file. + double gap_thickness = 4.0; + double iron_thickness = 10.0; //10.0 cm + int number_of_layers = 10; + + //... Barrel parameters: + //... tolerance 1 mm + double yokeBarrelThickness = gap_thickness + + number_of_layers*(iron_thickness + gap_thickness) + + 3*(5.6*iron_thickness + gap_thickness) + + 0.1; // the tolerance 1 mm + + double yokeEndcapThickness = number_of_layers*(iron_thickness + gap_thickness) + + 2*(5.6*iron_thickness + gap_thickness); // + gap_thickness; + + double rInnerEndcap = Yoke_endcap_inner_radius; + double rOuterEndcap = rInnerBarrel + yokeBarrelThickness; + double z_halfBarrel = zStartEndcap - yokeBarrelEndcapGap; + + //Port from Mokka: + // Endcap Thickness has no tolerance + // But the placement should shift_middle by -0.05 (0.5*mm) later + double Yoke_Endcap_module_dim_z = yokeEndcapThickness; + + //double Yoke_cell_dim_x = rOuterEndcap*2.0 / floor (rOuterEndcap*2.0/Yoke_cells_size); + //double Yoke_cell_dim_y = Yoke_cell_dim_x; + + cout<<" Build the yoke within this dimension "<<endl; + cout << " ...Yoke db: symmetry " << symmetry <<endl; + cout << " ...Yoke db: rInnerEndcap " << rInnerEndcap <<endl; + cout << " ...Yoke db: rOuterEndcap " << rOuterEndcap <<endl; + cout << " ...Yoke db: zStartEndcap " << zStartEndcap <<endl; + + cout << " ...Muon db: iron_thickness " << iron_thickness <<endl; + cout << " ...Muon db: gap_thickness " << gap_thickness <<endl; + cout << " ...Muon db: number_of_layers " << number_of_layers <<endl; + + cout << " ...Muon par: yokeEndcapThickness " << yokeEndcapThickness <<endl; + cout << " ...Muon par: Barrel_half_z " << z_halfBarrel <<endl; + + Readout readout = sens.readout(); + Segmentation seg = readout.segmentation(); + + std::vector<double> cellSizeVector = seg.segmentation()->cellDimensions(0); //Assume uniform cell sizes, provide dummy cellID + double cell_sizeX = cellSizeVector[0]; + double cell_sizeY = cellSizeVector[1]; + + //========== fill data for reconstruction ============================ + LayeredCalorimeterData* caloData = new LayeredCalorimeterData ; + caloData->layoutType = LayeredCalorimeterData::EndcapLayout ; + caloData->inner_symmetry = symmetry ; + caloData->outer_symmetry = symmetry ; + caloData->phi0 = 0 ; // hardcoded + + /// extent of the calorimeter in the r-z-plane [ rmin, rmax, zmin, zmax ] in mm. + caloData->extent[0] = rInnerEndcap ; + caloData->extent[1] = rOuterEndcap ; + caloData->extent[2] = zStartEndcap ; + caloData->extent[3] = zStartEndcap + Yoke_Endcap_module_dim_z ; + + + + PolyhedraRegular YokeEndcapSolid( symmetry, M_PI/symmetry, rInnerEndcap, rOuterEndcap, Yoke_Endcap_module_dim_z); + + Volume mod_vol(det_name+"_module", YokeEndcapSolid, yokeMaterial); + + mod_vol.setVisAttributes(theDetector.visAttributes(x_det.visStr())); + + +//==================================================================== +// Build chamber volume +//==================================================================== + //double gap_thickness = db->fetchDouble("layer_thickness"); + + //-------------------- start loop over Yoke layers ---------------------- + // Loop over the sets of layer elements in the detector. + + double nRadiationLengths=0.; + double nInteractionLengths=0.; + double thickness_sum=0; + + + int l_num = 1; + for(xml_coll_t li(x_det,_U(layer)); li; ++li) { + xml_comp_t x_layer = li; + int repeat = x_layer.repeat(); + + // Loop over number of repeats for this layer. + for (int i=0; i<repeat; i++) { + //if(i>11) continue; + string l_name = _toString(l_num,"layer%d"); + double l_thickness = layering.layer(i)->thickness(); // Layer's thickness. + + LayeredCalorimeterData::Layer caloLayer ; + caloLayer.cellSize0 = cell_sizeX; + caloLayer.cellSize1 = cell_sizeY; + + PolyhedraRegular ChamberSolid( symmetry, M_PI/symmetry, rInnerEndcap + tolerance, rOuterEndcap - tolerance, l_thickness); + Volume ChamberLog(det_name+"_"+l_name,ChamberSolid,air); + DetElement layer(l_name, det_id); + + ChamberLog.setVisAttributes(theDetector.visAttributes(x_layer.visStr())); + + // Loop over the sublayers or slices for this layer. + int s_num = 1; + double s_pos_z = -(l_thickness / 2); + + double shift_middle = - yokeEndcapThickness/2 - 0.05 //-0.5*mm since PolyhedraRegular from -Yoke_Endcap_module_dim_z/2 to Yoke_Endcap_module_dim_z/2 + + iron_thickness*(i+1) + + (i+0.5)*gap_thickness; + + if( i>= 10){ + shift_middle = - yokeEndcapThickness/2 - 0.05 //0.5*mm + + iron_thickness*(i+1+(i-9)*4.6) + (i+0.5)*gap_thickness; + } + + //-------------------------------------------------------------------------------- + // Build Layer, Sensitive Scintilator in the middle, and Air tolorance at two sides + //-------------------------------------------------------------------------------- + double radiator_thickness = -0.05 + 0.5*gap_thickness + iron_thickness - l_thickness/2.0 ; + if ( i>0 ) radiator_thickness = gap_thickness + iron_thickness - l_thickness ; + if ( i>=10 ) radiator_thickness = gap_thickness + 5.6*iron_thickness - l_thickness ; + + nRadiationLengths = radiator_thickness/(yokeMaterial.radLength()); + nInteractionLengths = radiator_thickness/(yokeMaterial.intLength()); + thickness_sum = radiator_thickness; + + for(xml_coll_t si(x_layer,_U(slice)); si; ++si) { + xml_comp_t x_slice = si; + string s_name = _toString(s_num,"slice%d"); + double s_thickness = x_slice.thickness(); + Material slice_material = theDetector.material(x_slice.materialStr()); + + s_pos_z += s_thickness/2.; + + PolyhedraRegular sliceSolid( symmetry, M_PI/symmetry, rInnerEndcap + tolerance + 0.01, rOuterEndcap - tolerance -0.01, s_thickness); + Volume s_vol(det_name+"_"+l_name+"_"+s_name,sliceSolid,slice_material); + DetElement slice(layer,s_name,det_id); + + nRadiationLengths += s_thickness/(2.*slice_material.radLength()); + nInteractionLengths += s_thickness/(2.*slice_material.intLength()); + thickness_sum += s_thickness/2; + + if ( x_slice.isSensitive() ) { + s_vol.setSensitiveDetector(sens); + cout << " ...Endcap i, position: " << i << " " << zStartEndcap + yokeEndcapThickness/2 + shift_middle + l_thickness/2.0 + s_pos_z << endl; +#if DD4HEP_VERSION_GE( 0, 15 ) + //Store "inner" quantities + caloLayer.inner_nRadiationLengths = nRadiationLengths; + caloLayer.inner_nInteractionLengths = nInteractionLengths; + caloLayer.inner_thickness = thickness_sum; + //Store scintillator thickness + caloLayer.sensitive_thickness = s_thickness; +#endif + //Reset counters to measure "outside" quantitites + nRadiationLengths=0.; + nInteractionLengths=0.; + thickness_sum = 0.; + } + + nRadiationLengths += s_thickness/(2.*slice_material.radLength()); + nInteractionLengths += s_thickness/(2.*slice_material.intLength()); + thickness_sum += s_thickness/2; + + // Set region, limitset, and vis. + s_vol.setAttributes(theDetector,x_slice.regionStr(),x_slice.limitsStr(),x_slice.visStr()); + + Position s_pos(0,0,s_pos_z); // Position of the layer. + PlacedVolume s_phv = ChamberLog.placeVolume(s_vol,s_pos); + slice.setPlacement(s_phv); + + // Increment x position for next slice. + s_pos_z += s_thickness/2.; + + ++s_num; + + } + +#if DD4HEP_VERSION_GE( 0, 15 ) + //Store "outer" quantities + caloLayer.outer_nRadiationLengths = nRadiationLengths; + caloLayer.outer_nInteractionLengths = nInteractionLengths; + caloLayer.outer_thickness = thickness_sum; +#endif + + ++l_num; + + Position xyzVec(0,0,shift_middle); + + PlacedVolume layer_phv = mod_vol.placeVolume(ChamberLog,xyzVec); + layer_phv.addPhysVolID("layer", l_num); + //string stave_name = "stave1"; + string stave_layer_name = "stave1"+_toString(l_num,"layer%d"); + DetElement stave(stave_layer_name,det_id);; + stave.setPlacement(layer_phv); + sdet.add(stave); + + //----------------------------------------------------------------------------------------- + + + caloLayer.distance = zStartEndcap + yokeEndcapThickness/2.0 + shift_middle + - caloLayer.inner_thickness ; + caloLayer.absorberThickness = radiator_thickness ; + + caloData->layers.push_back( caloLayer ) ; + + //----------------------------------------------------------------------------------------- + + } + + } + +//==================================================================== +// Check Yoke05 plug module +//==================================================================== + bool build_plug = false; + double HCAL_z = theDetector.constant<double>("HcalEndcap_max_z");; + double HCAL_plug_gap = theDetector.constant<double>("Hcal_Yoke_plug_gap"); + int Hcal_endcap_outer_symmetry = theDetector.constant<int>("Hcal_endcap_outer_symmetry"); + double plug_thickness = zStartEndcap-HCAL_z-HCAL_plug_gap; + + double rInnerPlug = Yoke_endcap_inner_radius; + double rOuterPlug = HCAL_R_max*cos(dd4hep::pi/16.) *cos(dd4hep::pi/Hcal_endcap_outer_symmetry); + double Yoke_Plug_module_dim_z = plug_thickness; + + // Is there a space to build Yoke plug + if( Yoke_Plug_module_dim_z > 0 ) + { + build_plug = true; + + cout << " ...Plug par: build_plug is true, there is space to build yoke plug" <<endl; + cout << " ...Plug par: HCAL_half_z " << HCAL_z <<endl; + cout << " ...Plug par: HCAL_Plug_Gap " << HCAL_plug_gap <<endl; + cout << " ...Plug par: Plug Thickness " << plug_thickness <<endl; + cout << " ...Plug par: Plug Radius " << rOuterPlug <<endl; + + } + +//==================================================================== +// Place Yoke05 Endcaps module into the world volume +//==================================================================== + + double zEndcap = zStartEndcap + yokeEndcapThickness/2.0 + 0.1; // Need 0.1 (1.0*mm) according to the Mokka Yoke05 driver. + double zPlug = zStartEndcap - plug_thickness/2.0 -0.05; // Need 0.05 (0.5*mm) according to the Mokka Yoke05 driver. + + for(int module_num=0;module_num<2;module_num++) { + + int module_id = ( module_num == 0 ) ? 0:6; + double this_module_z_offset = ( module_id == 0 ) ? - zEndcap : zEndcap; + double this_module_rotY = ( module_id == 0 ) ? M_PI:0; + + Position xyzVec(0,0,this_module_z_offset); + RotationZYX rot(0,this_module_rotY,0); + Rotation3D rot3D(rot); + Transform3D tran3D(rot3D,xyzVec); + + PlacedVolume pv = envelope.placeVolume(mod_vol,tran3D); + pv.addPhysVolID("module",module_id); // z: -/+ 0/6 + + string m_name = _toString(module_id,"module%d"); + DetElement sd (m_name,det_id); + sd.setPlacement(pv); + sdet.add(sd); + + //==================================================================== + // If build_plug is true, Place the plug module into the world volume + //==================================================================== + if(build_plug == true){ + PolyhedraRegular YokePlugSolid( symmetry, M_PI/symmetry, rInnerPlug, rOuterPlug, Yoke_Plug_module_dim_z); + Volume plug_vol(det_name+"_plug", YokePlugSolid, yokeMaterial); + plug_vol.setVisAttributes(theDetector.visAttributes(x_det.visStr())); + + double this_plug_z_offset = ( module_id == 0 ) ? - zPlug : zPlug; + Position plug_pos(0,0,this_plug_z_offset); + PlacedVolume plug_phv = envelope.placeVolume(plug_vol,plug_pos); + string plug_name = _toString(module_id,"plug%d"); + DetElement plug (plug_name,det_id); + plug.setPlacement(plug_phv); + } + + } + + sdet.addExtension< LayeredCalorimeterData >( caloData ) ; + + return sdet; +} + +DECLARE_DETELEMENT(Yoke05_Endcaps,create_detector) diff --git a/Detector/DetCEPCv4/src/other/SCoil02_geo.cpp b/Detector/DetCEPCv4/src/other/SCoil02_geo.cpp new file mode 100644 index 0000000000000000000000000000000000000000..424e6b71ea7d55a95f6b6c5be332a647e32d31c8 --- /dev/null +++ b/Detector/DetCEPCv4/src/other/SCoil02_geo.cpp @@ -0,0 +1,497 @@ +//==================================================================== +// 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) diff --git a/Examples/CMakeLists.txt b/Examples/CMakeLists.txt index 9c00a9eaa78745d8e3ddac59f1377379e7d3db6b..6d37ea639a5354eb09dd50e37a86ce23a596654a 100644 --- a/Examples/CMakeLists.txt +++ b/Examples/CMakeLists.txt @@ -18,6 +18,10 @@ gaudi_add_module(Examples ${podio_LIBRARIES} podio::podioRootIO ) +if (GenFit_FOUND) + target_link_libraries(Examples PUBLIC GenFit::genfit2) +endif() + target_include_directories(Examples PUBLIC $<BUILD_INTERFACE:${CMAKE_CURRENT_LIST_DIR}>/include $<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}>) diff --git a/Simulation/DetSimAna/src/Edm4hepWriterAnaElemTool.cpp b/Simulation/DetSimAna/src/Edm4hepWriterAnaElemTool.cpp index 951ff463723de7ccd5af6004adc45feca0ee41da..2736ac984c15b53f291dfac472a5e3307f823a60 100644 --- a/Simulation/DetSimAna/src/Edm4hepWriterAnaElemTool.cpp +++ b/Simulation/DetSimAna/src/Edm4hepWriterAnaElemTool.cpp @@ -66,6 +66,13 @@ Edm4hepWriterAnaElemTool::EndOfEventAction(const G4Event* anEvent) { auto hcalendcapringcol = m_HcalEndcapRingCol.createAndPut(); auto hcalendcapringcontribcol = m_HcalEndcapRingContributionCol.createAndPut(); + auto coilcols = m_COILCol.createAndPut(); + + auto muonbarrelcol = m_MuonBarrelCol.createAndPut(); + auto muonbarrelcontribcols = m_MuonBarrelContributionCol.createAndPut(); + auto muonendcapscol = m_MuonEndcapsCol.createAndPut(); + auto muonendcapscontribcols = m_MuonEndcapsContributionCol.createAndPut(); + auto driftchamberhitscol = m_DriftChamberHitsCol.createAndPut(); // readout defined in DD4hep @@ -137,6 +144,14 @@ Edm4hepWriterAnaElemTool::EndOfEventAction(const G4Event* anEvent) { } else if (collect->GetName() == "HcalEndcapRingCollection") { calo_col_ptr = hcalendcapringcol; calo_contrib_col_ptr = hcalendcapringcontribcol; + } else if (collect->GetName() == "COILCollection") { + tracker_col_ptr = coilcols; + } else if (collect->GetName() == "MuonBarrelCollection") { + calo_col_ptr = muonbarrelcol; + calo_contrib_col_ptr = muonbarrelcontribcols; + } else if (collect->GetName() == "MuonEndcapsCollection") { + calo_col_ptr = muonendcapscol; + calo_contrib_col_ptr = muonendcapscontribcols; } else if (collect->GetName() == "DriftChamberHitsCollection") { tracker_col_ptr = driftchamberhitscol; } else { diff --git a/Simulation/DetSimAna/src/Edm4hepWriterAnaElemTool.h b/Simulation/DetSimAna/src/Edm4hepWriterAnaElemTool.h index bd71f932377845ca8d56b1ee84d238a6f7ce3e1d..26a1ba48a1ab00a05fa65a4fa011320d1770d988 100644 --- a/Simulation/DetSimAna/src/Edm4hepWriterAnaElemTool.h +++ b/Simulation/DetSimAna/src/Edm4hepWriterAnaElemTool.h @@ -98,6 +98,22 @@ private: "HcalEndcapRingContributionCollection", Gaudi::DataHandle::Writer, this}; + // Coil + DataHandle<edm4hep::SimTrackerHitCollection> m_COILCol{"COILCollection", + Gaudi::DataHandle::Writer, this}; + + // Muon + DataHandle<edm4hep::SimCalorimeterHitCollection> m_MuonBarrelCol{"MuonBarrelCollection", + Gaudi::DataHandle::Writer, this}; + DataHandle<edm4hep::CaloHitContributionCollection> m_MuonBarrelContributionCol{ + "MuonBarrelContributionCollection", + Gaudi::DataHandle::Writer, this}; + DataHandle<edm4hep::SimCalorimeterHitCollection> m_MuonEndcapsCol{"MuonEndcapsCollection", + Gaudi::DataHandle::Writer, this}; + DataHandle<edm4hep::CaloHitContributionCollection> m_MuonEndcapsContributionCol{ + "MuonEndcapsContributionCollection", + Gaudi::DataHandle::Writer, this}; + // Drift Chamber // - DriftChamberHitsCollection DataHandle<edm4hep::SimTrackerHitCollection> m_DriftChamberHitsCol{ diff --git a/cmake/CEPCSWDependencies.cmake b/cmake/CEPCSWDependencies.cmake index 92d8911e3e65a9a6f09548c2aec2b73a082e4c61..78aa0f26d7c8c84bfb581cb6bdebf9c53568e522 100644 --- a/cmake/CEPCSWDependencies.cmake +++ b/cmake/CEPCSWDependencies.cmake @@ -31,3 +31,4 @@ find_package(LCIO REQUIRED) find_package(PandoraSDK REQUIRED) find_package(podio REQUIRED) find_package(ROOT COMPONENTS EG Graf Graf3d Gpad MathCore Net RIO Tree TreePlayer REQUIRED) +find_package(GenFit) diff --git a/cmake/FindGenFit.cmake b/cmake/FindGenFit.cmake new file mode 100644 index 0000000000000000000000000000000000000000..6a3cf181bb45f63a5608fb6cc3eb8692fe1ef89b --- /dev/null +++ b/cmake/FindGenFit.cmake @@ -0,0 +1,55 @@ +# - Try to find GenFit +# Defines: +# +# GenFit_FOUND +# GenFit_INCLUDE_DIRS +# GenFit_LIBRARIES +# +# Imports: +# +# GenFit::genfit2 +# +# Usage of the target instead of the variables is advised + +# Find quietly if already found before +if(DEFINED CACHE{GenFit_INCLUDE_DIRS}) + set(${CMAKE_FIND_PACKAGE_NAME}_FIND_QUIETLY YES) +endif() + +find_path(GenFit_INCLUDE_DIRS NAMES GFGbl.h + HINTS ${GENFIT_ROOT_DIR}/include $ENV{GENFIT_ROOT_DIR}/include + ${GenFit_DIR}/include $ENV{GenFit_DIR}/include + ${CMAKE_PREFIX_PATH}/include +) +find_library(GenFit_LIBRARIES NAMES genfit2 + HINTS $ENV{GENFIT_ROOT_DIR}/lib ${GENFIT_ROOT_DIR}/lib + ${GenFit_DIR}/lib ${GenFit_DIR}/lib64 + $ENV{GenFit_DIR}/lib $ENV{GenFit_DIR}/lib64 + ${CMAKE_PREFIX_PATH}/lib ${CMAKE_PREFIX_PATH}/lib64 +) + +# handle the QUIETLY and REQUIRED arguments and set GENFIT_FOUND to TRUE if +# all listed variables are TRUE +INCLUDE(FindPackageHandleStandardArgs) +FIND_PACKAGE_HANDLE_STANDARD_ARGS(GenFit DEFAULT_MSG GenFit_INCLUDE_DIRS GenFit_LIBRARIES) + +mark_as_advanced(GenFit_FOUND GenFit_INCLUDE_DIRS GenFit_LIBRARIES) + +# Modernisation: create an interface target to link against +if(TARGET GenFit::genfit2) + return() +endif() +if(GenFit_FOUND) + add_library(GenFit::genfit2 IMPORTED INTERFACE) + target_include_directories(GenFit::genfit2 SYSTEM INTERFACE "${GenFit_INCLUDE_DIRS}") + target_link_libraries(GenFit::genfit2 INTERFACE "${GenFit_LIBRARIES}") + + # Display the imported target for the user to know + if(NOT ${CMAKE_FIND_PACKAGE_NAME}_FIND_QUIETLY) + message(STATUS " Import target: GenFit::genfit2") + endif() +endif() + +if(COMMAND __deprecate_var_for_target) + variable_watch(GenFit_INCLUDE_DIRS __deprecate_var_for_target) +endif()