CMS 3D CMS Logo

GflashTrajectory.cc
Go to the documentation of this file.
1 // Most methods of this class are excerpted from CDF Helix and Trajectory class
2 
4 
6  : _cotTheta(0.0),
7  _curvature(0.0),
8  _z0(0.0),
9  _d0(0.0),
10  _phi0(0.0),
11  _isStale(true),
12  _sinPhi0(2),
13  _cosPhi0(2),
14  _sinTheta(2),
15  _cosTheta(2),
16  _s(-999.999),
17  _aa(2),
18  _ss(2),
19  _cc(2) {
20  // detault constructor
21 }
22 
23 // GflashTrajectory::GflashTrajectory(const HepGeom::Vector3D<double> &
24 // MomentumGev, const HepGeom::Point3D<double> & PositionCm, double q,
25 // double
26 // BFieldTesla)
27 void GflashTrajectory::initializeTrajectory(const HepGeom::Vector3D<double> &MomentumGev,
28  const HepGeom::Point3D<double> &PositionCm,
29  double q,
30  double BFieldTesla) {
31  double CotTheta = 0.0;
32  double W = 0;
33  double Z0 = 0;
34  double D0 = 0;
35  double Phi0 = 0;
36 
37  if (BFieldTesla != 0.0 && q != 0.0) {
38  double CurvatureConstant = 0.0029979;
39  double Helicity = -1.0 * fabs(BFieldTesla) * fabs(q) / (BFieldTesla * q);
40  double Radius = fabs(MomentumGev.perp() / (CurvatureConstant * BFieldTesla * q));
41 
42  if (Radius == 0.0)
43  W = HUGE_VAL;
44  else
45  W = Helicity / Radius;
46  double phi1 = MomentumGev.phi();
47  double x = PositionCm.x(), y = PositionCm.y(), z = PositionCm.z();
48  double sinPhi1 = sin(phi1), cosPhi1 = cos(phi1);
49  double gamma = atan((x * cosPhi1 + y * sinPhi1) / (x * sinPhi1 - y * cosPhi1 - 1 / W));
50  Phi0 = phi1 + gamma;
51  if (Phi0 > M_PI)
52  Phi0 = Phi0 - 2.0 * M_PI;
53  if (Phi0 < -M_PI)
54  Phi0 = Phi0 + 2.0 * M_PI;
55  D0 = ((1 / W + y * cosPhi1 - x * sinPhi1) / cos(gamma) - 1 / W);
56  CotTheta = MomentumGev.z() / MomentumGev.perp();
57  Z0 = z + gamma * CotTheta / W;
58  } else {
59  CLHEP::Hep3Vector direction = MomentumGev.unit();
60  CLHEP::Hep3Vector projectedDirection = CLHEP::Hep3Vector(direction.x(), direction.y(), 0.0).unit();
61  double s = projectedDirection.dot(PositionCm);
62  double sprime = s / sin(direction.theta());
63  Z0 = (PositionCm - sprime * direction).z();
64  Phi0 = MomentumGev.phi();
65  CotTheta = MomentumGev.z() / MomentumGev.perp();
66  W = 0.0;
67  D0 = (PositionCm.y() * cos(Phi0) - PositionCm.x() * sin(Phi0));
68  }
69 
70  _cotTheta = CotTheta;
71  _curvature = W / 2;
72  _z0 = Z0;
73  _d0 = D0;
74  _phi0 = Phi0;
75 
76  _isStale = true;
77  _s = -999.999;
78  _aa = -999.999;
79  _ss = -999.999;
80  _cc = -999.999;
81  _sinPhi0 = 1.0;
82  _cosPhi0 = 1.0;
83  _sinTheta = 1.0;
84  _cosTheta = 1.0;
85 }
86 
88 
89 void GflashTrajectory::setCotTheta(double cotTheta) {
90  _cotTheta = cotTheta;
91  _isStale = true;
92 }
93 
96  _isStale = true;
97 }
98 
100  _z0 = z0;
101  _isStale = true;
102 }
103 
105  _d0 = d0;
106  _isStale = true;
107 }
108 
109 void GflashTrajectory::setPhi0(double phi0) {
110  _phi0 = phi0;
111  _isStale = true;
112 }
113 
115  _refreshCache();
116  return _sinPhi0;
117 }
119  _refreshCache();
120  return _cosPhi0;
121 }
123  _refreshCache();
124  return _sinTheta;
125 }
127  _refreshCache();
128  return _cosTheta;
129 }
130 
131 HepGeom::Point3D<double> GflashTrajectory::getPosition(double s) const {
133  if (s == 0.0 || _curvature == 0.0) {
134  return HepGeom::Point3D<double>(
136  } else {
137  return HepGeom::Point3D<double>(
138  (_cosPhi0 * _ss - _sinPhi0 * (2.0 * _curvature * _d0 + 1.0 - _cc)) / (2.0 * _curvature),
139  (_sinPhi0 * _ss + _cosPhi0 * (2.0 * _curvature * _d0 + 1.0 - _cc)) / (2.0 * _curvature),
140  _s * _cosTheta + _z0);
141  }
142 }
143 
144 HepGeom::Vector3D<double> GflashTrajectory::getDirection(double s) const {
146  if (s == 0.0) {
147  return HepGeom::Vector3D<double>(_cosPhi0 * _sinTheta, _sinPhi0 * _sinTheta, _cosTheta);
148  }
149  double xtan = _sinTheta * (_cosPhi0 * _cc - _sinPhi0 * _ss);
150  double ytan = _sinTheta * (_cosPhi0 * _ss + _sinPhi0 * _cc);
151  double ztan = _cosTheta;
152  return HepGeom::Vector3D<double>(xtan, ytan, ztan);
153 }
154 
157 
158  double cP0sT = _cosPhi0 * _sinTheta, sP0sT = _sinPhi0 * _sinTheta;
159  if (s && _curvature) {
160  point.getPosition().set((_cosPhi0 * _ss - _sinPhi0 * (2.0 * _curvature * _d0 + 1.0 - _cc)) / (2.0 * _curvature),
161  (_sinPhi0 * _ss + _cosPhi0 * (2.0 * _curvature * _d0 + 1.0 - _cc)) / (2.0 * _curvature),
162  s * _cosTheta + _z0);
163 
164  point.getMomentum().set(cP0sT * _cc - sP0sT * _ss, cP0sT * _ss + sP0sT * _cc, _cosTheta);
165  point.setPathLength(s);
166  } else {
167  point.getPosition().set(-_d0 * _sinPhi0 + s * cP0sT, _d0 * _cosPhi0 + s * sP0sT, _z0 + s * _cosTheta);
168 
169  point.getMomentum().set(cP0sT, sP0sT, _cosTheta);
170 
171  point.setPathLength(s);
172  }
173 }
174 
176  return (getSinTheta() ? (getL2DAtR(rho) / getSinTheta()) : 0.0);
177 }
178 
179 double GflashTrajectory::getPathLengthAtZ(double z) const {
180  return (getCosTheta() ? (z - getZ0()) / getCosTheta() : 0.0);
181 }
182 
183 double GflashTrajectory::getZAtR(double rho) const { return _z0 + getCotTheta() * getL2DAtR(rho); }
184 
185 double GflashTrajectory::getL2DAtR(double rho) const {
186  double L2D;
187 
188  double c = getCurvature();
189  double d = getD0();
190 
191  if (c != 0.0) {
192  double rad = (rho * rho - d * d) / (1.0 + 2.0 * c * d);
193  double rprime;
194  if (rad < 0.0) {
195  rprime = 0.0;
196  } else {
197  rprime = sqrt(rad);
198  }
199  if (c * rprime > 1.0 || c * rprime < -1.0) {
200  L2D = c * rprime > 0. ? M_PI / c : -M_PI / c;
201  } else
202  L2D = asin(c * rprime) / c;
203  } else {
204  double rad = rho * rho - d * d;
205  double rprime;
206  if (rad < 0.0)
207  rprime = 0.0;
208  else
209  rprime = sqrt(rad);
210 
211  L2D = rprime;
212  }
213  return L2D;
214 }
215 
216 // Update _sinTheta,_cosTheta,_sinPhi0, and _cosPhi0
218  if (_isStale) {
219  _isStale = false;
220  double theta;
221  if (_cotTheta == 0.0) {
222  theta = M_PI / 2.0;
223  } else {
224  theta = atan(1.0 / _cotTheta);
225  if (theta < 0.0)
226  theta += M_PI;
227  }
228  if (theta == 0.0) {
229  _sinTheta = 0.0;
230  _cosTheta = 1.0;
231  } else {
232  _cosTheta = cos(theta);
234  }
235  if (_phi0 == 0.0) {
236  _sinPhi0 = 0.0;
237  _cosPhi0 = 1.0;
238  } else {
239  _cosPhi0 = cos(_phi0);
240  _sinPhi0 = sin(_phi0);
241  // _sinPhi0 = sqrt(1.0-_cosPhi0*_cosPhi0);
242  // if (_phi0>M_PI) _sinPhi0 = -_sinPhi0;
243  }
244  }
245 }
246 // Update _s, _aa, _ss, and _cc if the arclength has changed.
248  _refreshCache();
249  if (_s != s) {
250  _s = s;
251  _aa = 2.0 * _s * _curvature * _sinTheta;
252  if (_aa == 0.0) {
253  _ss = 0.0;
254  _cc = 1.0;
255  } else {
256  _ss = sin(_aa);
257  _cc = cos(_aa);
258  }
259  }
260 }
HepGeom::Point3D< double > getPosition(double s=0.0) const
double getSinTheta() const
Divides< arg, void > D0
Definition: Factorize.h:135
Sin< T >::type sin(const T &t)
Definition: Sin.h:22
void _refreshCache() const
void setCurvature(double curvature)
float float float z
T curvature(T InversePt, const MagneticField &field)
void setPhi0(double phi0)
double getPathLengthAtRhoEquals(double rho) const
T sqrt(T t)
Definition: SSEVec.h:23
void setZ0(double z0)
Cos< T >::type cos(const T &t)
Definition: Cos.h:22
void setD0(double d0)
double getZAtR(double r) const
double getPathLengthAtZ(double z) const
double getCurvature() const
double getCotTheta() const
d
Definition: ztail.py:151
double getSinPhi0() const
#define M_PI
void getGflashTrajectoryPoint(GflashTrajectoryPoint &point, double s) const
void _cacheSinesAndCosines(double s) const
double getL2DAtR(double r) const
static constexpr float d0
HepGeom::Vector3D< double > getDirection(double s=0.0) const
static const double Z0
double getCosPhi0() const
double getD0() const
double getZ0() const
Geom::Theta< T > theta() const
double getCosTheta() const
*vegas h *****************************************************used in the default bin number in original ***version of VEGAS is ***a higher bin number might help to derive a more precise ***grade subtle point
Definition: invegas.h:5
void setCotTheta(double cotTheta)
void initializeTrajectory(const HepGeom::Vector3D< double > &, const HepGeom::Point3D< double > &, double q, double Field)