20 #include "Eigen/Dense"
23 namespace VectorHelpers {
39 template <
typename Derived>
40 double phi(
const Eigen::MatrixBase<Derived>&
v) noexcept {
41 constexpr
int rows = Eigen::MatrixBase<Derived>::RowsAtCompileTime;
42 if constexpr (rows != -1) {
44 static_assert(rows >= 2,
45 "Phi function not valid for vectors not at least 2D");
49 "Phi function not valid for vectors not at least 2D");
51 return std::atan2(
v[1],
v[0]);
61 double phi(
const T&
v) noexcept {
71 template <
typename Derived>
72 double perp(
const Eigen::MatrixBase<Derived>&
v) noexcept {
73 constexpr
int rows = Eigen::MatrixBase<Derived>::RowsAtCompileTime;
74 if constexpr (rows != -1) {
76 static_assert(rows >= 2,
77 "Perp function not valid for vectors not at least 2D");
81 "Perp function not valid for vectors not at least 2D");
83 return std::hypot(
v[0],
v[1]);
92 template <
typename Derived>
93 double theta(
const Eigen::MatrixBase<Derived>&
v) noexcept {
94 constexpr
int rows = Eigen::MatrixBase<Derived>::RowsAtCompileTime;
95 if constexpr (rows != -1) {
97 static_assert(rows == 3,
"Theta function not valid for non-3D vectors.");
100 assert(
v.rows() == 3 &&
"Theta function not valid for non-3D vectors.");
103 return std::atan2(
perp(
v),
v[2]);
112 template <
typename Derived>
113 double eta(
const Eigen::MatrixBase<Derived>&
v) noexcept {
114 constexpr
int rows = Eigen::MatrixBase<Derived>::RowsAtCompileTime;
115 if constexpr (rows != -1) {
117 static_assert(rows == 3,
"Eta function not valid for non-3D vectors.");
120 assert(
v.rows() == 3 &&
"Eta function not valid for non-3D vectors.");
123 if (
v[0] == 0. &&
v[1] == 0.) {
124 return std::copysign(std::numeric_limits<double>::infinity(),
v[2]);
126 return std::asinh(
v[2] /
perp(
v));
146 return {cosPhi, sinPhi, cosTheta, sinTheta, invSinTheta};
162 return perp(position);
164 return phi(position);
166 return perp(position) *
phi(position);
168 return theta(position);
170 return eta(position);
172 return position.norm();
174 assert(
false and
"Invalid BinningValue enum value");
175 return std::numeric_limits<double>::quiet_NaN();
187 r.col(0) = m.col(0).cross(v);
188 r.col(1) = m.col(1).cross(v);
189 r.col(2) = m.col(2).cross(v);
196 return pos4.segment<3>(
ePos0);
205 template <
typename vector3_t>
208 -> Eigen::Matrix<typename vector3_t::Scalar, 4, 1> {
209 EIGEN_STATIC_ASSERT_VECTOR_SPECIFIC_SIZE(vector3_t, 3);
211 Eigen::Matrix<typename vector3_t::Scalar, 4, 1> vec4;
230 double phi = std::atan2(trfDir[2], trfDir[0]);
231 double theta = std::atan2(trfDir[2], trfDir[1]);