Belle II Software  release-05-01-25
eclGeometry.cc
1 #include <ecl/geometry/BelleCrystal.h>
2 #include <ecl/geometry/BelleLathe.h>
3 #include <gtest/gtest.h>
4 #include "ecl/geometry/shapes.h"
5 
6 using namespace std;
7 using namespace Belle2;
8 using namespace ECL;
9 
10 namespace {
11 
13  class BelleCrystalTest : public ::testing::Test {};
14 
16  class BelleLatheTest : public ::testing::Test {
17  protected:
18  double absolute_tolerance = 0.00001;
19  };
20 
21  TEST_F(BelleCrystalTest, BoundingBoxFourSides)
22  {
23  // Create box size 2 2 2
24  G4ThreeVector vertices[] = {G4ThreeVector(-1, -1, -1), G4ThreeVector(1, -1, -1), G4ThreeVector(1, 1, -1), G4ThreeVector(-1, 1, -1),
25  G4ThreeVector(-1, -1, 1), G4ThreeVector(1, -1, 1), G4ThreeVector(1, 1, 1), G4ThreeVector(-1, 1, 1)
26  };
27  BelleCrystal* crystal = new BelleCrystal("solid4", 4, vertices);
28 
29  // Get bounding box
30  G4ThreeVector pMin; G4ThreeVector pMax;
31  crystal->BoundingLimits(pMin, pMax);
32 
33  // Manually calculated bounding box
34  G4ThreeVector pMin_real(-1, -1, -1); G4ThreeVector pMax_real(1, 1, 1);
35 
36  EXPECT_DOUBLE_EQ(pMin_real.x(), pMin.x());
37  EXPECT_DOUBLE_EQ(pMin_real.y(), pMin.y());
38  EXPECT_DOUBLE_EQ(pMin_real.z(), pMin.z());
39 
40  EXPECT_DOUBLE_EQ(pMax_real.x(), pMax.x());
41  EXPECT_DOUBLE_EQ(pMax_real.y(), pMax.y());
42  EXPECT_DOUBLE_EQ(pMax_real.z(), pMax.z());
43  }
44 
45  TEST_F(BelleCrystalTest, BoundingBoxFiveSides)
46  {
47  // Create pentagon side
48  double z = 1;
49  double c1 = 0.25 * (sqrt(5) - 1), c2 = 0.25 * (sqrt(5) + 1);
50  double s1 = 0.25 * sqrt(10 + 2 * sqrt(5)), s2 = 0.25 * sqrt(10 - 2 * sqrt(5));
51  G4ThreeVector vertices[] = {G4ThreeVector(0, 1, -z), G4ThreeVector(-s1, c1, -z), G4ThreeVector(-s2, -c2, -z), G4ThreeVector(s2, -c2, -z), G4ThreeVector(s1, c1, -z),
52  G4ThreeVector(0, 1, z), G4ThreeVector(-s1, c1, z), G4ThreeVector(-s2, -c2, z), G4ThreeVector(s2, -c2, z), G4ThreeVector(s1, c1, z)
53  };
54  BelleCrystal* crystal = new BelleCrystal("solid5", 5, vertices);
55 
56  // Get bounding box
57  G4ThreeVector pMin; G4ThreeVector pMax;
58  crystal->BoundingLimits(pMin, pMax);
59 
60  // Manually calculated bounding box
61  G4ThreeVector pMin_real(-s1, -c2, -z); G4ThreeVector pMax_real(s1, 1, z);
62 
63  EXPECT_DOUBLE_EQ(pMin_real.x(), pMin.x());
64  EXPECT_DOUBLE_EQ(pMin_real.y(), pMin.y());
65  EXPECT_DOUBLE_EQ(pMin_real.z(), pMin.z());
66 
67  EXPECT_DOUBLE_EQ(pMax_real.x(), pMax.x());
68  EXPECT_DOUBLE_EQ(pMax_real.y(), pMax.y());
69  EXPECT_DOUBLE_EQ(pMax_real.z(), pMax.z());
70  }
71 
72  TEST_F(BelleCrystalTest, PentagonSurface)
73  {
74  // Create pentagon side
75  double z = 1;
76  double c1 = 0.25 * (sqrt(5) - 1), c2 = 0.25 * (sqrt(5) + 1);
77  double s1 = 0.25 * sqrt(10 + 2 * sqrt(5)), s2 = 0.25 * sqrt(10 - 2 * sqrt(5));
78  G4ThreeVector p0m(0, 1, -z), p1m(-s1, c1, -z), p2m(-s2, -c2, -z), p3m(s2, -c2, -z), p4m(s1, c1, -z);
79  G4ThreeVector p0p(0, 1, z), p1p(-s1, c1, z), p2p(-s2, -c2, z), p3p(s2, -c2, z), p4p(s1, c1, z);
80  G4ThreeVector vertices[] = {p0m, p1m, p2m, p3m, p4m, p0p, p1p, p2p, p3p, p4p};
81  BelleCrystal* c = new BelleCrystal("solid5", 5, vertices);
82 
83  for (int i = 0; i < 1000 * 100; i++) {
84  G4ThreeVector p = c->GetPointOnSurface();
85  EXPECT_EQ(c->Inside(p), kSurface);
86  }
87  delete c;
88  }
89 
90  TEST_F(BelleCrystalTest, BarrelSurfaces)
91  {
92  vector<shape_t*> cryst = load_shapes("/ecl/data/crystal_shape_barrel.dat");
93  double wrapthickness = 0.17;
94  for (auto it = cryst.begin(); it != cryst.end(); it++) {
95  shape_t* s = *it;
96  std::string prefix("sv_"); prefix += "barrel"; prefix += "_wrap";
97  G4Translate3D tw;
98  G4VSolid* c = s->get_solid(prefix, wrapthickness, tw);
99  for (int i = 0; i < 1000 * 100; i++) {
100  G4ThreeVector p = c->GetPointOnSurface();
101  EInside I = c->Inside(p);
102  EXPECT_EQ(I, kSurface);
103  }
104  delete c;
105  }
106  for (auto it = cryst.begin(); it != cryst.end(); it++) delete *it;
107  }
108 
109  TEST_F(BelleCrystalTest, ForwardSurfaces)
110  {
111  vector<shape_t*> cryst = load_shapes("/ecl/data/crystal_shape_forward.dat");
112  double wrapthickness = 0.17;
113  for (auto it = cryst.begin(); it != cryst.end(); it++) {
114  shape_t* s = *it;
115  std::string prefix("sv_"); prefix += "barrel"; prefix += "_wrap";
116  G4Translate3D tw;
117  G4VSolid* c = s->get_solid(prefix, wrapthickness, tw);
118  for (int i = 0; i < 1000 * 100; i++) {
119  G4ThreeVector p = c->GetPointOnSurface();
120  EInside I = c->Inside(p);
121  EXPECT_EQ(I, kSurface);
122  }
123  delete c;
124  }
125  for (auto it = cryst.begin(); it != cryst.end(); it++) delete *it;
126  }
127 
128  TEST_F(BelleCrystalTest, BackwardSurfaces)
129  {
130  vector<shape_t*> cryst = load_shapes("/ecl/data/crystal_shape_backward.dat");
131  double wrapthickness = 0.17;
132  for (auto it = cryst.begin(); it != cryst.end(); it++) {
133  shape_t* s = *it;
134  std::string prefix("sv_"); prefix += "barrel"; prefix += "_wrap";
135  G4Translate3D tw;
136  G4VSolid* c = s->get_solid(prefix, wrapthickness, tw);
137  for (int i = 0; i < 1000 * 100; i++) {
138  G4ThreeVector p = c->GetPointOnSurface();
139  EInside I = c->Inside(p);
140  EXPECT_EQ(I, kSurface);
141  }
142  delete c;
143  }
144  for (auto it = cryst.begin(); it != cryst.end(); it++) delete *it;
145  }
146 
147  // Bounding limits for half circle starting at pi/2
148  TEST_F(BelleLatheTest, BoundingBoxSect0)
149  {
150  // Create the Belle Lathe
151  zr_t bint[] = {{ -1, 0}, {1, 0}, {1, 1}, { -1, 1}}; //z, r
152  std::vector<zr_t> contourb(bint, bint + sizeof(bint) / sizeof(zr_t));
153  BelleLathe* sect = new BelleLathe("sect", M_PI / 2, M_PI, contourb);
154 
155  // Get bounding box
156  G4ThreeVector pMin; G4ThreeVector pMax;
157  sect->BoundingLimits(pMin, pMax);
158 
159  // Manually calculated bounding box
160  G4ThreeVector pMin_real(-1, -1, -1);
161  G4ThreeVector pMax_real(0, 1, 1);
162 
163  EXPECT_NEAR(pMin_real.x(), pMin.x(), absolute_tolerance);
164  EXPECT_NEAR(pMin_real.y(), pMin.y(), absolute_tolerance);
165  EXPECT_NEAR(pMin_real.z(), pMin.z(), absolute_tolerance);
166 
167  EXPECT_NEAR(pMax_real.x(), pMax.x(), absolute_tolerance);
168  EXPECT_NEAR(pMax_real.y(), pMax.y(), absolute_tolerance);
169  EXPECT_NEAR(pMax_real.z(), pMax.z(), absolute_tolerance);
170  }
171 
172  // Bouding limits for half circle starting at 3pi/2
173  TEST_F(BelleLatheTest, BoundingBoxSect1)
174  {
175  // Create the Belle Lathe
176  zr_t bint[] = {{ -1, 0}, {1, 0}, {1, 1}, { -1, 1}}; //z, r
177  std::vector<zr_t> contourb(bint, bint + sizeof(bint) / sizeof(zr_t));
178  BelleLathe* sect = new BelleLathe("sect", 3 * M_PI / 2, M_PI, contourb);
179 
180  // Get bounding box
181  G4ThreeVector pMin; G4ThreeVector pMax;
182  sect->BoundingLimits(pMin, pMax);
183 
184  // Manually calculated bounding box
185  G4ThreeVector pMin_real(0, -1, -1);
186  G4ThreeVector pMax_real(1, 1, 1);
187 
188  EXPECT_NEAR(pMin_real.x(), pMin.x(), absolute_tolerance);
189  EXPECT_NEAR(pMin_real.y(), pMin.y(), absolute_tolerance);
190  EXPECT_NEAR(pMin_real.z(), pMin.z(), absolute_tolerance);
191 
192  EXPECT_NEAR(pMax_real.x(), pMax.x(), absolute_tolerance);
193  EXPECT_NEAR(pMax_real.y(), pMax.y(), absolute_tolerance);
194  EXPECT_NEAR(pMax_real.z(), pMax.z(), absolute_tolerance);
195  }
196 
197  // Bouding limits for quarter starting at pi
198  TEST_F(BelleLatheTest, BoundingBoxSect2)
199  {
200  // Create the Belle Lathe
201  zr_t bint[] = {{ -1, 0}, {1, 0}, {1, 1}, { -1, 1}}; //z, r
202  std::vector<zr_t> contourb(bint, bint + sizeof(bint) / sizeof(zr_t));
203  BelleLathe* sect = new BelleLathe("sect", M_PI, M_PI / 2, contourb);
204 
205  // Get bounding box
206  G4ThreeVector pMin; G4ThreeVector pMax;
207  sect->BoundingLimits(pMin, pMax);
208 
209  // Manually calculated bounding box
210  G4ThreeVector pMin_real(-1, -1, -1);
211  G4ThreeVector pMax_real(0, 0, 1);
212 
213  EXPECT_NEAR(pMin_real.x(), pMin.x(), absolute_tolerance);
214  EXPECT_NEAR(pMin_real.y(), pMin.y(), absolute_tolerance);
215  EXPECT_NEAR(pMin_real.z(), pMin.z(), absolute_tolerance);
216 
217  EXPECT_NEAR(pMax_real.x(), pMax.x(), absolute_tolerance);
218  EXPECT_NEAR(pMax_real.y(), pMax.y(), absolute_tolerance);
219  EXPECT_NEAR(pMax_real.z(), pMax.z(), absolute_tolerance);
220  }
221 
222  // Bouding limits for three quarter starting at 0
223  TEST_F(BelleLatheTest, BoundingBoxSect3)
224  {
225  // Create the Belle Lathe
226  zr_t bint[] = {{ -1, 0}, {1, 0}, {1, 1}, { -1, 1}}; //z, r
227  std::vector<zr_t> contourb(bint, bint + sizeof(bint) / sizeof(zr_t));
228  BelleLathe* sect = new BelleLathe("sect", 0, 3 * M_PI / 2, contourb);
229 
230  // Get bounding box
231  G4ThreeVector pMin; G4ThreeVector pMax;
232  sect->BoundingLimits(pMin, pMax);
233 
234  // Manually calculated bounding box
235  G4ThreeVector pMin_real(-1, -1, -1);
236  G4ThreeVector pMax_real(1, 1, 1);
237 
238  EXPECT_NEAR(pMin_real.x(), pMin.x(), absolute_tolerance);
239  EXPECT_NEAR(pMin_real.y(), pMin.y(), absolute_tolerance);
240  EXPECT_NEAR(pMin_real.z(), pMin.z(), absolute_tolerance);
241 
242  EXPECT_NEAR(pMax_real.x(), pMax.x(), absolute_tolerance);
243  EXPECT_NEAR(pMax_real.y(), pMax.y(), absolute_tolerance);
244  EXPECT_NEAR(pMax_real.z(), pMax.z(), absolute_tolerance);
245  }
246 
247  // Bouding limits for quarter starting at pi/4 w/ hole
248  TEST_F(BelleLatheTest, BoundingBoxSect4)
249  {
250  // Create the Belle Lathe
251  zr_t bint[] = {{ -1, 0.5}, {1, 0.5}, {1, 1}, { -1, 1}}; //z, r, rmin is 0.5
252  std::vector<zr_t> contourb(bint, bint + sizeof(bint) / sizeof(zr_t));
253  BelleLathe* sect = new BelleLathe("sect", M_PI / 4, M_PI / 2, contourb);
254 
255  // Get bounding box
256  G4ThreeVector pMin; G4ThreeVector pMax;
257  sect->BoundingLimits(pMin, pMax);
258 
259  // Manually calculated bounding box
260  G4ThreeVector pMin_real(cos(3 * M_PI / 4), 0.5 * sin(M_PI / 4), -1);
261  G4ThreeVector pMax_real(cos(M_PI / 4), 1, 1);
262 
263  EXPECT_NEAR(pMin_real.x(), pMin.x(), absolute_tolerance);
264  EXPECT_NEAR(pMin_real.y(), pMin.y(), absolute_tolerance);
265  EXPECT_NEAR(pMin_real.z(), pMin.z(), absolute_tolerance);
266 
267  EXPECT_NEAR(pMax_real.x(), pMax.x(), absolute_tolerance);
268  EXPECT_NEAR(pMax_real.y(), pMax.y(), absolute_tolerance);
269  EXPECT_NEAR(pMax_real.z(), pMax.z(), absolute_tolerance);
270  }
271 }
Belle2::ECL::BelleCrystal::BoundingLimits
void BoundingLimits(G4ThreeVector &pMin, G4ThreeVector &pMax) const
Two vectors define an axis-parallel bounding box for the shape.
Definition: BelleCrystal.cc:725
Belle2::ECL::shape_t
Definition: shapes.h:39
Belle2
Abstract base class for different kinds of events.
Definition: MillepedeAlgorithm.h:19
Belle2::ECL::BelleCrystal
a Belle crystal in Geant4
Definition: BelleCrystal.h:45
Belle2::TEST_F
TEST_F(GlobalLabelTest, LargeNumberOfTimeDependentParameters)
Test large number of time-dep params for registration and retrieval.
Definition: globalLabel.cc:65
Belle2::ECL::BelleLathe::BoundingLimits
void BoundingLimits(G4ThreeVector &pMin, G4ThreeVector &pMax) const
Two vectors define an axis-parallel bounding box for the shape.
Definition: BelleLathe.cc:1837
Belle2::ECL::zr_t
Definition: BelleLathe.h:35
Belle2::ECL::BelleLathe
Definition: BelleLathe.h:60