File indexing completed on 2024-04-06 12:05:26
0001 #include "DetectorDescription/Core/interface/Polyhedra.h"
0002 #include "DataFormats/Math/interface/GeantUnits.h"
0003
0004 #include <cmath>
0005
0006 #include "DetectorDescription/Core/interface/DDSolidShapes.h"
0007 #include "DetectorDescription/Core/interface/Solid.h"
0008 #include "FWCore/MessageLogger/interface/MessageLogger.h"
0009 #include "FWCore/Utilities/interface/Exception.h"
0010
0011 using DDI::Polyhedra;
0012
0013 using std::cos;
0014 using std::fabs;
0015 using std::sin;
0016 using namespace geant_units;
0017 using namespace geant_units::operators;
0018
0019 Polyhedra::Polyhedra(int sides,
0020 double startPhi,
0021 double deltaPhi,
0022 const std::vector<double>& z,
0023 const std::vector<double>& rmin,
0024 const std::vector<double>& rmax)
0025 : Solid(DDSolidShape::ddpolyhedra_rrz) {
0026 p_.emplace_back(sides);
0027 p_.emplace_back(startPhi);
0028 p_.emplace_back(deltaPhi);
0029 if ((z.size() != rmin.size()) || (z.size() != rmax.size())) {
0030 throw cms::Exception("DDException") << "Polyhedra(..): std::vectors z,rmin,rmax not of same length";
0031 } else {
0032 for (unsigned int i = 0; i < z.size(); ++i) {
0033 p_.emplace_back(z[i]);
0034 p_.emplace_back(rmin[i]);
0035 p_.emplace_back(rmax[i]);
0036 }
0037 }
0038 }
0039
0040 Polyhedra::Polyhedra(
0041 int sides, double startPhi, double deltaPhi, const std::vector<double>& z, const std::vector<double>& r)
0042 : Solid(DDSolidShape::ddpolyhedra_rz) {
0043 p_.emplace_back(sides);
0044 p_.emplace_back(startPhi);
0045 p_.emplace_back(deltaPhi);
0046 if (z.size() != r.size()) {
0047 throw cms::Exception("DDException") << "Polyhedra(..): std::vectors z,rmin,rmax not of same length";
0048 } else {
0049 for (unsigned int i = 0; i < z.size(); ++i) {
0050 p_.emplace_back(z[i]);
0051 p_.emplace_back(r[i]);
0052 }
0053 }
0054 }
0055
0056 double Polyhedra::volume() const {
0057 double volume = 0;
0058
0059
0060
0061
0062
0063
0064
0065
0066
0067
0068
0069
0070
0071
0072
0073
0074
0075
0076
0077
0078
0079
0080
0081 if (shape() == DDSolidShape::ddpolyhedra_rrz) {
0082 int loop = (p_.size() - 3) / 3 - 1;
0083 double sec = 0;
0084 double a = 0.5 * fabs(p_[2] / p_[0]);
0085 int i = 3;
0086 for (int j = 3; j < (loop + 3); ++j) {
0087 double dz = fabs(p_[i] - p_[i + 3]);
0088
0089
0090
0091
0092
0093
0094
0095 double z = dz / 2.;
0096
0097 double H1 = (p_[i + 2] - p_[i + 1]) * cos(a);
0098 double Bl1 = p_[i + 1] * sin(a);
0099 double Tl1 = p_[i + 2] * sin(a);
0100
0101 double H2 = (p_[i + 5] - p_[i + 4]) * cos(a);
0102 double Bl2 = p_[i + 4] * sin(a);
0103 double Tl2 = p_[i + 5] * sin(a);
0104
0105 double s = (2 * H1 * Bl1 + 2 * H1 * Tl1) * z +
0106 (H1 * Bl2 - 2 * H1 * Bl1 + H1 * Tl2 - 2 * H1 * Tl1 + H2 * Bl1 + H2 * Tl1 + H2 * Tl2 - H2 * Tl1) * z +
0107 (2 / 3) * (H2 * Bl2 - H2 * Bl1 - H1 * Bl2 + H1 * Bl1 - H1 * Tl2 + H1 * Tl1) * z;
0108 s = s * p_[0];
0109 sec += s;
0110 i += 3;
0111 }
0112 volume = sec;
0113 return volume;
0114 }
0115 int sides = int(p_[0]);
0116
0117 double phiDelta = p_[2];
0118
0119 double zBegin = 0;
0120 double zEnd = 0;
0121 double rBegin = 0;
0122 double rEnd = 0;
0123 double z = 0;
0124 double alpha = 0;
0125 double beta = 0;
0126 unsigned int i = 3;
0127
0128 alpha = fabs(phiDelta);
0129 beta = 0.5 * (alpha / sides);
0130
0131 while (i < (p_.size() - 2)) {
0132 zBegin = p_[i];
0133 zEnd = p_[i + 2];
0134 rBegin = p_[i + 1];
0135 rEnd = p_[i + 3];
0136 z = zBegin - zEnd;
0137
0138
0139 double volume1 = (rEnd * rEnd + rBegin * rBegin + rBegin * rEnd) * z / 3;
0140
0141 volume = volume + volume1;
0142
0143 i = i + 2;
0144 }
0145
0146
0147
0148 i = p_.size() - 2;
0149 zBegin = p_[i];
0150 zEnd = p_[3];
0151 rBegin = p_[i + 1];
0152 rEnd = p_[4];
0153 z = zBegin - zEnd;
0154
0155 double volume2 = (rEnd * rEnd + rBegin * rBegin + rBegin * rEnd) * z / 3;
0156
0157 volume = volume + volume2;
0158
0159 volume = fabs(sides * cos(beta) * sin(beta) * volume);
0160
0161 return volume;
0162 }
0163
0164 void DDI::Polyhedra::stream(std::ostream& os) const {
0165 os << " sides=" << p_[0] << " startPhi[deg]=" << convertRadToDeg(p_[1]) << " dPhi[deg]=" << convertRadToDeg(p_[2])
0166 << " Sizes[cm]=";
0167 for (unsigned k = 3; k < p_.size(); ++k)
0168 os << convertMmToCm(p_[k]) << " ";
0169 }