ATLAS Offline Software
Loading...
Searching...
No Matches
DoubleTrapezoidVolumeBounds.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2024 CERN for the benefit of the ATLAS collaboration
3*/
4
6// DoubleTrapezoidVolumeBounds.cxx, (c) ATLAS Detector software
8
9// Trk
11// TrkSurfaces
15// Gaudi
16#include "GaudiKernel/MsgStream.h"
17#include "GaudiKernel/SystemOfUnits.h"
18// STD
19#include <cmath>
20#include <iomanip>
21#include <iostream>
22
35
37 double minhalex,
38 double medhalex,
39 double maxhalex,
40 double haley1,
41 double haley2,
42 double halez)
43 : VolumeBounds()
44 , m_minHalfX(minhalex)
45 , m_medHalfX(medhalex)
46 , m_maxHalfX(maxhalex)
47 , m_halfY1(haley1)
48 , m_halfY2(haley2)
49 , m_halfZ(halez)
50 , m_alpha1(0.)
51 , m_alpha2(0.)
53{
54 m_alpha1 = atan2(m_medHalfX - m_minHalfX, 2. * m_halfY1);
55 m_alpha2 = atan2(m_medHalfX - m_maxHalfX, 2. * m_halfY2);
56}
57
71
73
77{
78 if (this != &trabo) {
79 m_minHalfX = trabo.m_minHalfX;
80 m_medHalfX = trabo.m_medHalfX;
81 m_maxHalfX = trabo.m_maxHalfX;
82 m_halfY1 = trabo.m_halfY1;
83 m_halfY2 = trabo.m_halfY2;
84 m_halfZ = trabo.m_halfZ;
85 m_alpha1 = trabo.m_alpha1;
86 m_alpha2 = trabo.m_alpha2;
88 }
89 return *this;
90}
91
92std::vector<std::unique_ptr<Trk::Surface>>
94 (const Amg::Transform3D& transform)
95{
96 auto retsf = std::vector<std::unique_ptr<Trk::Surface>>();
97
98 // face surfaces xy
99 Amg::RotationMatrix3D diamondRotation(transform.rotation());
100 Amg::Vector3D diamondX(diamondRotation.col(0));
101 Amg::Vector3D diamondY(diamondRotation.col(1));
102 Amg::Vector3D diamondZ(diamondRotation.col(2));
103 Amg::Vector3D diamondCenter(transform.translation());
104
105 // (1) - at negative local z
106 retsf.push_back(std::make_unique<Trk::PlaneSurface>(
108 transform *
109 Amg::Translation3D(Amg::Vector3D(0., 0., -this->halflengthZ())) *
110 Amg::AngleAxis3D(180 * Gaudi::Units::deg, Amg::Vector3D(0., 1., 0.))
111 ),
112 this->faceXYDiamondBounds()));
113 // (2) - at positive local z
114 retsf.push_back(std::make_unique<Trk::PlaneSurface>(
116 transform *
118 this->faceXYDiamondBounds()));
119 // face surfaces yz
120 // transmute cyclical
121 // (3) - at point A, attached to alpha opening angle
122 // in the local diamond coordinate system the center of the bottom left yz face plane is:
123 Amg::Vector3D A(- this->minHalflengthX(), -this->halflengthY1(), 0.);
124 Amg::AngleAxis3D alpha1ZRotation(this->alpha1(), Amg::Vector3D(0., 0., 1.));
125 // the face plane has to be rotated first by 90 degrees around the z-axis
126 // because the x-axis should point into ~y direction
127 // then it has to be rotated around the y-axis by 90 degrees to become a yz plane
128 // finally it is rotated by alpha1 around the z-axis
129 Amg::RotationMatrix3D alpha1Rotation(
130 alpha1ZRotation *
131 Amg::AngleAxis3D(-90 * Gaudi::Units::deg, Amg::Vector3D(0., 1., 0.)) *
132 Amg::AngleAxis3D(90 * Gaudi::Units::deg, Amg::Vector3D(0., 0., 1.)));
133 std::shared_ptr<RectangleBounds> faceAlpha1Bounds = this->faceAlpha1RectangleBounds();
134 const Amg::Vector3D& faceAlpha1Position(A);
135 retsf.push_back(std::make_unique<Trk::PlaneSurface>(
137 transform * Amg::Translation3D(faceAlpha1Position) * Amg::Transform3D(alpha1Rotation) ),
138 faceAlpha1Bounds));
139 // (4) - at point B, attached to beta opening angle
140 // in the local diamond coordinate system the center of the bottom right yz face plane is:
141 Amg::Vector3D B(this->minHalflengthX(), -this->halflengthY1(), 0.);
142 Amg::AngleAxis3D beta1ZRotation(-this->alpha1(), Amg::Vector3D(0., 0., 1.));
143 Amg::RotationMatrix3D beta1Rotation(
144 beta1ZRotation *
145 Amg::AngleAxis3D(90 * Gaudi::Units::deg, Amg::Vector3D(0., 1., 0.)) *
146 Amg::AngleAxis3D(90 * Gaudi::Units::deg, Amg::Vector3D(0., 0., 1.)));
147 std::shared_ptr<RectangleBounds> faceBeta1Bounds = this->faceBeta1RectangleBounds();
148 const Amg::Vector3D& faceBeta1Position(B);
149 retsf.push_back(std::make_unique<Trk::PlaneSurface>(
150 transform * Amg::Translation3D(faceBeta1Position) * Amg::Transform3D(beta1Rotation) ,
151 faceBeta1Bounds));
152 // face surfaces yz
153 // transmute cyclical
154 // (5) - at point A', attached to alpha opening angle
155 // center of the left top yz face plate;
156 Amg::Vector3D AA(- this->maxHalflengthX(), this->halflengthY2(), 0.);
157 Amg::AngleAxis3D alpha2ZRotation(-this->alpha2(), Amg::Vector3D(0., 0., 1.));
158 Amg::RotationMatrix3D alpha2Rotation(
159 alpha2ZRotation *
160 Amg::AngleAxis3D(-90 * Gaudi::Units::deg, Amg::Vector3D(0., 1., 0.)) *
161 Amg::AngleAxis3D(-90 * Gaudi::Units::deg, Amg::Vector3D(0., 0., 1.)));
162 std::shared_ptr<RectangleBounds> faceAlpha2Bounds = this->faceAlpha2RectangleBounds();
163 const Amg::Vector3D& faceAlpha2Position(
164 AA);
165 retsf.push_back(std::make_unique<Trk::PlaneSurface>(
167 transform * Amg::Translation3D(faceAlpha2Position) * Amg::Transform3D(alpha2Rotation)),
168 faceAlpha2Bounds));
169 // (6) - at point B', attached to beta opening angle
170 // center of the right top yz face plate;
171 Amg::Vector3D BB( this->maxHalflengthX(),this->halflengthY2(), 0.);
172 Amg::AngleAxis3D beta2ZRotation(this->alpha2(), Amg::Vector3D(0., 0., 1.));
173 Amg::RotationMatrix3D beta2Rotation(
174 beta2ZRotation *
175 Amg::AngleAxis3D(90 * Gaudi::Units::deg, Amg::Vector3D(0., 1., 0.)) *
176 Amg::AngleAxis3D(-90 * Gaudi::Units::deg, Amg::Vector3D(0., 0., 1.)));
177 std::shared_ptr<RectangleBounds> faceBeta2Bounds = this->faceBeta2RectangleBounds();
178 const Amg::Vector3D& faceBeta2Position(BB);
179 retsf.push_back(std::make_unique<Trk::PlaneSurface>(
180 transform * Amg::Translation3D(faceBeta2Position) * Amg::Transform3D(beta2Rotation),
181 faceBeta2Bounds));
182 // face surfaces zx
183 // (7) - at negative local y
184 retsf.push_back(std::make_unique<Trk::PlaneSurface>(
186 transform *
187 Amg::Translation3D(Amg::Vector3D(0., -2 * this->halflengthY1(), 0.)) *
188 Amg::AngleAxis3D(180. * Gaudi::Units::deg, Amg::Vector3D(1., 0., 0.)) *
189 Amg::AngleAxis3D(-90 * Gaudi::Units::deg, Amg::Vector3D(0., 1., 0.)) *
190 Amg::AngleAxis3D(-90. * Gaudi::Units::deg, Amg::Vector3D(1., 0., 0.))),
192 // (8) - at positive local y
193 retsf.push_back(std::make_unique<Trk::PlaneSurface>(
195 transform *
196 Amg::Translation3D(Amg::Vector3D(0., 2*this->halflengthY2(), 0.)) *
197 Amg::AngleAxis3D(-90 * Gaudi::Units::deg, Amg::Vector3D(0., 1., 0.)) *
198 Amg::AngleAxis3D(-90. * Gaudi::Units::deg, Amg::Vector3D(1., 0., 0.))),
199 this->faceZXRectangleBoundsTop()));
200
201 return retsf;
202}
203
204// faces in xy
205std::shared_ptr<Trk::DiamondBounds>
207{
208 return std::make_shared<Trk::DiamondBounds>(
210}
211
212std::shared_ptr<Trk::RectangleBounds>
214{
215 return std::make_shared<Trk::RectangleBounds>(m_halfY1 / cos(m_alpha1), m_halfZ);
216}
217
218std::shared_ptr<Trk::RectangleBounds>
220{
221 return std::make_shared<Trk::RectangleBounds>(m_halfY2 / cos(m_alpha2), m_halfZ);
222}
223
224std::shared_ptr<Trk::RectangleBounds>
226{
227 return std::make_shared<Trk::RectangleBounds>(m_halfY1 / cos(m_alpha1), m_halfZ);
228}
229
230std::shared_ptr<Trk::RectangleBounds>
232{
233 return std::make_shared<Trk::RectangleBounds>(m_halfY2 / cos(m_alpha2), m_halfZ);
234}
235
236std::shared_ptr<Trk::RectangleBounds>
238{
239 return std::make_shared<Trk::RectangleBounds>(m_halfZ, m_minHalfX);
240}
241
242std::shared_ptr<Trk::RectangleBounds>
244{
245 return std::make_shared<Trk::RectangleBounds>(m_halfZ, m_maxHalfX);
246}
247
248// Trk::RectangleBounds*
249// Trk::DoubleTrapezoidVolumeBounds::faceZXRectangleBoundsTop() const
250//{
251// double delta = (m_alpha < m_beta) ? m_alpha - M_PI/2. : m_beta - M_PI/2.;
252// return new Trk::RectangleBounds(m_halfZ,
253// 0.5*(m_minHalfX+m_minHalfX+2.*m_halfY/cos(delta)));
254//}
255
256bool
258 const
259{
260 if (std::abs(pos.z()) > m_halfZ + tol)
261 return false;
262 if (pos.y() < -2 * m_halfY1 - tol)
263 return false;
264 if (pos.y() > 2 * m_halfY2 + tol)
265 return false;
266 std::shared_ptr<Trk::DiamondBounds> faceXYBounds = this->faceXYDiamondBounds();
267 Amg::Vector2D locp(pos.x(), pos.y());
268 bool inside(faceXYBounds->inside(locp, tol, tol));
269 return inside;
270}
271
272// ostream operator overload
273MsgStream&
275{
276 std::stringstream temp_sl;
277 temp_sl << std::setiosflags(std::ios::fixed);
278 temp_sl << std::setprecision(7);
279 temp_sl << "Trk::DoubleTrapezoidVolumeBounds: (minhalfX, medhalfX, maxhalfX, "
280 "halfY1, halfY2, halfZ) = ";
281 temp_sl << "(" << m_minHalfX << ", " << m_medHalfX << ", " << m_maxHalfX;
282 temp_sl << ", " << m_halfY1 << ", " << m_halfY2 << ", " << m_halfZ << ")";
283 sl << temp_sl.str();
284 return sl;
285}
286
287std::ostream&
289{
290 std::stringstream temp_sl;
291 temp_sl << std::setiosflags(std::ios::fixed);
292 temp_sl << std::setprecision(7);
293 temp_sl << "Trk::DoubleTrapezoidVolumeBounds: ) =(minhalfX, medhalfX, "
294 "maxhalfX, halfY1, halfY2, halfZ) ";
295 temp_sl << "(" << m_minHalfX << ", " << m_medHalfX << ", " << m_maxHalfX;
296 temp_sl << ", " << m_halfY1 << ", " << m_halfY2 << ", " << m_halfZ << ")";
297 sl << temp_sl.str();
298 return sl;
299}
300
Bounds for a double trapezoidal shaped Volume, the decomposeToSurfaces method creates a vector of 8 s...
double minHalflengthX() const
This method returns the X halflength at minimal Y.
std::shared_ptr< DiamondBounds > faceXYDiamondBounds() const
This method returns the associated DoubleTrapezoidBounds of the face PlaneSurface parallel to local x...
double m_alpha1
opening angle alpha (in point A)
double alpha2() const
This method returns the opening angle in point A' (negative local x)
MsgStream & dump(MsgStream &sl) const override final
Output Method for MsgStream.
Trk::EightObjectsAccessor m_objectAccessor
There's only one single object Acessor for the moment has to be implemented if Cuboids are used more ...
DoubleTrapezoidVolumeBounds & operator=(const DoubleTrapezoidVolumeBounds &bobo)
Assignment operator.
bool inside(const Amg::Vector3D &, double tol=0.) const override final
This method checks if position in the 3D volume frame is inside the cylinder.
double m_alpha2
opening angle alpha (in point A')
std::shared_ptr< RectangleBounds > faceBeta1RectangleBounds() const
This method returns the associated RecantleBounds of the face PlaneSurface attached to beta (positive...
double halflengthZ() const
This method returns the halflength in local z.
double m_minHalfX
minimal Y halflength in x
std::shared_ptr< RectangleBounds > faceZXRectangleBoundsBottom() const
This method returns the associated RecantleBounds of the face PlaneSurface parallel to local zx plane...
virtual std::vector< std::unique_ptr< Trk::Surface > > decomposeToSurfaces(const Amg::Transform3D &transform) override final
Method to decompose the Bounds into Surfaces.
double halflengthY1() const
This method returns the halflength1 in local y.
std::shared_ptr< RectangleBounds > faceZXRectangleBoundsTop() const
This method returns the associated RecantleBounds of the face PlaneSurface parallel to local zx plane...
double alpha1() const
This method returns the opening angle in point A (negative local x)
double halflengthY2() const
This method returns the halflength2 in local y.
double m_maxHalfX
maximal Y halflength in x
std::shared_ptr< RectangleBounds > faceAlpha2RectangleBounds() const
double maxHalflengthX() const
This method returns the X halflength at maximal Y (local coordinates)
std::shared_ptr< RectangleBounds > faceBeta2RectangleBounds() const
virtual ~DoubleTrapezoidVolumeBounds()
Destructor.
std::shared_ptr< RectangleBounds > faceAlpha1RectangleBounds() const
This method returns the associated RecantleBounds of the face PlaneSurface attached to alpha (negativ...
VolumeBounds()
Default Constructor.
Eigen::AngleAxisd AngleAxis3D
Eigen::Matrix< double, 3, 3 > RotationMatrix3D
Eigen::Affine3d Transform3D
Eigen::Matrix< double, 2, 1 > Vector2D
Eigen::Matrix< double, 3, 1 > Vector3D
Eigen::Translation< double, 3 > Translation3D
hold the test vectors and ease the comparison