g2o
sbacam.h
Go to the documentation of this file.
1 // g2o - General Graph Optimization
2 // Copyright (C) 2011 Kurt Konolige
3 // All rights reserved.
4 //
5 // Redistribution and use in source and binary forms, with or without
6 // modification, are permitted provided that the following conditions are
7 // met:
8 //
9 // * Redistributions of source code must retain the above copyright notice,
10 // this list of conditions and the following disclaimer.
11 // * Redistributions in binary form must reproduce the above copyright
12 // notice, this list of conditions and the following disclaimer in the
13 // documentation and/or other materials provided with the distribution.
14 //
15 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
16 // IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
17 // TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
18 // PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
19 // HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
20 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
21 // TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
22 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
23 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
24 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
25 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 
37 
38 #ifndef G2O_SBACam_
39 #define G2O_SBACam_
40 
41 #include <Eigen/Core>
42 #include <Eigen/Geometry>
43 
44 #include "g2o/stuff/misc.h"
45 #include "g2o/stuff/macros.h"
47 
48 #include "g2o_types_sba_api.h"
49 
50 // this seems to have to go outside of the AISNav namespace...
51 //USING_PART_OF_NAMESPACE_EIGEN;
52 
53 namespace g2o {
54 
55  typedef Eigen::Matrix<double, 6, 1> Vector6d;
56 
58  {
59  EIGEN_MAKE_ALIGNED_OPERATOR_NEW
60 
61  public:
62  // camera matrix and stereo baseline
63  Eigen::Matrix3d Kcam;
64  double baseline;
65 
66  // transformations
67  Eigen::Matrix<double,3,4> w2n; // transform from world to node coordinates
68  Eigen::Matrix<double,3,4> w2i; // transform from world to image coordinates
69 
70  // Derivatives of the rotation matrix transpose wrt quaternion xyz, used for
71  // calculating Jacobian wrt pose of a projection.
72  Eigen::Matrix3d dRdx, dRdy, dRdz;
73 
74  // initialize an object
76  {
77  SE3Quat();
78  setKcam(1,1,0.5,0.5,0); // unit image projection
79  }
80 
81 
82  // set the object pose
83  SBACam(const Eigen::Quaterniond& r_, const Eigen::Vector3d& t_) : SE3Quat(r_, t_)
84  {
85  setTransform();
86  setProjection();
87  setDr();
88  }
89 
90  SBACam(const SE3Quat& p) : SE3Quat(p) {
91  setTransform();
92  setProjection();
93  setDr();
94  }
95 
96  // update from the linear solution
97  //defined in se3quat
98  void update(const Vector6d& update)
99  {
100  // std::cout << "UPDATE " << update.transpose() << std::endl;
101  // position update
102  _t += update.head(3);
103  // small quaternion update
104  Eigen::Quaterniond qr;
105  qr.vec() = update.segment<3>(3);
106  qr.w() = sqrt(1.0 - qr.vec().squaredNorm()); // should always be positive
107  _r *= qr; // post-multiply
108  _r.normalize();
109  setTransform();
110  setProjection();
111  setDr();
112  // std::cout << t.transpose() << std::endl;
113  // std::cout << r.coeffs().transpose() << std::endl;
114  }
115 
116  // transforms
117  static void transformW2F(Eigen::Matrix<double,3,4> &m,
118  const Eigen::Vector3d &trans,
119  const Eigen::Quaterniond &qrot)
120  {
121  m.block<3,3>(0,0) = qrot.toRotationMatrix().transpose();
122  m.col(3).setZero(); // make sure there's no translation
123  Eigen::Vector4d tt;
124  tt.head(3) = trans;
125  tt[3] = 1.0;
126  m.col(3) = -m*tt;
127  }
128 
129  static void transformF2W(Eigen::Matrix<double,3,4> &m,
130  const Eigen::Vector3d &trans,
131  const Eigen::Quaterniond &qrot)
132  {
133  m.block<3,3>(0,0) = qrot.toRotationMatrix();
134  m.col(3) = trans;
135  }
136 
137  // set up camera matrix
138  void setKcam(double fx, double fy, double cx, double cy, double tx)
139  {
140  Kcam.setZero();
141  Kcam(0,0) = fx;
142  Kcam(1,1) = fy;
143  Kcam(0,2) = cx;
144  Kcam(1,2) = cy;
145  Kcam(2,2) = 1.0;
146  baseline = tx;
147  setProjection();
148  setDr();
149  }
150 
151  // set transform from world to cam coords
152  void setTransform() { transformW2F(w2n,_t,_r); }
153 
154  // Set up world-to-image projection matrix (w2i), assumes camera parameters
155  // are filled.
156  void setProjection() { w2i = Kcam * w2n; }
157 
158  // sets angle derivatives
159  void setDr()
160  {
161  // inefficient, just for testing
162  // use simple multiplications and additions for production code in calculating dRdx,y,z
163  Eigen::Matrix3d dRidx, dRidy, dRidz;
164  dRidx << 0.0,0.0,0.0,
165  0.0,0.0,2.0,
166  0.0,-2.0,0.0;
167  dRidy << 0.0,0.0,-2.0,
168  0.0,0.0,0.0,
169  2.0,0.0,0.0;
170  dRidz << 0.0,2.0,0.0,
171  -2.0,0.0,0.0,
172  0.0,0.0,0.0;
173 
174  // for dS'*R', with dS the incremental change
175  dRdx = dRidx * w2n.block<3,3>(0,0);
176  dRdy = dRidy * w2n.block<3,3>(0,0);
177  dRdz = dRidz * w2n.block<3,3>(0,0);
178  }
179 
180  };
181 
182 
183  // human-readable SBACam object
184  inline std::ostream& operator <<(std::ostream& out_str,
185  const SBACam& cam)
186  {
187  out_str << cam.translation().transpose() << std::endl;
188  out_str << cam.rotation().coeffs().transpose() << std::endl << std::endl;
189  out_str << cam.Kcam << std::endl << std::endl;
190  out_str << cam.w2n << std::endl << std::endl;
191  out_str << cam.w2i << std::endl << std::endl;
192 
193  return out_str;
194  };
195 
196 
197  //
198  // class for edges from vps to points with normals
199  //
200 
202  {
203  EIGEN_MAKE_ALIGNED_OPERATOR_NEW
204 
205  public:
206  // point position
207  Eigen::Vector3d pos;
208 
209  // unit normal
210  Eigen::Vector3d normal;
211 
212  // rotation matrix for normal
213  Eigen::Matrix3d R;
214 
215  // initialize an object
217  {
218  pos.setZero();
219  normal << 0, 0, 1;
220  makeRot();
221  }
222 
223  // set up rotation matrix
224  void makeRot()
225  {
226  Eigen::Vector3d y;
227  y << 0, 1, 0;
228  R.row(2) = normal;
229  y = y - normal(1)*normal;
230  y.normalize(); // need to check if y is close to 0
231  R.row(1) = y;
232  R.row(0) = normal.cross(R.row(1));
233  // cout << normal.transpose() << endl;
234  // cout << R << endl << endl;
235  // cout << R*R.transpose() << endl << endl;
236  }
237 
238  };
239 
240 } // end namespace
241 
242 
243 #endif // SBACam
#define G2O_TYPES_SBA_API
void setDr()
Definition: sbacam.h:159
double baseline
Definition: sbacam.h:64
SBACam(const SE3Quat &p)
Definition: sbacam.h:90
some general case utility functions
Eigen::Vector3d normal
Definition: sbacam.h:210
void makeRot()
Definition: sbacam.h:224
static void transformF2W(Eigen::Matrix< double, 3, 4 > &m, const Eigen::Vector3d &trans, const Eigen::Quaterniond &qrot)
Definition: sbacam.h:129
SBACam(const Eigen::Quaterniond &r_, const Eigen::Vector3d &t_)
Definition: sbacam.h:83
Eigen::Matrix3d dRdz
Definition: sbacam.h:72
Eigen::Matrix3d Kcam
Definition: sbacam.h:63
void setTransform()
Definition: sbacam.h:152
Eigen::Matrix3d R
Definition: sbacam.h:213
Eigen::Matrix< double, 3, 4 > w2i
Definition: sbacam.h:68
SBACam()
Definition: sbacam.h:75
void setProjection()
Definition: sbacam.h:156
Eigen::Vector3d pos
Definition: sbacam.h:207
const Eigen::Quaterniond & rotation() const
Definition: se3quat.h:97
void update(const Vector6d &update)
Definition: sbacam.h:98
static void transformW2F(Eigen::Matrix< double, 3, 4 > &m, const Eigen::Vector3d &trans, const Eigen::Quaterniond &qrot)
Definition: sbacam.h:117
std::ostream & operator<<(std::ostream &os, const G2OBatchStatistics &st)
Definition: batch_stats.cpp:48
void setKcam(double fx, double fy, double cx, double cy, double tx)
Definition: sbacam.h:138
Eigen::Matrix< double, 3, 4 > w2n
Definition: sbacam.h:67
const Vector3D & translation() const
Definition: se3quat.h:93
Matrix< double, 6, 1, Eigen::ColMajor > Vector6d
Definition: types_icp.cpp:75