ACloudViewer  3.9.4
A Modern Library for 3D Data Processing
pose.h
Go to the documentation of this file.
1 // ----------------------------------------------------------------------------
2 // - CloudViewer: www.cloudViewer.org -
3 // ----------------------------------------------------------------------------
4 // Copyright (c) 2018-2024 www.cloudViewer.org
5 // SPDX-License-Identifier: MIT
6 // ----------------------------------------------------------------------------
7 
8 #pragma once
9 
10 #include <Eigen/Core>
11 #include <vector>
12 
13 #include "util/alignment.h"
14 #include "util/types.h"
15 
16 namespace colmap {
17 
18 // Compose the skew symmetric cross product matrix from a vector.
19 Eigen::Matrix3d CrossProductMatrix(const Eigen::Vector3d& vector);
20 
21 // Convert 3D rotation matrix to Euler angles.
22 //
23 // The convention `R = Rx * Ry * Rz` is used,
24 // using a right-handed coordinate system.
25 //
26 // @param R 3x3 rotation matrix.
27 // @param rx, ry, rz Euler angles in radians.
28 void RotationMatrixToEulerAngles(const Eigen::Matrix3d& R,
29  double* rx,
30  double* ry,
31  double* rz);
32 
33 // Convert Euler angles to 3D rotation matrix.
34 //
35 // The convention `R = Rz * Ry * Rx` is used,
36 // using a right-handed coordinate system.
37 //
38 // @param rx, ry, rz Euler angles in radians.
39 //
40 // @return 3x3 rotation matrix.
41 Eigen::Matrix3d EulerAnglesToRotationMatrix(const double rx,
42  const double ry,
43  const double rz);
44 
45 // Convert 3D rotation matrix to Quaternion representation.
46 //
47 // @param rot_mat 3x3 rotation matrix.
48 //
49 // @return Unit Quaternion rotation coefficients (w, x, y, z).
50 Eigen::Vector4d RotationMatrixToQuaternion(const Eigen::Matrix3d& rot_mat);
51 
52 // Convert Quaternion representation to 3D rotation matrix.
53 //
54 // @param qvec Unit Quaternion rotation coefficients (w, x, y, z).
55 //
56 // @return 3x3 rotation matrix.
57 Eigen::Matrix3d QuaternionToRotationMatrix(const Eigen::Vector4d& qvec);
58 
59 // Compose the Quaternion vector corresponding to a identity transformation.
60 inline Eigen::Vector4d ComposeIdentityQuaternion();
61 
62 // Normalize Quaternion vector.
63 //
64 // @param qvec Quaternion rotation coefficients (w, x, y, z).
65 //
66 // @return Unit Quaternion rotation coefficients (w, x, y, z).
67 Eigen::Vector4d NormalizeQuaternion(const Eigen::Vector4d& qvec);
68 
69 // Invert Quaternion vector to return Quaternion of inverse rotation.
70 //
71 // @param qvec Quaternion rotation coefficients (w, x, y, z).
72 //
73 // @return Inverse Quaternion rotation coefficients (w, x, y, z).
74 Eigen::Vector4d InvertQuaternion(const Eigen::Vector4d& qvec);
75 
76 // Concatenate Quaternion rotations such that the rotation of `qvec1` is applied
77 // before the rotation of `qvec2`.
78 //
79 // @param qvec1 Quaternion rotation coefficients (w, x, y, z).
80 // @param qvec2 Quaternion rotation coefficients (w, x, y, z).
81 //
82 // @return Concatenated Quaternion coefficients (w, x, y, z).
83 Eigen::Vector4d ConcatenateQuaternions(const Eigen::Vector4d& qvec1,
84  const Eigen::Vector4d& qvec2);
85 
86 // Transform point by quaternion rotation.
87 //
88 // @param qvec Quaternion rotation coefficients (w, x, y, z).
89 // @param point Point to rotate.
90 //
91 // @return Rotated point.
92 Eigen::Vector3d QuaternionRotatePoint(const Eigen::Vector4d& qvec,
93  const Eigen::Vector3d& point);
94 
95 // Compute the weighted average of multiple Quaternions according to:
96 //
97 // Markley, F. Landis, et al. "Averaging quaternions."
98 // Journal of Guidance, Control, and Dynamics 30.4 (2007): 1193-1197.
99 //
100 // @param qvecs The Quaternions to be averaged.
101 // @param weights Non-negative weights.
102 //
103 // @return The average Quaternion.
104 Eigen::Vector4d AverageQuaternions(const std::vector<Eigen::Vector4d>& qvecs,
105  const std::vector<double>& weights);
106 
107 // Compose rotation matrix that rotates unit vector 1 to unit vector 2.
108 // Note that when vector 1 points into the opposite direction of vector 2,
109 // the function returns an identity rotation.
110 Eigen::Matrix3d RotationFromUnitVectors(const Eigen::Vector3d& vec1,
111  const Eigen::Vector3d& vec2);
112 
113 // Extract camera projection center from projection matrix, i.e. the projection
114 // center in world coordinates `-R^T t`.
115 Eigen::Vector3d ProjectionCenterFromMatrix(
116  const Eigen::Matrix3x4d& proj_matrix);
117 
118 // Extract camera projection center from projection parameters.
119 //
120 // @param qvec Unit Quaternion rotation coefficients (w, x, y, z).
121 // @param tvec 3x1 translation vector.
122 //
123 // @return 3x1 camera projection center.
124 Eigen::Vector3d ProjectionCenterFromPose(const Eigen::Vector4d& qvec,
125  const Eigen::Vector3d& tvec);
126 
127 // Compute the relative transformation from pose 1 to 2.
128 //
129 // @param qvec1, tvec1 First camera pose.
130 // @param qvec2, tvec2 Second camera pose.
131 // @param qvec12, tvec12 Relative pose.
132 void ComputeRelativePose(const Eigen::Vector4d& qvec1,
133  const Eigen::Vector3d& tvec1,
134  const Eigen::Vector4d& qvec2,
135  const Eigen::Vector3d& tvec2,
136  Eigen::Vector4d* qvec12,
137  Eigen::Vector3d* tvec12);
138 
139 // Concatenate the transformations of the two poses.
140 //
141 // @param qvec1, tvec1 First camera pose.
142 // @param qvec2, tvec2 Second camera pose.
143 // @param qvec12, tvec12 Concatenated pose.
144 void ConcatenatePoses(const Eigen::Vector4d& qvec1,
145  const Eigen::Vector3d& tvec1,
146  const Eigen::Vector4d& qvec2,
147  const Eigen::Vector3d& tvec2,
148  Eigen::Vector4d* qvec12,
149  Eigen::Vector3d* tvec12);
150 
151 // Invert transformation of the pose.
152 // @param qvec, tvec Input camera pose.
153 // @param inv_qvec, inv_tvec Inverse camera pose.
154 void InvertPose(const Eigen::Vector4d& qvec,
155  const Eigen::Vector3d& tvec,
156  Eigen::Vector4d* inv_qvec,
157  Eigen::Vector3d* inv_tvec);
158 
159 // Linearly interpolate camera pose.
160 //
161 // @param qvec1, tvec1 Camera pose at t0 = 0.
162 // @param qvec2, tvec2 Camera pose at t1 = 1.
163 // @param t Interpolation time.
164 // @param qveci, tveci Camera pose at time t.
165 void InterpolatePose(const Eigen::Vector4d& qvec1,
166  const Eigen::Vector3d& tvec1,
167  const Eigen::Vector4d& qvec2,
168  const Eigen::Vector3d& tvec2,
169  const double t,
170  Eigen::Vector4d* qveci,
171  Eigen::Vector3d* tveci);
172 
173 // Calculate baseline vector from first to second pose.
174 //
175 // The given rotation and orientation is expected as the
176 // world to camera transformation.
177 //
178 // @param qvec1 Unit Quaternion rotation coefficients (w, x, y, z).
179 // @param tvec1 3x1 translation vector.
180 // @param qvec2 Unit Quaternion rotation coefficients (w, x, y, z).
181 // @param tvec2 3x1 translation vector.
182 //
183 // @return Baseline vector from 1 to 2.
184 Eigen::Vector3d CalculateBaseline(const Eigen::Vector4d& qvec1,
185  const Eigen::Vector3d& tvec1,
186  const Eigen::Vector4d& qvec2,
187  const Eigen::Vector3d& tvec2);
188 
189 // Perform cheirality constraint test, i.e., determine which of the triangulated
190 // correspondences lie in front of of both cameras. The first camera has the
191 // projection matrix P1 = [I | 0] and the second camera has the projection
192 // matrix P2 = [R | t].
193 //
194 // @param R 3x3 rotation matrix of second projection matrix.
195 // @param t 3x1 translation vector of second projection matrix.
196 // @param points1 First set of corresponding points.
197 // @param points2 Second set of corresponding points.
198 // @param points3D Points that lie in front of both cameras.
199 bool CheckCheirality(const Eigen::Matrix3d& R,
200  const Eigen::Vector3d& t,
201  const std::vector<Eigen::Vector2d>& points1,
202  const std::vector<Eigen::Vector2d>& points2,
203  std::vector<Eigen::Vector3d>* points3D);
204 
206 // Implementation
208 
209 Eigen::Vector4d ComposeIdentityQuaternion() {
210  return Eigen::Vector4d(1, 0, 0, 0);
211 }
212 
213 } // namespace colmap
Matrix< double, 3, 4 > Matrix3x4d
Definition: types.h:39
Eigen::Vector3d ProjectionCenterFromMatrix(const Eigen::Matrix3x4d &proj_matrix)
Definition: pose.cc:159
Eigen::Matrix3d RotationFromUnitVectors(const Eigen::Vector3d &vector1, const Eigen::Vector3d &vector2)
Definition: pose.cc:145
void ComputeRelativePose(const Eigen::Vector4d &qvec1, const Eigen::Vector3d &tvec1, const Eigen::Vector4d &qvec2, const Eigen::Vector3d &tvec2, Eigen::Vector4d *qvec12, Eigen::Vector3d *tvec12)
Definition: pose.cc:173
Eigen::Matrix3d EulerAnglesToRotationMatrix(const double rx, const double ry, const double rz)
Definition: pose.cc:59
Eigen::Vector4d ComposeIdentityQuaternion()
Definition: pose.h:209
void InvertPose(const Eigen::Vector4d &qvec, const Eigen::Vector3d &tvec, Eigen::Vector4d *inv_qvec, Eigen::Vector3d *inv_tvec)
Definition: pose.cc:192
Eigen::Matrix3d CrossProductMatrix(const Eigen::Vector3d &vector)
Definition: pose.cc:41
Eigen::Vector4d NormalizeQuaternion(const Eigen::Vector4d &qvec)
Definition: pose.cc:82
Eigen::Vector4d AverageQuaternions(const std::vector< Eigen::Vector4d > &qvecs, const std::vector< double > &weights)
Definition: pose.cc:118
void ConcatenatePoses(const Eigen::Vector4d &qvec1, const Eigen::Vector3d &tvec1, const Eigen::Vector4d &qvec2, const Eigen::Vector3d &tvec2, Eigen::Vector4d *qvec12, Eigen::Vector3d *tvec12)
Definition: pose.cc:183
Eigen::Vector4d RotationMatrixToQuaternion(const Eigen::Matrix3d &rot_mat)
Definition: pose.cc:70
Eigen::Vector4d ConcatenateQuaternions(const Eigen::Vector4d &qvec1, const Eigen::Vector4d &qvec2)
Definition: pose.cc:97
Eigen::Vector4d InvertQuaternion(const Eigen::Vector4d &qvec)
Definition: pose.cc:93
Eigen::Vector3d QuaternionRotatePoint(const Eigen::Vector4d &qvec, const Eigen::Vector3d &point)
Definition: pose.cc:110
Eigen::Vector3d ProjectionCenterFromPose(const Eigen::Vector4d &qvec, const Eigen::Vector3d &tvec)
Definition: pose.cc:164
Eigen::Vector3d CalculateBaseline(const Eigen::Vector4d &qvec1, const Eigen::Vector3d &tvec1, const Eigen::Vector4d &qvec2, const Eigen::Vector3d &tvec2)
Definition: pose.cc:216
void RotationMatrixToEulerAngles(const Eigen::Matrix3d &R, double *rx, double *ry, double *rz)
Definition: pose.cc:48
void InterpolatePose(const Eigen::Vector4d &qvec1, const Eigen::Vector3d &tvec1, const Eigen::Vector4d &qvec2, const Eigen::Vector3d &tvec2, const double t, Eigen::Vector4d *qveci, Eigen::Vector3d *tveci)
Definition: pose.cc:198
bool CheckCheirality(const Eigen::Matrix3d &R, const Eigen::Vector3d &t, const std::vector< Eigen::Vector2d > &points1, const std::vector< Eigen::Vector2d > &points2, std::vector< Eigen::Vector3d > *points3D)
Definition: pose.cc:225
Eigen::Matrix3d QuaternionToRotationMatrix(const Eigen::Vector4d &qvec)
Definition: pose.cc:75