Garfield++ 3.0
A toolkit for the detailed simulation of particle detectors based on ionisation measurement in gases and semiconductors
Loading...
Searching...
No Matches
SolidSphere.cc
Go to the documentation of this file.
1#include <cmath>
2#include <iostream>
3
7
8namespace Garfield {
9
10SolidSphere::SolidSphere(const double cx, const double cy, const double cz,
11 const double r)
12 : Solid(cx, cy, cz, "SolidSphere") {
13 SetRadius(r);
14}
15
16bool SolidSphere::IsInside(const double x, const double y,
17 const double z) const {
18 // Transform the point to local coordinates.
19 const double dx = x - m_cX;
20 const double dy = y - m_cY;
21 const double dz = z - m_cZ;
22
23 if (fabs(dx) > m_r || fabs(dy) > m_r || fabs(dz) > m_r) {
24 if (m_debug) {
25 std::cout << "SolidSphere::IsInside: (" << x << ", " << y << ", " << z
26 << ") is outside.\n";
27 }
28 return false;
29 }
30
31 const double r = sqrt(dx * dx + dy * dy + dz * dz);
32 if (r <= m_r) {
33 if (m_debug) {
34 std::cout << "SolidSphere::IsInside: (" << x << ", " << y << ", " << z
35 << ") is inside.\n";
36 }
37 return true;
38 }
39
40 if (m_debug) {
41 std::cout << "SolidSphere::IsInside: (" << x << ", " << y << ", " << z
42 << ") is outside.\n";
43 }
44 return false;
45}
46
47bool SolidSphere::GetBoundingBox(double& xmin, double& ymin, double& zmin,
48 double& xmax, double& ymax,
49 double& zmax) const {
50 xmin = m_cX - m_r;
51 xmax = m_cX + m_r;
52 ymin = m_cY - m_r;
53 ymax = m_cY + m_r;
54 zmin = m_cZ - m_r;
55 zmax = m_cZ + m_r;
56 return true;
57}
58
59void SolidSphere::SetRadius(const double r) {
60 if (r <= 0.) {
61 std::cerr << "SolidSphere::SetRadius: Radius must be > 0.\n";
62 return;
63 }
64 m_r = r;
65}
66
67void SolidSphere::SetMeridians(const unsigned int n) {
68 if (n < 3) {
69 std::cerr << "SolidSphere::SetMeridians: Number must be >= 3.\n";
70 return;
71 }
72 m_n = n;
73}
74
75bool SolidSphere::SolidPanels(std::vector<Panel>& panels) {
76 const auto id = GetId();
77 const unsigned int nPanels = panels.size();
78 // Loop over the sphere.
79 for (unsigned int i = 1; i <= m_n; ++i) {
80 const double phi0 = TwoPi * (i - 1.) / m_n;
81 const double phi1 = TwoPi * double(i) / m_n;
82 const double cphi0 = cos(phi0);
83 const double sphi0 = sin(phi0);
84 const double cphi1 = cos(phi1);
85 const double sphi1 = sin(phi1);
86 for (unsigned int j = 1; j <= m_n; ++j) {
87 const double theta0 = -HalfPi + Pi * (j - 1.) / m_n;
88 const double theta1 = -HalfPi + Pi * double(j) / m_n;
89 const double ctheta0 = cos(theta0);
90 const double stheta0 = sin(theta0);
91 const double ctheta1 = cos(theta1);
92 const double stheta1 = sin(theta1);
93 Panel newpanel;
94 // Corners of this parcel.
95 if (j == 1) {
96 const double xv0 = m_cX + m_r * cphi0 * ctheta0;
97 const double yv0 = m_cY + m_r * sphi0 * ctheta0;
98 const double zv0 = m_cZ + m_r * stheta0;
99 const double xv1 = m_cX + m_r * cphi1 * ctheta1;
100 const double yv1 = m_cY + m_r * sphi1 * ctheta1;
101 const double zv1 = m_cZ + m_r * stheta1;
102 const double xv2 = m_cX + m_r * cphi0 * ctheta1;
103 const double yv2 = m_cY + m_r * sphi0 * ctheta1;
104 const double zv2 = m_cZ + m_r * stheta1;
105 newpanel.xv = {xv0, xv1, xv2};
106 newpanel.yv = {yv0, yv1, yv2};
107 newpanel.zv = {zv0, zv1, zv2};
108 } else if (j == m_n) {
109 const double xv0 = m_cX + m_r * cphi0 * ctheta0;
110 const double yv0 = m_cY + m_r * sphi0 * ctheta0;
111 const double zv0 = m_cZ + m_r * stheta0;
112 const double xv1 = m_cX + m_r * cphi1 * ctheta0;
113 const double yv1 = m_cY + m_r * sphi1 * ctheta0;
114 const double zv1 = m_cZ + m_r * stheta0;
115 const double xv2 = m_cX + m_r * cphi1 * ctheta1;
116 const double yv2 = m_cY + m_r * sphi1 * ctheta1;
117 const double zv2 = m_cZ + m_r * stheta1;
118 newpanel.xv = {xv0, xv1, xv2};
119 newpanel.yv = {yv0, yv1, yv2};
120 newpanel.zv = {zv0, zv1, zv2};
121 } else {
122 const double xv0 = m_cX + m_r * cphi0 * ctheta0;
123 const double yv0 = m_cY + m_r * sphi0 * ctheta0;
124 const double zv0 = m_cZ + m_r * stheta0;
125 const double xv1 = m_cX + m_r * cphi1 * ctheta0;
126 const double yv1 = m_cY + m_r * sphi1 * ctheta0;
127 const double zv1 = m_cZ + m_r * stheta0;
128 const double xv2 = m_cX + m_r * cphi1 * ctheta1;
129 const double yv2 = m_cY + m_r * sphi1 * ctheta1;
130 const double zv2 = m_cZ + m_r * stheta1;
131 const double xv3 = m_cX + m_r * cphi0 * ctheta1;
132 const double yv3 = m_cY + m_r * sphi0 * ctheta1;
133 const double zv3 = m_cZ + m_r * stheta1;
134 newpanel.xv = {xv0, xv1, xv2, xv3};
135 newpanel.yv = {yv0, yv1, yv2, yv3};
136 newpanel.zv = {zv0, zv1, zv2, zv3};
137 }
138 // Inclination angle in theta.
139 const double alpha =
140 atan2((ctheta0 - ctheta1) * sqrt((1. + cos(phi1 - phi0)) / 2),
141 stheta1 - stheta0);
142 const double calpha = cos(alpha);
143 const double salpha = sin(alpha);
144 // Store the panel.
145 newpanel.a = cos(0.5 * (phi0 + phi1)) * calpha;
146 newpanel.b = sin(0.5 * (phi0 + phi1)) * calpha;
147 newpanel.c = salpha;
148 newpanel.volume = id;
149 panels.push_back(std::move(newpanel));
150 }
151 }
152 std::cout << "SolidSphere::SolidPanels: " << panels.size() - nPanels
153 << " panels.\n";
154 return true;
155}
156
158 return m_dis;
159}
160
161
162}
bool GetBoundingBox(double &xmin, double &ymin, double &zmin, double &xmax, double &ymax, double &zmax) const override
Return the bounding box of the solid.
Definition: SolidSphere.cc:47
bool IsInside(const double x, const double y, const double z) const override
Check whether a given point is inside the solid.
Definition: SolidSphere.cc:16
void SetRadius(const double r)
Set the radius of the sphere.
Definition: SolidSphere.cc:59
double GetDiscretisationLevel(const Panel &panel) override
Retrieve the discretization level of a panel.
Definition: SolidSphere.cc:157
bool SolidPanels(std::vector< Panel > &panels) override
Retrieve the surface panels of the solid.
Definition: SolidSphere.cc:75
SolidSphere(const double cx, const double cy, const double cz, const double r)
Constructor.
Definition: SolidSphere.cc:10
void SetMeridians(const unsigned int n)
Definition: SolidSphere.cc:67
Abstract base class for solids.
Definition: Solid.hh:28
double m_cZ
Definition: Solid.hh:164
unsigned int GetId() const
Get the ID of the solid.
Definition: Solid.hh:117
double m_cY
Definition: Solid.hh:164
bool m_debug
Debug flag.
Definition: Solid.hh:177
double m_cX
Centre of the solid.
Definition: Solid.hh:164
Surface panel.
Definition: Solid.hh:11
std::vector< double > zv
Z-coordinates of vertices.
Definition: Solid.hh:19
int volume
Reference to solid to which the panel belongs.
Definition: Solid.hh:23
double a
Perpendicular vector.
Definition: Solid.hh:13
double c
Definition: Solid.hh:13
double b
Definition: Solid.hh:13
std::vector< double > xv
X-coordinates of vertices.
Definition: Solid.hh:15
std::vector< double > yv
Y-coordinates of vertices.
Definition: Solid.hh:17