29 AngleAxisd aa(AngleAxisd(nyaw, Vector3d::UnitZ()) *
30 AngleAxisd(nroll, Vector3d::UnitX()) *
31 AngleAxisd(npitch, Vector3d::UnitY()));
33 Eigen::Isometry3d retval = Isometry3d::Identity();
34 retval.matrix().block<3, 3>(0, 0) = aa.toRotationMatrix();
35 retval.translation() = Vector3d(nx, ny, nz);
89 void move(
const Isometry3d& newPosition,
int&
id) {
90 Isometry3d delta =
_position.inverse() * newPosition;
100 Matrix6 pinfo = Matrix6::Zero();
113 Matrix6 m = Matrix6::Identity();
114 for (
int i = 0; i < 6; ++i) {
129 Isometry3d newPosition =
_position * delta;
130 move(newPosition,
id);
134 for (
size_t i = 0; i <
_sensors.size(); ++i) {
153 for (WorldItemSet::iterator it =
_world.begin(); it !=
_world.end(); ++it) {
159 void move(
int robotIndex,
const Isometry3d& newRobotPose) {
220 const Isometry3d& robotPose = position;
225 Line3D measuredLine = sensorPose.inverse() * worldLine;
231 measuredLine.
oplus(noise);
233 Matrix4d m = Matrix4d::Zero();
234 m(0, 0) = 1.0 / (
_nline(0));
235 m(1, 1) = 1.0 / (
_nline(1));
236 m(2, 2) = 1.0 / (
_nline(2));
237 m(3, 3) = 1.0 / (
_nline(3));
248int main(
int argc,
char** argv) {
249 bool verbose, robustKernel, fixLines, planarMotion, listSolvers;
254 arg.
param(
"i", maxIterations, 10,
"perform n iterations");
255 arg.
param(
"v", verbose,
false,
"verbose output of the optimization process");
256 arg.
param(
"solver", strSolver,
"lm_var",
"select one specific solver");
257 arg.
param(
"lambdaInit", lambdaInit, 0,
258 "user specified lambda init for levenberg");
259 arg.
param(
"robustKernel", robustKernel,
false,
"use robust error functions");
260 arg.
param(
"fixLines", fixLines,
false,
261 "fix the lines (do localization only)");
262 arg.
param(
"planarMotion", planarMotion,
false,
"robot moves on a plane");
263 arg.
param(
"listSolvers", listSolvers,
false,
"list the solvers");
268 odomOffset->
setId(0);
275 solverFactory->
construct(strSolver, solverProperty);
283 std::cout <<
"Error allocating solver. Allocating \"" << strSolver
284 <<
"\" failed!" << std::endl;
285 std::cout <<
"Available solvers: " << std::endl;
287 std::cout <<
"--------------" << std::endl;
291 std::cout <<
"Creating simulator" << std::endl;
294 std::cout <<
"Creating robot" << std::endl;
297 std::cout <<
"Creating line sensor" << std::endl;
298 Isometry3d sensorPose = Isometry3d::Identity();
300 ls->
_nline << 0.001, 0.001, 0.001, 0.0001;
306 std::cout <<
"Creating landmark line 1" << std::endl;
309 liv << 0.0, 0.0, 5.0, 0.0, 1.0, 0.0;
315 std::cout <<
"Creating landmark line 2" << std::endl;
316 liv << 5.0, 0.0, 0.0, 0.0, 0.0, 1.0;
323 std::cout <<
"Creating landmark line 3" << std::endl;
324 liv << 0.0, 5.0, 0.0, 1.0, 0.0, 0.0;
333 r->_planarMotion =
true;
334 r->_nmovecov << 0.01, 0.0025, 1e-9, 0.001, 0.001, 0.025;
335 q = Quaterniond(AngleAxisd(0.2, Vector3d::UnitZ()).toRotationMatrix());
336 iq = Quaterniond(AngleAxisd(-0.2, Vector3d::UnitZ()).toRotationMatrix());
338 r->_planarMotion =
false;
339 r->_nmovecov << 0.1, 0.005, 1e-9, 0.001, 0.001, 0.05;
340 q = Quaterniond((AngleAxisd(M_PI / 10, Vector3d::UnitZ()) *
341 AngleAxisd(0.1, Vector3d::UnitY()))
342 .toRotationMatrix());
343 iq = Quaterniond((AngleAxisd(-M_PI / 10, Vector3d::UnitZ()) *
344 AngleAxisd(0.1, Vector3d::UnitY()))
345 .toRotationMatrix());
348 Isometry3d delta = Isometry3d::Identity();
351 Isometry3d startPose = Isometry3d::Identity();
352 startPose.matrix().block<3, 3>(0, 0) =
353 AngleAxisd(-0.75 * M_PI, Vector3d::UnitZ()).toRotationMatrix();
354 sim->
move(0, startPose);
358 double delta_t = 0.2;
359 for (
int j = 0; j < l; ++j) {
360 Vector3d tr(1.0, 0.0, 0.0);
361 delta.matrix().block<3, 3>(0, 0) = q.toRotationMatrix();
363 delta.matrix().block<3, 3>(0, 0) = Matrix3d::Identity();
365 delta.translation() = tr * (delta_t * j);
366 Isometry3d iDelta = delta.inverse();
367 for (
int a = 0; a < 2; ++a) {
368 for (
int i = 0; i < k; ++i) {
380 for (
int j = 0; j < l; ++j) {
381 Vector3d tr(1.0, 0.0, 0.0);
382 delta.matrix().block<3, 3>(0, 0) = iq.toRotationMatrix();
384 delta.matrix().block<3, 3>(0, 0) = Matrix3d::Identity();
386 delta.translation() = tr * (delta_t * j);
387 Isometry3d iDelta = delta.inverse();
388 for (
int a = 0; a < 2; ++a) {
389 for (
int i = 0; i < k; ++i) {
401 std::cout << std::endl;
409 ofstream osp(
"line3d.g2o");
411 std::cout <<
"Saved graph on file line3d.g2o, use g2o_viewer to work with it."
EIGEN_STRONG_INLINE const Measurement & measurement() const
accessor functions for the measurement represented by the edge
void setInformation(const InformationType &information)
OptimizableGraph * graph() const
std::set< BaseSensor * > _sensors
const EstimateType & estimate() const
return the current estimate of the vertex
void setEstimate(const EstimateType &et)
set the estimate for the vertex also calls updateCache()
Command line parsing of argc and argv.
bool parseArgs(int argc, char **argv, bool exitOnError=true)
void param(const std::string &name, bool &p, bool defValue, const std::string &desc)
virtual void setMeasurement(const Vector6 &m)
virtual void setMeasurement(const Isometry3 &m)
Edge between two 3D pose vertices.
virtual void setMeasurement(const Isometry3 &m)
const VertexContainer & vertices() const
static G2O_TYPES_SLAM3D_ADDONS_API Line3D fromCartesian(const Vector6 &cart)
G2O_TYPES_SLAM3D_ADDONS_API void oplus(const Vector4 &v)
bool setParameterId(int argNum, int paramId)
A general case Vertex for optimization.
virtual void setId(int id)
void setFixed(bool fixed)
true => this node should be considered fixed during the optimization
create solvers based on their short name
OptimizationAlgorithm * construct(const std::string &tag, OptimizationAlgorithmProperty &solverProperty) const
static OptimizationAlgorithmFactory * instance()
return the instance
void listSolvers(std::ostream &os) const
list the known solvers into a stream
Generic interface for a non-linear solver operating on a graph.
virtual void move(const PoseType &pose_)
virtual void relativeMove(const PoseType &movement_)
static double gaussRand(double mean, double sigma)
void setAlgorithm(OptimizationAlgorithm *algorithm)
OptimizationAlgorithm * solver()
3D pose Vertex, represented as an Isometry3
Eigen::Matrix< double, 6, 6 > Matrix6
#define G2O_USE_OPTIMIZATION_LIBRARY(libraryname)
std::vector< Sensor * > SensorVector
Vector4d sample_noise_from_line(const Vector4d &cov)
std::vector< Robot * > RobotVector
std::set< WorldItem * > WorldItemSet
Eigen::Isometry3d sample_noise_from_se3(const Vector6 &cov)
std::vector< Sensor * > SensorVector
std::vector< Robot * > RobotVector
std::set< WorldItem * > WorldItemSet
LineItem(OptimizableGraph *graph_, int id)
LineSensor(Robot *r, int offsetId, const Isometry3d &offset_)
virtual bool sense(WorldItem *wi, const Isometry3d &position)
VertexSE3 * _offsetVertex
virtual bool isVisible(const WorldItem *wi) const
EIGEN_MAKE_ALIGNED_OPERATOR_NEW
void move(const Isometry3d &newPosition, int &id)
EIGEN_MAKE_ALIGNED_OPERATOR_NEW
void relativeMove(const Isometry3d &delta, int &id)
Robot(OptimizableGraph *graph_)
void sense(WorldItem *wi=0)
virtual bool isVisible(const WorldItem *) const
virtual bool sense(WorldItem *, const Isometry3d &)
OptimizableGraph * _graph
SimulatorItem(OptimizableGraph *graph_)
OptimizableGraph * graph()
void sense(int robotIndex)
void relativeMove(int robotIndex, const Isometry3d &delta)
Simulator(OptimizableGraph *graph_)
void move(int robotIndex, const Isometry3d &newRobotPose)
OptimizableGraph::Vertex * _vertex
WorldItem(OptimizableGraph *graph_, OptimizableGraph::Vertex *vertex_=0)
OptimizableGraph::Vertex * vertex()
void setVertex(OptimizableGraph::Vertex *vertex_)
virtual bool addEdge(HyperGraph::Edge *e)
virtual bool save(std::ostream &os, int level=0) const
save the graph to a stream. Again uses the Factory system.
bool addParameter(Parameter *p)
virtual bool addVertex(HyperGraph::Vertex *v, Data *userData)
Vertex * vertex(int id)
returns the vertex number id appropriately casted
describe the properties of a solver