|
| 1 | +/////////////////////////////////////////////////////////////////////////////// |
| 2 | +// File: DDHGCalPassive.cc |
| 3 | +// Description: Geometry factory class for the passive part of a full silicon |
| 4 | +// module |
| 5 | +// Created by Sunanda Banerjee |
| 6 | +/////////////////////////////////////////////////////////////////////////////// |
| 7 | + |
| 8 | +#include <string> |
| 9 | +#include <vector> |
| 10 | +#include <sstream> |
| 11 | + |
| 12 | +#include "DD4hep/DetFactoryHelper.h" |
| 13 | +#include "DataFormats/Math/interface/angle_units.h" |
| 14 | +#include "DetectorDescription/DDCMS/interface/DDPlugins.h" |
| 15 | +#include "DetectorDescription/DDCMS/interface/DDutils.h" |
| 16 | +#include "FWCore/MessageLogger/interface/MessageLogger.h" |
| 17 | +#include "Geometry/HGCalCommonData/interface/HGCalGeomTools.h" |
| 18 | + |
| 19 | +//#define EDM_ML_DEBUG |
| 20 | +using namespace angle_units::operators; |
| 21 | + |
| 22 | +struct HGCalPassive { |
| 23 | + HGCalPassive() { throw cms::Exception("HGCalGeom") << "Wrong initialization to HGCalPassive"; } |
| 24 | + HGCalPassive(cms::DDParsingContext& ctxt, xml_h e) { |
| 25 | + cms::DDNamespace ns(ctxt, e, true); |
| 26 | + cms::DDAlgoArguments args(ctxt, e); |
| 27 | +#ifdef EDM_ML_DEBUG |
| 28 | + edm::LogVerbatim("HGCalGeom") << "DDHGCalPassive: Creating an instance"; |
| 29 | +#endif |
| 30 | + std::string parentName = args.parentName(); |
| 31 | + std::string material = args.value<std::string>("ModuleMaterial"); // Material name for mother volume |
| 32 | + double thick = args.value<double>("Thickness"); // Thickness of the section |
| 33 | + double zMinBlock = args.value<double>("zMinBlock"); // z-position of the first layer |
| 34 | + double moduleThick = args.value<double>("ModuleThick"); // Thickness of the overall module |
| 35 | + std::vector<std::string> tagLayer = |
| 36 | + args.value<std::vector<std::string>>("TagLayer"); // Tag of the layer (to be added to name) |
| 37 | + std::vector<std::string> tagSector = |
| 38 | + args.value<std::vector<std::string>>("TagSector"); // Tag of the sector (to be added to name) |
| 39 | + int parts = args.value<int>("Parts"); // number of parts in units of 30 degree |
| 40 | + double phi0 = args.value<double>("PhiStart"); // Start phi of the first cassette |
| 41 | + double dphi = (2._pi) / tagSector.size(); // delta phi of the cassette |
| 42 | +#ifdef EDM_ML_DEBUG |
| 43 | + edm::LogVerbatim("HGCalGeom") << "DDHGCalPassive: " << tagLayer.size() << " Modules with base name " << parentName |
| 44 | + << " made of " << material << " T " << thick << " Sectors " << tagSector.size() |
| 45 | + << " Parts " << parts << " phi0 " << convertRadToDeg(phi0); |
| 46 | + for (unsigned int i = 0; i < tagLayer.size(); ++i) |
| 47 | + edm::LogVerbatim("HGCalGeom") << "Layer " << i << " Tag " << tagLayer[i] << " T " << moduleThick; |
| 48 | + for (unsigned int i = 0; i < tagSector.size(); ++i) |
| 49 | + edm::LogVerbatim("HGCalGeom") << "Sector " << i << " Tag " << tagSector[i] << " W " << convertRadToDeg(dphi); |
| 50 | +#endif |
| 51 | + std::vector<std::string> layerNames = args.value<std::vector<std::string>>("LayerNames"); // Names of the layers |
| 52 | + std::vector<std::string> materials = |
| 53 | + args.value<std::vector<std::string>>("LayerMaterials"); // Materials of the layers |
| 54 | + std::vector<double> layerThick = args.value<std::vector<double>>("LayerThickness"); // Thickness of layers |
| 55 | +#ifdef EDM_ML_DEBUG |
| 56 | + edm::LogVerbatim("HGCalGeom") << "DDHGCalPassive: " << layerNames.size() << " types of volumes"; |
| 57 | + for (unsigned int i = 0; i < layerNames.size(); ++i) |
| 58 | + edm::LogVerbatim("HGCalGeom") << "Volume [" << i << "] " << layerNames[i] << " of thickness " << layerThick[i] |
| 59 | + << " filled with " << materials[i]; |
| 60 | +#endif |
| 61 | + |
| 62 | + std::vector<int> layerType = args.value<std::vector<int>>("LayerType"); // Layer types |
| 63 | +#ifdef EDM_ML_DEBUG |
| 64 | + std::ostringstream st1; |
| 65 | + for (unsigned int i = 0; i < layerType.size(); ++i) |
| 66 | + st1 << " [" << i << "] " << layerType[i]; |
| 67 | + edm::LogVerbatim("HGCalGeom") << "There are " << layerType.size() << " blocks" << st1.str(); |
| 68 | +#endif |
| 69 | + |
| 70 | + double shiftTop = args.value<double>("ShiftTop"); // Tolerance at the top |
| 71 | + double shiftBot = args.value<double>("ShiftBottom"); // Tolerance at the bottom |
| 72 | +#ifdef EDM_ML_DEBUG |
| 73 | + edm::LogVerbatim("HGCalGeom") << "Shifts st the top " << shiftTop << " and at the bottom " << shiftBot; |
| 74 | +#endif |
| 75 | + |
| 76 | + std::vector<double> slopeB = args.value<std::vector<double>>("SlopeBottom"); // Slope at the lower R |
| 77 | + std::vector<double> zFrontB = args.value<std::vector<double>>("ZFrontBottom"); // Starting Z values for the slopes |
| 78 | + std::vector<double> rMinFront = args.value<std::vector<double>>("RMinFront"); // Corresponding rMin's |
| 79 | + std::vector<double> slopeT = args.value<std::vector<double>>("SlopeTop"); // Slopes at the larger R |
| 80 | + std::vector<double> zFrontT = args.value<std::vector<double>>("ZFrontTop"); // Starting Z values for the slopes |
| 81 | + std::vector<double> rMaxFront = args.value<std::vector<double>>("RMaxFront"); // Corresponding rMax's |
| 82 | +#ifdef EDM_ML_DEBUG |
| 83 | + for (unsigned int i = 0; i < slopeB.size(); ++i) |
| 84 | + edm::LogVerbatim("HGCalGeom") << "Bottom Block [" << i << "] Zmin " << zFrontB[i] << " Rmin " << rMinFront[i] |
| 85 | + << " Slope " << slopeB[i]; |
| 86 | + for (unsigned int i = 0; i < slopeT.size(); ++i) |
| 87 | + edm::LogVerbatim("HGCalGeom") << "Top Block [" << i << "] Zmin " << zFrontT[i] << " Rmax " << rMaxFront[i] |
| 88 | + << " Slope " << slopeT[i]; |
| 89 | + |
| 90 | + edm::LogVerbatim("HGCalGeom") << "==>> Executing DDHGCalPassive..."; |
| 91 | +#endif |
| 92 | + |
| 93 | + static constexpr double tol = 0.00001; |
| 94 | + |
| 95 | + // Loop over Layers |
| 96 | + double zim(zMinBlock); |
| 97 | + //Loop over layers |
| 98 | + for (unsigned int j = 0; j < tagLayer.size(); ++j) { |
| 99 | + double routF = HGCalGeomTools::radius(zim, zFrontT, rMaxFront, slopeT) - shiftTop; |
| 100 | + double zo = zim + moduleThick; |
| 101 | + double rinB = HGCalGeomTools::radius(zo, zFrontB, rMinFront, slopeB) + shiftBot; |
| 102 | + zim += moduleThick; |
| 103 | + for (unsigned int k = 0; k < tagSector.size(); ++k) { |
| 104 | + std::string parentName = parentName + tagLayer[j] + tagSector[k]; |
| 105 | + double phi1 = phi0 + k * dphi; |
| 106 | + double phi2 = phi1 + dphi; |
| 107 | + double phi0 = phi1 + 0.5 * dphi; |
| 108 | + // First the mother |
| 109 | + std::vector<double> xM, yM; |
| 110 | + if (parts == 1) { |
| 111 | + xM = {rinB * cos(phi1), routF * cos(phi1), routF * cos(phi2), rinB * cos(phi2)}; |
| 112 | + yM = {rinB * sin(phi1), routF * sin(phi1), routF * sin(phi2), rinB * sin(phi2)}; |
| 113 | + } else { |
| 114 | + xM = {rinB * cos(phi1), |
| 115 | + routF * cos(phi1), |
| 116 | + routF * cos(phi0), |
| 117 | + routF * cos(phi2), |
| 118 | + rinB * cos(phi2), |
| 119 | + rinB * cos(phi0)}; |
| 120 | + yM = {rinB * sin(phi1), |
| 121 | + routF * sin(phi1), |
| 122 | + routF * sin(phi0), |
| 123 | + routF * sin(phi2), |
| 124 | + rinB * sin(phi2), |
| 125 | + rinB * sin(phi0)}; |
| 126 | + } |
| 127 | + std::vector<double> zw = {-0.5 * thick, 0.5 * thick}; |
| 128 | + std::vector<double> zx(2, 0), zy(2, 0), scale(2, 1.0); |
| 129 | + dd4hep::Solid solid = dd4hep::ExtrudedPolygon(xM, yM, zw, zx, zy, scale); |
| 130 | + ns.addSolidNS(ns.prepend(parentName), solid); |
| 131 | + dd4hep::Material matter = ns.material(material); |
| 132 | + dd4hep::Volume glogM = dd4hep::Volume(solid.name(), solid, matter); |
| 133 | +#ifdef EDM_ML_DEBUG |
| 134 | + edm::LogVerbatim("HGCalGeom") << "DDHGCalPassive: " << solid.name() << " extruded polygon made of " |
| 135 | + << matter.name() << " z|x|y|s (0) " << zw[0] << ":" << zx[0] << ":" << zy[0] |
| 136 | + << ":" << scale[0] << " z|x|y|s (1) " << zw[1] << ":" << zx[1] << ":" << zy[1] |
| 137 | + << ":" << scale[1] << " and " << xM.size() << " edges"; |
| 138 | + for (unsigned int kk = 0; kk < xM.size(); ++kk) |
| 139 | + edm::LogVerbatim("HGCalGeom") << "[" << kk << "] " << xM[kk] << ":" << yM[kk]; |
| 140 | +#endif |
| 141 | + |
| 142 | + // Then the layers |
| 143 | + std::vector<dd4hep::Volume> glogs(materials.size()); |
| 144 | + std::vector<int> copyNumber(materials.size(), 1); |
| 145 | + double zi(-0.5 * thick), thickTot(0.0); |
| 146 | + for (unsigned int l = 0; l < layerType.size(); l++) { |
| 147 | + unsigned int i = layerType[l]; |
| 148 | + if (copyNumber[i] == 1) { |
| 149 | + zw[0] = -0.5 * layerThick[i]; |
| 150 | + zw[1] = 0.5 * layerThick[i]; |
| 151 | + std::string layerName = parentName + layerNames[i]; |
| 152 | + solid = dd4hep::ExtrudedPolygon(xM, yM, zw, zx, zy, scale); |
| 153 | + ns.addSolidNS(ns.prepend(layerName), solid); |
| 154 | + dd4hep::Material matter = ns.material(materials[i]); |
| 155 | + glogs[i] = dd4hep::Volume(solid.name(), solid, matter); |
| 156 | +#ifdef EDM_ML_DEBUG |
| 157 | + edm::LogVerbatim("HGCalGeom") |
| 158 | + << "DDHGCalPassive: Layer " << i << ":" << l << ":" << solid.name() << " extruded polygon made of " |
| 159 | + << matter.name() << " z|x|y|s (0) " << zw[0] << ":" << zx[0] << ":" << zy[0] << ":" << scale[0] |
| 160 | + << " z|x|y|s (1) " << zw[1] << ":" << zx[1] << ":" << zy[1] << ":" << scale[1] << " and " << xM.size() |
| 161 | + << " edges"; |
| 162 | + for (unsigned int kk = 0; kk < xM.size(); ++kk) |
| 163 | + edm::LogVerbatim("HGCalGeom") << "[" << kk << "] " << xM[kk] << ":" << yM[kk]; |
| 164 | +#endif |
| 165 | + } |
| 166 | + dd4hep::Position tran0(0, 0, (zi + 0.5 * layerThick[i])); |
| 167 | + glogM.placeVolume(glogs[i], copyNumber[i], tran0); |
| 168 | +#ifdef EDM_ML_DEBUG |
| 169 | + edm::LogVerbatim("HGCalGeom") << "DDHGCalPassive: " << glogs[i].name() << " number " << copyNumber[i] |
| 170 | + << " positioned in " << glogM.name() << " at (0, 0, " |
| 171 | + << cms::convert2mm(zi + 0.5 * layerThick[i]) << ") with no rotation"; |
| 172 | +#endif |
| 173 | + ++copyNumber[i]; |
| 174 | + zi += layerThick[i]; |
| 175 | + thickTot += layerThick[i]; |
| 176 | + } |
| 177 | + if ((std::abs(thickTot - thick) >= tol) && (!layerType.empty())) { |
| 178 | + if (thickTot > thick) { |
| 179 | + edm::LogError("HGCalGeom") << "Thickness of the partition " << thick << " is smaller than " << thickTot |
| 180 | + << ": thickness of all its components **** ERROR ****"; |
| 181 | + } else { |
| 182 | + edm::LogWarning("HGCalGeom") << "Thickness of the partition " << thick << " does not match with " |
| 183 | + << thickTot << " of the components"; |
| 184 | + } |
| 185 | + } |
| 186 | + } |
| 187 | + } |
| 188 | + } |
| 189 | +}; |
| 190 | + |
| 191 | +static long algorithm(dd4hep::Detector& /* description */, cms::DDParsingContext& ctxt, xml_h e) { |
| 192 | + HGCalPassive passiveAlgo(ctxt, e); |
| 193 | + return cms::s_executed; |
| 194 | +} |
| 195 | + |
| 196 | +DECLARE_DDCMS_DETELEMENT(DDCMS_hgcal_DDHGCalPassive, algorithm) |
0 commit comments